Microsoft MVP성태의 닷넷 이야기
디버깅 기술: 14. TFS 오류 추적(TF53010, TF14105) [링크 복사], [링크+제목 복사],
조회: 30013
글쓴 사람
정성태 (techsharer at outlook.com)
홈페이지
첨부 파일
 


TFS 오류 추적(TF53010, TF14105)


요즘... 제 TFS 서버 상태가 말이 아니군요. 이거저거 계정 지워가면서 임의로 DB 레코드 지워가다 보니, 아무리 테스트를 위한 TFS 서버라지만 왠지 제가 너무했다는 생각이 들 정도입니다. ^^; 그러다 보니, 이번에 설명하는 상황은 매우 특수할 수 있기 때문에 여러분들이 이와 같은 오류 상황을 겪을 일은 매우 드물긴 하겠지만, 저 스스로의 문제 해결의 흐름을 기억해 두기 위해서라도 이렇게 토픽으로 남겨봅니다.

어쨌든, 최근에 제가 TFS를 완전히 엉망으로 만들어 놨던 것은, 얼마 전 "TF10217, TF53010, TF14105 오류" 문제를 해결하는 과정에서 제가 임의로 삭제했던 DB 레코드들로 인한 것이었습니다. 그 토픽에서 소개했던 "View History Errors"에서 설명된 해결 방법을 따르지 않고, 없어진 OwnerId에 해당하는 모든 tbl_Changeset의 레코드를 전부 "Delete From..."으로 삭제했더니... ^^; 그 이후로, 이벤트 로그에는 1시간마다 다음과 같은 오류가 남기 시작했습니다.

이벤트 형식: 오류
이벤트 원본: TFS Version Control
이벤트 범주: 없음
이벤트 ID: 3000
날짜:  2007-03-03
시간:  오후 9:08:37
사용자:  N/A
컴퓨터: WIN2003TEST
설명:
TF53010: An unexpected condition has occurred in a Team Foundation component. The information contained here should be made available to your site administrative staff.
Technical Information (for the administrative staff):
Date (UTC): 2007-03-03 오후 12:08:37
Machine: WIN2003TEST
Application Domain: /LM/W3SVC/3/Root/VersionControl-3-128173432737780965
Assembly: Microsoft.TeamFoundation.Common, Version=8.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a; v2.0.50727
Process Details:
  Process Name: w3wp
  Process Id: 4996
  Thread Id: 2244
  Account name: TESTDOMAIN\TFSTEST

Detailed Message: TF14105: An exception occurred in the Team Foundation Source Control System.
Web Request Details
    Url: https://www.sysnet.pe.kr:8070/VersionControl/v1.0/repository.asmx [method: POST]
    User Agent: Team Foundation (w3wp.exe[Data Warehouse], 8.0.50727.762)
    Headers: Content-Length...[중간생략]...e-1812-412b-943f-4fbddda715ae
    Path: /VersionControl/v1.0/repository.asmx
    Local Request: False
    Host Address: 192.168.1.100
    User: TESTDOMAIN\TFSTEST [authentication type: NTLM]

Exception Message: Invalid attempt to read when no data is present. (type InvalidOperationException)

Exception Stack Trace:    at System.Data.SqlClient.SqlDataReader.ReadColumnHeader(Int32 i)
   at System.Data.SqlClient.SqlDataReader.IsDBNull(Int32 i)
   at Microsoft.TeamFoundation.Server.SqlColumnBinder.GetDateTime(SqlDataReader reader)
   at Microsoft.TeamFoundation.VersionControl.Server.VersionedItemComponent.ChangesetColumns.bind(SqlDataReader reader)
   at Microsoft.TeamFoundation.VersionControl.Server.VersionedItemComponent.QueryChangeset(Int32 changeset, Boolean includeChanges, IList changes, Changeset& changesetInfo)
   at Microsoft.TeamFoundation.VersionControl.Server.Changeset.QueryChangeset(IPrincipal userPrincipal, Int32 changeset, Boolean includeChanges, Boolean generateDownloadUrls)
   at Microsoft.TeamFoundation.VersionControl.Server.Repository.QueryChangeset(Int32 changesetId, Boolean includeChanges, Boolean generateDownloadUrls)

원인은, TFSServerScheduler가 해당 요청을 1시간마다 주기적으로 발생시키는 것에서 기인했습니다.




문제는 단지 TFSServerScheduler에 대한 요청을 정상적으로 처리하지 못한 것만이 아니었습니다. 애석하게도, "팀 프로젝트"로 등록된 것들 중 몇 개는 그와 연결된 "소스 컨트롤"을 열려고 하면 아래와 같은 에러를 내면서 진행이 되지 않았습니다.

tfs_vss_error_tf10175_1.png
"
Configure Source Control

Either source control has not been configured for this team project or
you do not have permission to access it. Would you like to create the
source control folder, $/SysnetSite?
"

게다가 해당 소스 컨트롤에 등록된 솔루션 프로젝트를 열려고 하면 아래와 같은 에러 메시지가 뜨고.

tfs_vss_error_tf10175_2.png
"
The solution appears to be under source control, but its binding information cannot be found. Because it is not
possible to recover this missing information automatically, the projects whose bindings are missing will be treated as
not under source control.
"

물론, "Source Control Explorer"에는 아래와 같이 등록되어 있으며, 그 중의 아무 파일이나 "check-out"을 하려고 하면 다음과 같은 오류 메시지가 "Output" 윈도우에 남게 됩니다.

"
TF10175: The team project folder $/SysnetSite does not exist. 
Contact your Team Foundation Server administrator and ask that it be created.
"

심지어, 아래와 같이 Workspace 관리창에서 현재 등록된 Team Project 목록에도 누락되어 있습니다. (보시는 것처럼, "SysnetSite" 팀 프로젝트가 목록에 없습니다.)

tfs_vss_error_tf10175_3.png




일단, 문제 자체는 "Changeset" 테이블에서 삭제된 changeset 레코드들을 다시 복원하면 그만이었지만. 저는 그 실수를 전혀 모르는 상태라는 가정으로 이 문제를 풀어보고 싶었습니다.

우선, 이벤트 로그를 살펴보면 Process ID는 4996이고, 발생한 예외는 "InvalidOperationException"임을 알 수 있습니다. 이 정보를 바탕으로 문제를 추적하기 위한 2가지의 방법이 생각났습니다. 하나는 WinDBG를 이용하여 "Microsoft.TeamFoundation.VersionControl.Server.Repository.QueryChangeset" 메서드가 실행될 때의 인자값을 확인하는 것과, 또 하나는 HttpModule을 web.config에 등록해서 "QueryChangeset" 메서드를 담고 있는 repository.asmx가 호출될 때의 인자값을 확인하는 방법입니다.

이번에는 ^^ 그동안의 토픽들(Main Method에 Break Point 걸기, Managed Method에 Break Point 걸기, 예외 발생 시 Minidump 생성 - WinDBG)에 대한 실습 삼아서 WinDBG로 알아내는 것을 선택해 보았습니다.(사실 ^^ 바로 이번 이야기를 위해서 그와 같은 토픽들을 써온 것이었습니다.)

처음에는 미니덤프를 떠서 확인해 보려고 했습니다. 이벤트 로그의 내용을 기반으로 windbg를 실행시킨 후, "File" / "Attach to Process..." 메뉴를 이용하여 PID 값이 "4996"인 w3wp.exe에 디버거를 연결시켰습니다. 그리고는, ".loadby sos mscorwks" 명령어등의 기초 작업을 한 후, "!soe" 확장 명령어를 다음과 같이 실행시켰습니다.

!soe -create System.InvalidOperationException 1

이어서, "Debug" / "Event Filters..." 메뉴를 선택하여 "CLR exception"의 "Commands..." 설정을 다음으로 대체했습니다.

!soe  System.InvalidOperationException 1;.if(@$t1==0) {g} .else {.dump /ma /u c:\\temp\\ANE.dmp;}

자... 이제 여유를 가지고 ^^ 예외가 발생할 때까지 (1시간마다 발생했으니) 기다리면 됩니다. 그러면, "System.InvalidOperationException" 예외가 발생하자마자 다음과 같은 내용이 windbg 화면에 출력되면서 미니덤프 파일이 남겨지게 됩니다.

(1384.1474): CLR exception - code e0434f4d (first chance)
Creating c:\\temp\\ANE_1778_2007-03-02_01-15-17-452_1384.dmp - mini user dump
Dump successfully written
First chance exceptions are reported before any exception handling.
This exception may be expected and handled.
eax=05afebe0 ebx=048ca748 ecx=00000000 edx=00000025 esi=05afec6c edi=e0434f4d
eip=7c815e02 esp=05afebdc ebp=05afec30 iopl=0         nv up ei pl nz na po nc
cs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000202
kernel32!RaiseException+0x53:
7c815e02 5e              pop     esi

자... 이제 "c:\\temp\\ANE_1778_2007-03-02_01-15-17-452_1384.dmp" 파일을 자신의 개발 환경에 복사한 후 windbg.exe에서 "File" / "Open Crash Dump..." 메뉴를 통해 로드를 합니다. 그다음 역시 ".loadby sos mscorwks" 명령 후 "!clrstack -a" 명령을 실행하니 다음과 같은 결과가 나왔습니다.

0:018> !loadby sos mscorwks
0:018> !clrstack -a
OS Thread Id: 0x1474 (18)
ESP       EIP     
05afecb8 7c815e02 [HelperMethodFrame: 05afecb8] 
05afed5c 6539fdcc System.Data.SqlClient.SqlDataReader.ReadColumnHeader(Int32)
    PARAMETERS:
        this = <no data>
        i = <no data>
    LOCALS:
        <no data>
        ...[중간 생략]...
        
05afee68 009c0783 Microsoft.TeamFoundation.VersionControl.Server.Repository.QueryChangeset(Int32, Boolean, Boolean)
    PARAMETERS:
        this = 0x0304cacc
        changesetId = <no data>
        includeChanges = <no data>
        generateDownloadUrls = <no data>
    LOCALS:
        <no data>
        0x05afee80 = 0x00000000

...[중간 생략]...

05aff5d0 65fbc567 System.Web.Hosting.ISAPIRuntime.ProcessRequest(IntPtr, Int32)

05aff780 79f1ef33 [ContextTransitionFrame: 05aff780] 
05aff7d0 79f1ef33 [GCFrame: 05aff7d0] 
05aff928 79f1ef33 [ComMethodFrame: 05aff928] 

아... 이런... 실망이군요. 왜 changesetId, includeChanges, generateDownloadUrls 인자들의 값이 미니덤프에는 없는 걸까요? 덤프 옵션도 "/ma"로 했는데... 혹시 이 부분에 대해서 의견주실 분이 계시면 ^^ 댓글 부탁드리겠습니다.

어쨌든, 미니덤프는 예외가 발생했을 때는 이미 시점이 늦은 것 같고, 아마도 "QueryChangeset" 메서드가 실행되는 시점에는 가능하지 않을까 라는 생각이 들어서, 다시 w3wp.exe에 디버거를 연결해서 다음과 같이 "QueryChangeset"에 대해서 정지점을 걸었습니다.

0:027> !bpmd Microsoft.TeamFoundation.VersionControl.Server.DLL Microsoft.TeamFoundation.VersionControl.Server.Repository.QueryChangeset
Found 1 methods...
MethodDesc = 05882be8
Setting breakpoint: bp 05BDC0D8 [Microsoft.TeamFoundation.VersionControl.Server.Repository.QueryChangeset(Int32, Boolean, Boolean)]
0:027> g
Breakpoint 0 hit
eax=0754eb60 ebx=0754eadc ecx=0798c1ac edx=000000e7 esi=054abff8 edi=00000000
eip=05bdc0d8 esp=0754eaac ebp=0754eac0 iopl=0         nv up ei pl zr na pe nc
cs=001b  ss=0023  ds=0023  es=0023  fs=003b  gs=0000             efl=00000246
05bdc0d8 55              push    ebp

다행히도, 이번에는 인자값을 다음과 같이 확인할 수 있었습니다.

0:022> !clrstack -a
OS Thread Id: 0x10ac (22)
ESP       EIP     
0754eaac 05bdc0d8 Microsoft.TeamFoundation.VersionControl.Server.Repository.QueryChangeset(Int32, Boolean, Boolean)
    PARAMETERS:
        this = 0x0798c1ac
        changesetId = 0x000000e7  // 231
        includeChanges = 0x00000001
        generateDownloadUrls = 0x00000000
    LOCALS:
        <no data>
        <no data>
... [생략]...

이제, 해당 changesetId 값대로 "TfsVersionControl" DB의 "tbl_ChangeSet"에서 231번 값을 갖는 레코드를 확인해 봤습니다. 당연히 ^^ 없었습니다. 이제부터가 문제군요. ^^; 함부로 삭제했던 "tbl_ChangeSet" 테이블 내용을 채워넣어야 하는데 어떤 값들을 채워야 할지 고민이 되었습니다. 그나저나... "QueryChangeset"을 포함한 asmx를 호출하는 TFSServerScheduler가 어떻게 해당 ChangesetId 값들을 알수 있었을 까 싶어서, 다른 DB의 테이블들을 찾아보았습니다. 오... 다행히도 "TFSWarehouse" DB의 "Changeset" 테이블이 있는 것이 눈에 띄였습니다. 이제부턴 간단하지요! "tbl_ChangeSet" 테이블에 삭제된 값들을 "Changeset" 테이블로부터 모두 가져왔습니다.

대충 다음과 같은 식으로 내용을 채웠습니다.

tbl_ChangeSet

ChangeSetId : TFSWarehouse DB의 "Changeset" 테이블에 있는 ChangeSet ID 필드로부터 값을 가져옴
OwnerId : TfsVersionControl DB의 "tbl_Identity" 테이블에 있는 적절한 IdentityId 필드로부터 값을 가져옴
CreateDate : : TFSWarehouse DB의 "Changeset" 테이블에 있는 __LastUpdatedTime 필드로부터 값을 가져옴
Comment : NULL
ExtendedComment : NULL
CheckInNoteId : 기존 값들 중 하나
CommitterId : OwnerId 값과 동일하게 설정.

물론, 두말할 필요도 없겠지만 백업 받아둔 것이 있다면 거기서 복구하시는 것이 좋겠지요. ^^; (애석하게도 저는 VPC 단위로 복사만 해두었을 뿐, DBA 수준의 백업은 하지 않고 있었습니다. 음... 이해해주십시오. 테스트 환경입니다. ^^)

휴... 이렇게 하고 나서야 1시간마다 남겨지는 이벤트 로그 오류는 사라지게 되었습니다.




그래도, 약간의 문제가 더 있었습니다. 기존에 "없어진 것"으로 취급되었던 팀 프로젝트들에 연결되어 있던 솔루션을 VS.NET 2005에서 열려고 했을 때 발생하던 다음의 오류는 계속 나타났습니다.

tfs_vss_error_tf10175_2.png

"Source Control Explorer"에서 Workspace에 대해 WorkingFolder를 수동으로 매핑시키려고 해도 다음과 같은 오류가 발생하면서 더 이상 진행할 수 없었습니다.

tfs_vss_error_tf10175_5.png
"
The working folder '...' is already in use by
another workspace on this computer.
"

휴... 가능한 더 이상 DB 레코드를 직접 건드리기 싫지만, 어쩔 수 없게 되었습니다. 우선, "TfsVersionControl" DB의 "tbl_WorkingFolder" 테이블을 검사해보니, 다행히 문제의 원인을 알 수 있었습니다. 다음 그림과 같이 "WorkspaceId" 값이 현재는 존재하지 않는 값들로 (여기서는 1) 채워져 있었습니다.

tfs_vss_error_tf10175_6.png

그래서, tbl_Workspace의 OwnerId 값이 제 계정으로 되어 있는 WorkspaceId 값을 "tbl_WorkingFolder"의 "WorkspaceId" 값으로 업데이트를 했습니다. 와~~~ ^^ 이제서야 모든 문제가 해결되었습니다.



[이 토픽에 대해서 여러분들과 의견을 공유하고 싶습니다. 틀리거나 미흡한 부분 또는 의문 사항이 있으시면 언제든 댓글 남겨주십시오.]







[최초 등록일: ]
[최종 수정일: 6/25/2021]

Creative Commons License
이 저작물은 크리에이티브 커먼즈 코리아 저작자표시-비영리-변경금지 2.0 대한민국 라이센스에 따라 이용하실 수 있습니다.
by SeongTae Jeong, mailto:techsharer at outlook.com

비밀번호

댓글 작성자
 




... 121  122  123  124  125  126  127  128  129  130  [131]  132  133  134  135  ...
NoWriterDateCnt.TitleFile(s)
1780정성태10/15/201424118오류 유형: 249. The application-specific permission settings do not grant Local Activation permission for the COM Server application with CLSID
1779정성태10/15/201419633오류 유형: 248. Active Directory에서 OU가 지워지지 않는 경우
1778정성태10/10/201418073오류 유형: 247. The Netlogon service could not create server share C:\Windows\SYSVOL\sysvol\[도메인명]\SCRIPTS.
1777정성태10/10/201421179오류 유형: 246. The processing of Group Policy failed. Windows attempted to read the file \\[도메인]\sysvol\[도메인]\Policies\{...GUID...}\gpt.ini
1776정성태10/10/201418184오류 유형: 245. 이벤트 로그 - Name resolution for the name _ldap._tcp.dc._msdcs.[도메인명]. timed out after none of the configured DNS servers responded.
1775정성태10/9/201419297오류 유형: 244. Visual Studio 디버깅 (2) - Unable to break execution. This process is not currently executing the type of code that you selected to debug.
1774정성태10/9/201426535개발 환경 구성: 246. IIS 작업자 프로세스의 20분 자동 재생(Recycle)을 끄는 방법
1773정성태10/8/201429728.NET Framework: 471. 웹 브라우저로 다운로드가 되는 파일을 왜 C# 코드로 하면 안되는 걸까요? [1]
1772정성태10/3/201418486.NET Framework: 470. C# 3.0의 기본 인자(default parameter)가 .NET 1.1/2.0에서도 실행될까? [3]
1771정성태10/2/201428007개발 환경 구성: 245. 실행된 프로세스(EXE)의 명령행 인자를 확인하고 싶다면 - Sysmon [4]
1770정성태10/2/201421612개발 환경 구성: 244. 매크로 정의를 이용해 파일 하나로 C++과 C#에서 공유하는 방법 [1]파일 다운로드1
1769정성태10/1/201424035개발 환경 구성: 243. Scala 개발 환경 구성(JVM, 닷넷) [1]
1768정성태10/1/201419427개발 환경 구성: 242. 배치 파일에서 Thread.Sleep 효과를 주는 방법 [5]
1767정성태10/1/201424586VS.NET IDE: 94. Visual Studio 2012/2013에서의 매크로 구현 - Visual Commander [2]
1766정성태10/1/201422389개발 환경 구성: 241. 책 "프로그래밍 클로저: Lisp"을 읽고 나서. [1]
1765정성태9/30/201425963.NET Framework: 469. Unity3d에서 transform을 변수에 할당해 사용하는 특별한 이유가 있을까요?
1764정성태9/30/201422191오류 유형: 243. 파일 삭제가 안 되는 경우 - The action can't be comleted because the file is open in System
1763정성태9/30/201423802.NET Framework: 468. PDB 파일을 연동해 소스 코드 라인 정보를 알아내는 방법파일 다운로드1
1762정성태9/30/201424503.NET Framework: 467. 닷넷에서 EIP/RIP 레지스터 값을 구하는 방법 [1]파일 다운로드1
1761정성태9/29/201421502.NET Framework: 466. 윈도우 운영체제의 보안 그룹 이름 및 설명 문자열을 바꾸는 방법파일 다운로드1
1760정성태9/28/201419769.NET Framework: 465. ICorProfilerInfo::GetILToNativeMapping 메서드가 0x80131358을 반환하는 경우
1759정성태9/27/201430955개발 환경 구성: 240. Visual C++ / x64 환경에서 inline-assembly를 매크로 어셈블리로 대체하는 방법파일 다운로드1
1758정성태9/23/201437780개발 환경 구성: 239. 원격 데스크톱 접속(RDP)을 기존의 콘솔 모드처럼 사용하는 방법 [1]
1757정성태9/23/201418361오류 유형: 242. Lync로 모임 참여 시 소리만 들리지 않는 경우 - 두 번째 이야기
1756정성태9/23/201427339기타: 48. NVidia 제품의 과다한 디스크 사용 [2]
1755정성태9/22/201434128오류 유형: 241. Unity Web Player를 설치해도 여전히 설치하라는 화면이 나오는 경우 [4]
... 121  122  123  124  125  126  127  128  129  130  [131]  132  133  134  135  ...