Annotation of mstools/samples/sdktools/image/drwatson/debug.c, revision 1.1

1.1     ! root        1: /*++
        !             2: 
        !             3: Copyright (c) 1993  Microsoft Corporation
        !             4: 
        !             5: Module Name:
        !             6: 
        !             7:     debug.c
        !             8: 
        !             9: Abstract:
        !            10: 
        !            11:     This file implements the debug module for drwatson.  This module
        !            12:     processes all debug events and generates the postmortem dump.
        !            13: 
        !            14: Author:
        !            15: 
        !            16:     Wesley Witt (wesw) 1-May-1993
        !            17: 
        !            18: Environment:
        !            19: 
        !            20:     User Mode
        !            21: 
        !            22: --*/
        !            23: 
        !            24: #include <windows.h>
        !            25: #include <stdlib.h>
        !            26: #include <stdio.h>
        !            27: #include <string.h>
        !            28: 
        !            29: #include "drwatson.h"
        !            30: #include "proto.h"
        !            31: #include "messages.h"
        !            32: #include "resource.h"
        !            33: 
        !            34: typedef struct _tagSYSINFO {
        !            35:     char    szUserName[MAX_PATH];
        !            36:     char    szMachineName[MAX_PATH];
        !            37: } SYSINFO, *PSYSINFO;
        !            38: 
        !            39: 
        !            40: #define DBG_EXCEPTION_HANDLED           ((DWORD)0x00010001L)
        !            41: #define STATUS_POSSIBLE_DEADLOCK        ((DWORD)0xC0000194L)
        !            42: #define STATUS_SEGMENT_NOTIFICATION     ((DWORD)0x40000005L)
        !            43: #define STATUS_VDM_EVENT                STATUS_SEGMENT_NOTIFICATION
        !            44: 
        !            45: PMODULEINFO AllocMi( PDEBUGPACKET dp );
        !            46: PTHREADCONTEXT AllocTctx( PDEBUGPACKET dp );
        !            47: void PostMortemDump( PDEBUGPACKET dp, LPEXCEPTION_DEBUG_INFO ed );
        !            48: void AttachToActiveProcess ( PDEBUGPACKET dp );
        !            49: void ProcessCreateProcess( PDEBUGPACKET dp, LPDEBUG_EVENT de );
        !            50: void ProcessCreateThread( PDEBUGPACKET dp, LPDEBUG_EVENT de );
        !            51: void ProcessLoadDll( PDEBUGPACKET dp, LPDEBUG_EVENT de );
        !            52: void LogSystemInformation( PDEBUGPACKET dp );
        !            53: DWORD SysInfoThread( PSYSINFO si );
        !            54: void LogDisassembly( PDEBUGPACKET dp, PCRASHES pCrash );
        !            55: void LogStackWalk( PDEBUGPACKET dp );
        !            56: void LogStackDump( PDEBUGPACKET dp );
        !            57: char * GetExceptionText( DWORD dwExceptionCode );
        !            58: 
        !            59: 
        !            60: DWORD
        !            61: DispatchDebugEventThread( PDEBUGPACKET dp )
        !            62: 
        !            63: /*++
        !            64: 
        !            65: Routine Description:
        !            66: 
        !            67:     This is the entry point for DRWTSN32
        !            68: 
        !            69: Arguments:
        !            70: 
        !            71:     None.
        !            72: 
        !            73: Return Value:
        !            74: 
        !            75:     None.
        !            76: 
        !            77: --*/
        !            78: 
        !            79: {
        !            80:     DEBUG_EVENT   de;
        !            81:     DWORD         rc = 0;
        !            82:     char          szLogFileName[1024];
        !            83:     char          buf[1024];
        !            84: 
        !            85: 
        !            86:     if (dp->dwPidToDebug == 0) {
        !            87:         rc = 1;
        !            88:         goto exit;
        !            89:     }
        !            90: 
        !            91:     SetErrorMode( SEM_FAILCRITICALERRORS |
        !            92:                   SEM_NOGPFAULTERRORBOX  |
        !            93:                   SEM_NOOPENFILEERRORBOX   );
        !            94: 
        !            95:     AttachToActiveProcess( dp );
        !            96: 
        !            97:     strcpy( szLogFileName, dp->options.szLogPath );
        !            98:     MakeLogFileName( szLogFileName );
        !            99:     OpenLogFile( szLogFileName,
        !           100:                  dp->options.fAppendToLogFile,
        !           101:                  dp->options.fVisual
        !           102:                );
        !           103: 
        !           104:     while (TRUE) {
        !           105:         if (!WaitForDebugEvent( &de, 10000 )) {
        !           106:             rc = GetLastError();
        !           107:             goto exit;
        !           108:         }
        !           109:         switch (de.dwDebugEventCode) {
        !           110:             case EXCEPTION_DEBUG_EVENT:
        !           111:                 if (de.u.Exception.ExceptionRecord.ExceptionCode == STATUS_BREAKPOINT) {
        !           112:                     if (de.u.Exception.dwFirstChance) {
        !           113:                         if ( dp->hEventToSignal ) {
        !           114:                             SetEvent(dp->hEventToSignal);
        !           115:                             dp->hEventToSignal = 0L;
        !           116:                         }
        !           117:                         ContinueDebugEvent( de.dwProcessId, de.dwThreadId, DBG_EXCEPTION_HANDLED );
        !           118:                         continue;
        !           119:                     }
        !           120:                 }
        !           121:                 if (dp->options.fVisual) {
        !           122:                     //
        !           123:                     // this notification is necessary because the shell must know when
        !           124:                     // the debugee has been attached.  if it doesn't know and the user is
        !           125:                     // allowed to terminate drwatson then the system may intervene with
        !           126:                     // a popup.
        !           127:                     //
        !           128:                     SendMessage( dp->hwnd, WM_ATTACHCOMPLETE, 0, 0 );
        !           129:                     wsprintf( buf,
        !           130:                               LoadRcString( IDS_AE_TEXT ),
        !           131:                               GetExceptionText(de.u.Exception.ExceptionRecord.ExceptionCode),
        !           132:                               de.u.Exception.ExceptionRecord.ExceptionCode,
        !           133:                               de.u.Exception.ExceptionRecord.ExceptionAddress );
        !           134:                     SendMessage( dp->hwnd, WM_EXCEPTIONINFO, 0, (LPARAM) buf );
        !           135:                 }
        !           136:                 PostMortemDump( dp, &de.u.Exception );
        !           137:                 ContinueDebugEvent( de.dwProcessId, de.dwThreadId, DBG_EXCEPTION_NOT_HANDLED );
        !           138:                 continue;
        !           139: 
        !           140:             case CREATE_THREAD_DEBUG_EVENT:
        !           141:                 ProcessCreateThread( dp, &de );
        !           142:                 break;
        !           143: 
        !           144:             case CREATE_PROCESS_DEBUG_EVENT:
        !           145:                 ProcessModuleLoad( dp, &de );
        !           146:                 de.u.CreateThread.hThread = de.u.CreateProcessInfo.hThread;
        !           147:                 ProcessCreateThread( dp, &de );
        !           148:                 break;
        !           149: 
        !           150:             case EXIT_THREAD_DEBUG_EVENT:
        !           151:                 break;
        !           152: 
        !           153:             case EXIT_PROCESS_DEBUG_EVENT:
        !           154:                 goto exit;
        !           155:                 break;
        !           156: 
        !           157:             case LOAD_DLL_DEBUG_EVENT:
        !           158:                 ProcessModuleLoad( dp, &de );
        !           159:                 break;
        !           160: 
        !           161:             case UNLOAD_DLL_DEBUG_EVENT:
        !           162:                 break;
        !           163: 
        !           164:             case OUTPUT_DEBUG_STRING_EVENT:
        !           165:                 break;
        !           166: 
        !           167:             case RIP_EVENT:
        !           168:                 break;
        !           169: 
        !           170:             default:
        !           171:                 lprintf( MSG_INVALID_DEBUG_EVENT, de.dwDebugEventCode );
        !           172:                 break;
        !           173:         }
        !           174:         ContinueDebugEvent( de.dwProcessId, de.dwThreadId, DBG_CONTINUE );
        !           175:     }
        !           176: 
        !           177: exit:
        !           178:     CloseLogFile();
        !           179: 
        !           180:     if (dp->options.fVisual) {
        !           181:         SendMessage( dp->hwnd, WM_DUMPCOMPLETE, 0, 0 );
        !           182:     }
        !           183: 
        !           184:     return 0;
        !           185: }
        !           186: 
        !           187: PTHREADCONTEXT
        !           188: AllocTctx( PDEBUGPACKET dp )
        !           189: {
        !           190:     PTHREADCONTEXT ptctx;
        !           191: 
        !           192:     ptctx = (PTHREADCONTEXT) malloc( sizeof(THREADCONTEXT) );
        !           193:     if (ptctx == NULL) {
        !           194:         if (dp->options.fVisual) {
        !           195:             FatalError( LoadRcString(IDS_MEMORY) );
        !           196:         }
        !           197:         else {
        !           198:             ExitProcess( 1 );
        !           199:         }
        !           200:     }
        !           201:     memset( ptctx, 0, sizeof(THREADCONTEXT) );
        !           202: 
        !           203:     if (dp->tctxHead == NULL) {
        !           204:         dp->tctxHead = dp->tctxTail = ptctx;
        !           205:     }
        !           206:     else {
        !           207:         dp->tctxTail->next = ptctx;
        !           208:         dp->tctxTail = ptctx;
        !           209:     }
        !           210: 
        !           211:     return ptctx;
        !           212: }
        !           213: 
        !           214: void
        !           215: ProcessCreateThread( PDEBUGPACKET dp, LPDEBUG_EVENT de )
        !           216: {
        !           217:     dp->tctx              = AllocTctx( dp );
        !           218:     dp->tctx->hThread     = de->u.CreateThread.hThread;
        !           219:     dp->tctx->dwThreadId  = de->dwThreadId;
        !           220: 
        !           221:     return;
        !           222: }
        !           223: 
        !           224: void
        !           225: PostMortemDump( PDEBUGPACKET dp, LPEXCEPTION_DEBUG_INFO ed )
        !           226: {
        !           227:     PMODULEINFO       mi = dp->miHead;
        !           228:     PTHREADCONTEXT    ptctx;
        !           229:     char              dbuf[1024];
        !           230:     char              szDate[20];
        !           231:     char              szTime[20];
        !           232:     CRASHES           crash;
        !           233:     DWORD             dwThreadId;
        !           234:     HANDLE            hThread;
        !           235: 
        !           236: 
        !           237:     GetLocalTime( &crash.time );
        !           238:     crash.dwExceptionCode = ed->ExceptionRecord.ExceptionCode;
        !           239:     crash.dwAddress = (DWORD)ed->ExceptionRecord.ExceptionAddress;
        !           240:     strcpy( crash.szAppName, dp->miHead->szName );
        !           241: 
        !           242:     lprintf( MSG_APP_EXCEPTION );
        !           243:     wsprintf( dbuf, "%d", dp->dwPidToDebug );
        !           244:     lprintf( MSG_APP_EXEP_NAME, crash.szAppName, dbuf );
        !           245:     wsprintf( szDate, "%d/%d/%d", crash.time.wMonth,
        !           246:                                   crash.time.wDay,
        !           247:                                   crash.time.wYear );
        !           248:     wsprintf( szTime, "%d:%d:%d.%d", crash.time.wHour,
        !           249:                                      crash.time.wMinute,
        !           250:                                      crash.time.wSecond,
        !           251:                                      crash.time.wMilliseconds );
        !           252:     lprintf( MSG_APP_EXEP_WHEN, szDate, szTime );
        !           253:     wsprintf( dbuf, "%08lx", ed->ExceptionRecord.ExceptionCode );
        !           254:     lprintf( MSG_EXCEPTION_NUMBER, dbuf );
        !           255: 
        !           256: 
        !           257:     lprintfs( "(%s)\r\n\r\n",
        !           258:               GetExceptionText(ed->ExceptionRecord.ExceptionCode) );
        !           259: 
        !           260:     LogSystemInformation( dp );
        !           261: 
        !           262:     LogTaskList();
        !           263: 
        !           264:     mi = dp->miHead;
        !           265:     lprintf( MSG_MODULE_LIST );
        !           266:     while (mi) {
        !           267:         lprintfs( "(%08x - %08x) %s\r\n",
        !           268:                   (DWORD)mi->dwLoadAddress,
        !           269:                   (DWORD)mi->dwLoadAddress + mi->dwImageSize,
        !           270:                   mi->szName
        !           271:                 );
        !           272:         mi = mi->next;
        !           273:     }
        !           274:     lprintfs( "\r\n" );
        !           275: 
        !           276:     ptctx = dp->tctxHead;
        !           277:     while (ptctx) {
        !           278:         dp->tctx = ptctx;
        !           279: 
        !           280:         GetContextForThread( dp );
        !           281: 
        !           282:         if (ptctx->pc == (DWORD)ed->ExceptionRecord.ExceptionAddress) {
        !           283:             ptctx->fFaultingContext = TRUE;
        !           284:         }
        !           285: 
        !           286:         if ((!ptctx->fFaultingContext && dp->options.fDumpAllThreads) || ptctx->fFaultingContext) {
        !           287:             wsprintf( dbuf, "%x", dp->tctx->dwThreadId );
        !           288:             lprintf( MSG_STATE_DUMP, dbuf );
        !           289:             OutputAllRegs( dp );
        !           290:             LogDisassembly( dp, &crash );
        !           291:             LogStackWalk( dp );
        !           292:             LogStackDump( dp );
        !           293:         }
        !           294: 
        !           295:         ptctx = ptctx->next;
        !           296:         if (ptctx->next == NULL) {
        !           297:             // this forces the loop to ignore the last thread
        !           298:             // we want to do this because the last thread is a
        !           299:             // remote thread created by kernel32.dll for the purpose
        !           300:             // of attaching the debugger to the faulting process
        !           301:             break;
        !           302:         }
        !           303:     }
        !           304: 
        !           305:     if (dp->options.fDumpSymbols) {
        !           306:         DumpSymbols( dp );
        !           307:     }
        !           308: 
        !           309:     ElSaveCrash( &crash, dp->options.dwMaxCrashes );
        !           310: 
        !           311:     hThread = CreateThread( NULL,
        !           312:                             16000,
        !           313:                             (LPTHREAD_START_ROUTINE)TerminationThread,
        !           314:                             dp,
        !           315:                             THREAD_SET_INFORMATION,
        !           316:                             (LPDWORD)&dwThreadId
        !           317:                           );
        !           318: 
        !           319:     WaitForSingleObject( hThread, 30000 );
        !           320: 
        !           321:     return;
        !           322: }
        !           323: 
        !           324: void
        !           325: LogStackDump( PDEBUGPACKET dp )
        !           326: {
        !           327:     DWORD   i;
        !           328:     DWORD   j;
        !           329:     BYTE    stack[1024];
        !           330: 
        !           331: 
        !           332: 
        !           333:     memset( stack, 0, sizeof(stack) );
        !           334:     if (!ReadProcessMemory( dp->hProcess,
        !           335:                             (LPVOID)dp->tctx->stack,
        !           336:                             (LPVOID)stack,
        !           337:                             sizeof(stack),
        !           338:                             (LPDWORD)&i )) {
        !           339:         return;
        !           340:     }
        !           341: 
        !           342:     lprintf( MSG_STACK_DUMP_HEADER );
        !           343: 
        !           344:     for( i = 0; i < 20; i++ ) {
        !           345:         j = i * 16;
        !           346:         lprintfs( "%08x  %02x %02x %02x %02x %02x %02x %02x %02x - %02x %02x %02x %02x %02x %02x %02x %02x  %c%c%c%c%c%c%c%c%c%c%c%c%c%c%c%c\r\n",
        !           347:                   j + dp->tctx->stack,
        !           348:                   stack[ j +  0 ],
        !           349:                   stack[ j +  1 ],
        !           350:                   stack[ j +  2 ],
        !           351:                   stack[ j +  3 ],
        !           352:                   stack[ j +  4 ],
        !           353:                   stack[ j +  5 ],
        !           354:                   stack[ j +  6 ],
        !           355:                   stack[ j +  7 ],
        !           356:                   stack[ j +  8 ],
        !           357:                   stack[ j +  9 ],
        !           358:                   stack[ j + 10 ],
        !           359:                   stack[ j + 11 ],
        !           360:                   stack[ j + 12 ],
        !           361:                   stack[ j + 13 ],
        !           362:                   stack[ j + 14 ],
        !           363:                   stack[ j + 15 ],
        !           364:                   isprint( stack[ j +  0 ]) ? stack[ j +  0 ] : '.',
        !           365:                   isprint( stack[ j +  1 ]) ? stack[ j +  1 ] : '.',
        !           366:                   isprint( stack[ j +  2 ]) ? stack[ j +  2 ] : '.',
        !           367:                   isprint( stack[ j +  3 ]) ? stack[ j +  3 ] : '.',
        !           368:                   isprint( stack[ j +  4 ]) ? stack[ j +  4 ] : '.',
        !           369:                   isprint( stack[ j +  5 ]) ? stack[ j +  5 ] : '.',
        !           370:                   isprint( stack[ j +  6 ]) ? stack[ j +  6 ] : '.',
        !           371:                   isprint( stack[ j +  7 ]) ? stack[ j +  7 ] : '.',
        !           372:                   isprint( stack[ j +  8 ]) ? stack[ j +  8 ] : '.',
        !           373:                   isprint( stack[ j +  9 ]) ? stack[ j +  9 ] : '.',
        !           374:                   isprint( stack[ j + 10 ]) ? stack[ j + 10 ] : '.',
        !           375:                   isprint( stack[ j + 11 ]) ? stack[ j + 11 ] : '.',
        !           376:                   isprint( stack[ j + 12 ]) ? stack[ j + 12 ] : '.',
        !           377:                   isprint( stack[ j + 13 ]) ? stack[ j + 13 ] : '.',
        !           378:                   isprint( stack[ j + 14 ]) ? stack[ j + 14 ] : '.',
        !           379:                   isprint( stack[ j + 15 ]) ? stack[ j + 15 ] : '.'
        !           380:                 );
        !           381:     }
        !           382: 
        !           383:     lprintfs( "\r\n" );
        !           384:     return;
        !           385: }
        !           386: 
        !           387: void
        !           388: LogStackWalk( PDEBUGPACKET dp )
        !           389: {
        !           390:     STACKWALK         stk;
        !           391:     PSYMBOL           psym;
        !           392:     DWORD             dwDisplacement = 0;
        !           393:     DWORD             frames = 0;
        !           394:     char              *szSymName;
        !           395: 
        !           396: 
        !           397:     lprintf( MSG_STACKTRACE );
        !           398: 
        !           399:     stk.frame = dp->tctx->frame;
        !           400:     stk.pc = dp->tctx->pc;
        !           401:     stk.ul = 0;
        !           402: 
        !           403:     if (!StackWalkInit(&stk, dp)) {
        !           404:         lprintf( MSG_STACKTRACE_FAIL );
        !           405:         return;
        !           406:     }
        !           407: 
        !           408:     lprintf( MSG_STACKTRACE_HEADER );
        !           409: 
        !           410:     do {
        !           411:         psym = GetSymFromAddrAllContexts( stk.pc, &dwDisplacement, dp );
        !           412:         if (psym) {
        !           413:             szSymName = UnDName( &psym->szName[1] );
        !           414:         }
        !           415:         else {
        !           416:             szSymName = "<nosymbols>";
        !           417:         }
        !           418:         lprintfs( "%08x %08x %08x %08x %08x %08x ",
        !           419:                   stk.pc,
        !           420:                   stk.frame,
        !           421:                   stk.params[0],
        !           422:                   stk.params[1],
        !           423:                   stk.params[2],
        !           424:                   stk.params[3]
        !           425:                 );
        !           426: 
        !           427:         lprintfs( "%s\r\n", szSymName );
        !           428:     } while (StackWalkNext(&stk, dp) && frames++ < 100);
        !           429: 
        !           430:     lprintfs( "\r\n" );
        !           431: 
        !           432:     return;
        !           433: }
        !           434: 
        !           435: void
        !           436: LogDisassembly( PDEBUGPACKET dp, PCRASHES pCrash )
        !           437: {
        !           438:     PSYMBOL           psym;
        !           439:     DWORD             dwFuncAddr;
        !           440:     DWORD             dwFuncSize;
        !           441:     DWORD             dwDisplacement = 0;
        !           442:     char              *szSymName;
        !           443:     DWORD             offset;
        !           444:     int               i;
        !           445:     int               j;
        !           446:     char              dbuf[1024];
        !           447:     BOOL              fFaultingInst;
        !           448:     int               dwStartDis;
        !           449:     int               dwEndDis;
        !           450: 
        !           451: 
        !           452:     psym = GetSymFromAddr( dp->tctx->pc, &dwDisplacement, dp->tctx->mi );
        !           453: 
        !           454:     if (psym) {
        !           455:         dwFuncAddr = psym->addr;
        !           456:         dwFuncSize = psym->size;
        !           457:         szSymName = UnDName( &psym->szName[1] );
        !           458:     }
        !           459:     else {
        !           460:         dwFuncAddr = dp->tctx->pc - 50;
        !           461:         dwFuncSize = 100;
        !           462:         szSymName = "<nosymbols>";
        !           463:     }
        !           464: 
        !           465:     if (dp->tctx->fFaultingContext) {
        !           466:         strcpy( pCrash->szFunction, szSymName );
        !           467:     }
        !           468: 
        !           469:     lprintf( MSG_FUNCTION, szSymName );
        !           470: 
        !           471: tryagain:
        !           472:     //
        !           473:     // count the number of instructions in the function
        !           474:     // also, save the instruction number of context's pc
        !           475:     //
        !           476:     for (i=0,offset=dwFuncAddr,j=-1; offset<dwFuncAddr+dwFuncSize; i++) {
        !           477:         if (offset == dp->tctx->pc) {
        !           478:             j = i;
        !           479:         }
        !           480:         if (!disasm( dp, &offset, dbuf, TRUE )) {
        !           481:             break;
        !           482:         }
        !           483:     }
        !           484: 
        !           485:     if (j == -1) {
        !           486:         //
        !           487:         // we didn't find a match for the current pc
        !           488:         // this because we don't have symbols for the current pc and
        !           489:         // therefore had to just backup and start disassembling.  we try
        !           490:         // to recover by adding 1 to the func addr and do it again.
        !           491:         // eventually we will hit the pc and we will be a-ok.
        !           492:         //
        !           493:         dwFuncAddr++;
        !           494:         goto tryagain;
        !           495:     }
        !           496: 
        !           497:     //
        !           498:     // print the disassemled instructions.  only print the number
        !           499:     // of instructions before and after the current pc that the
        !           500:     // user specified in the registry options.
        !           501:     //
        !           502:     dwStartDis = max(0,j - (int)dp->options.dwInstructions);
        !           503:     dwEndDis = j+(int)dp->options.dwInstructions;
        !           504:     fFaultingInst = FALSE;
        !           505:     for (i=0,offset=dwFuncAddr; offset<dwFuncAddr+dwFuncSize; i++) {
        !           506:         if (offset == dp->tctx->pc) {
        !           507:             fFaultingInst = TRUE;
        !           508:         }
        !           509:         if (!disasm( dp, &offset, dbuf, TRUE )) {
        !           510:             break;
        !           511:         }
        !           512:         if (i >= dwStartDis) {
        !           513:             if (fFaultingInst && dp->tctx->fFaultingContext) {
        !           514:                 fFaultingInst = FALSE;
        !           515:                 lprintf( MSG_FAULT );
        !           516:             }
        !           517:             else {
        !           518:                 lprintfs( "        " );
        !           519:             }
        !           520:             lprintfs( "%s\r\n", dbuf );
        !           521:         }
        !           522:         if (i > dwEndDis) {
        !           523:             break;
        !           524:         }
        !           525:     }
        !           526: 
        !           527:     lprintfs( "\r\n" );
        !           528:     return;
        !           529: }
        !           530: 
        !           531: void
        !           532: AttachToActiveProcess ( PDEBUGPACKET dp )
        !           533: {
        !           534:     HANDLE              Token;
        !           535:     PTOKEN_PRIVILEGES   NewPrivileges;
        !           536:     BYTE                OldPriv[1024];
        !           537:     PBYTE               pbOldPriv;
        !           538:     ULONG               cbNeeded;
        !           539:     BOOLEAN             fRc;
        !           540:     LUID                LuidPrivilege;
        !           541: 
        !           542:     //
        !           543:     // Make sure we have access to adjust and to get the old token privileges
        !           544:     //
        !           545:     if (!OpenProcessToken( GetCurrentProcess(),
        !           546:                            TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY,
        !           547:                            &Token)) {
        !           548:         if (dp->options.fVisual) {
        !           549:             FatalError( LoadRcString(IDS_DEBUGPRIV) );
        !           550:         }
        !           551:         else {
        !           552:             ExitProcess( 1 );
        !           553:         }
        !           554:     }
        !           555: 
        !           556:     cbNeeded = 0;
        !           557: 
        !           558:     //
        !           559:     // Initialize the privilege adjustment structure
        !           560:     //
        !           561: 
        !           562:     LookupPrivilegeValue( NULL, SE_DEBUG_NAME, &LuidPrivilege );
        !           563: 
        !           564:     NewPrivileges =
        !           565:         (PTOKEN_PRIVILEGES)LocalAlloc(LMEM_ZEROINIT,
        !           566:                                       sizeof(TOKEN_PRIVILEGES) +
        !           567:                                           (1 - ANYSIZE_ARRAY) *
        !           568:                                           sizeof(LUID_AND_ATTRIBUTES));
        !           569:     if (NewPrivileges == NULL) {
        !           570:         if (dp->options.fVisual) {
        !           571:             FatalError( LoadRcString(IDS_DEBUGPRIV) );
        !           572:         }
        !           573:         else {
        !           574:             ExitProcess( 1 );
        !           575:         }
        !           576:     }
        !           577: 
        !           578:     NewPrivileges->PrivilegeCount = 1;
        !           579:     NewPrivileges->Privileges[0].Luid = LuidPrivilege;
        !           580:     NewPrivileges->Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
        !           581: 
        !           582:     //
        !           583:     // Enable the privilege
        !           584:     //
        !           585: 
        !           586:     pbOldPriv = OldPriv;
        !           587:     fRc = AdjustTokenPrivileges( Token,
        !           588:                                  FALSE,
        !           589:                                  NewPrivileges,
        !           590:                                  1024,
        !           591:                                  (PTOKEN_PRIVILEGES)pbOldPriv,
        !           592:                                  &cbNeeded );
        !           593: 
        !           594:     if (!fRc) {
        !           595: 
        !           596:         //
        !           597:         // If the stack was too small to hold the privileges
        !           598:         // then allocate off the heap
        !           599:         //
        !           600:         if (GetLastError() == ERROR_INSUFFICIENT_BUFFER) {
        !           601: 
        !           602:             pbOldPriv = LocalAlloc(LMEM_FIXED, cbNeeded);
        !           603:             if (pbOldPriv == NULL) {
        !           604:                 if (dp->options.fVisual) {
        !           605:                     FatalError( LoadRcString(IDS_DEBUGPRIV) );
        !           606:                 }
        !           607:                 else {
        !           608:                     ExitProcess( 1 );
        !           609:                 }
        !           610:             }
        !           611: 
        !           612:             fRc = AdjustTokenPrivileges( Token,
        !           613:                                          FALSE,
        !           614:                                          NewPrivileges,
        !           615:                                          cbNeeded,
        !           616:                                          (PTOKEN_PRIVILEGES)pbOldPriv,
        !           617:                                          &cbNeeded );
        !           618:         }
        !           619:     }
        !           620: 
        !           621: 
        !           622:     if (!DebugActiveProcess( dp->dwPidToDebug )) {
        !           623:         FatalError( LoadRcString(IDS_ATTACHFAIL) );
        !           624:         if (dp->options.fVisual) {
        !           625:             FatalError( LoadRcString(IDS_ATTACHFAIL) );
        !           626:         }
        !           627:         else {
        !           628:             ExitProcess( 1 );
        !           629:         }
        !           630:     }
        !           631: 
        !           632:     return;
        !           633: }
        !           634: 
        !           635: void
        !           636: LogSystemInformation( PDEBUGPACKET dp )
        !           637: {
        !           638:     char          buf[1024];
        !           639:     SYSTEM_INFO   si;
        !           640:     DWORD         ver;
        !           641:     SYSINFO       mySi;
        !           642:     DWORD         dwThreadId;
        !           643:     HANDLE        hThread;
        !           644: 
        !           645:     lprintf( MSG_SYSINFO_HEADER );
        !           646:     hThread = CreateThread( NULL,
        !           647:                             16000,
        !           648:                             (LPTHREAD_START_ROUTINE)SysInfoThread,
        !           649:                             &mySi,
        !           650:                             THREAD_SET_INFORMATION,
        !           651:                             (LPDWORD)&dwThreadId
        !           652:                           );
        !           653:     Sleep( 0 );
        !           654:     if (WaitForSingleObject( hThread, 30000 ) == WAIT_TIMEOUT) {
        !           655:         Assert(TerminateThread( hThread, 0 ) == TRUE);
        !           656:     }
        !           657:     lprintf( MSG_SYSINFO_COMPUTER, mySi.szMachineName );
        !           658:     lprintf( MSG_SYSINFO_USER, mySi.szUserName );
        !           659:     GetSystemInfo( &si );
        !           660:     wsprintf( buf, "%d", si.dwNumberOfProcessors );
        !           661:     lprintf( MSG_SYSINFO_NUM_PROC, buf );
        !           662:     lprintf( MSG_SYSINFO_PROC_TYPE );
        !           663:     switch(si.dwProcessorType) {
        !           664:         case PROCESSOR_INTEL_386:
        !           665:             lprintf( MSG_SYSINFO_I386 );
        !           666:             break;
        !           667: 
        !           668:         case PROCESSOR_INTEL_486:
        !           669:             lprintf( MSG_SYSINFO_I486 );
        !           670:             break;
        !           671: 
        !           672:         case PROCESSOR_INTEL_860:
        !           673:             lprintf( MSG_SYSINFO_I860 );
        !           674:             break;
        !           675: 
        !           676:         case PROCESSOR_MIPS_R2000:
        !           677:             lprintf( MSG_SYSINFO_R2000 );
        !           678:             break;
        !           679: 
        !           680:         case PROCESSOR_MIPS_R3000:
        !           681:             lprintf( MSG_SYSINFO_R3000 );
        !           682:             break;
        !           683: 
        !           684:         case PROCESSOR_MIPS_R4000:
        !           685:             lprintf( MSG_SYSINFO_R4000 );
        !           686:             break;
        !           687: 
        !           688:         case PROCESSOR_ALPHA_21064:
        !           689:             lprintf( MSG_SYSINFO_A21064 );
        !           690:             break;
        !           691: 
        !           692:         default:
        !           693:             lprintf( MSG_SYSINFO_UNKNOWN );
        !           694:             break;
        !           695:     }
        !           696:     ver = GetVersion();
        !           697:     wsprintf( buf, "%d.%d", LOBYTE(LOWORD(ver)), HIBYTE(LOWORD(ver)) );
        !           698:     lprintf( MSG_SYSINFO_WINVER, buf );
        !           699:     RegLogCurrentVersion();
        !           700:     lprintfs( "\r\n" );
        !           701: }
        !           702: 
        !           703: DWORD
        !           704: SysInfoThread( PSYSINFO si )
        !           705: {
        !           706:     DWORD len;
        !           707: 
        !           708:     strcpy( si->szMachineName, "<unknown machine name>" );
        !           709:     strcpy( si->szUserName,    "<unknown user name>" );
        !           710:     len = sizeof(si->szMachineName);
        !           711:     GetComputerName( si->szMachineName, &len );
        !           712:     len = sizeof(si->szUserName);
        !           713:     GetUserName( si->szUserName, &len );
        !           714: 
        !           715:     return 0;
        !           716: }
        !           717: 
        !           718: DWORD
        !           719: TerminationThread( PDEBUGPACKET dp )
        !           720: {
        !           721:     HANDLE hProcess;
        !           722: 
        !           723:     hProcess = OpenProcess( PROCESS_TERMINATE, FALSE, dp->dwPidToDebug );
        !           724:     if (hProcess != NULL) {
        !           725:         TerminateProcess( hProcess, 0 );
        !           726:         CloseHandle( hProcess );
        !           727:     }
        !           728: 
        !           729:     return 0;
        !           730: }
        !           731: 
        !           732: char *
        !           733: GetExceptionText( DWORD dwExceptionCode )
        !           734: {
        !           735:     static char buf[80];
        !           736:     DWORD dwFormatId = 0;
        !           737: 
        !           738:     memset( buf, 0, sizeof(buf) );
        !           739: 
        !           740:     switch (dwExceptionCode) {
        !           741:         case STATUS_SINGLE_STEP:
        !           742:             dwFormatId = MSG_SINGLE_STEP_EXCEPTION;
        !           743:             break;
        !           744: 
        !           745:         case DBG_CONTROL_C:
        !           746:             dwFormatId = MSG_CONTROLC_EXCEPTION;
        !           747:             break;
        !           748: 
        !           749:         case DBG_CONTROL_BREAK:
        !           750:             dwFormatId = MSG_CONTROL_BRK_EXCEPTION;
        !           751:             break;
        !           752: 
        !           753:         case STATUS_ACCESS_VIOLATION:
        !           754:             dwFormatId = MSG_ACCESS_VIOLATION_EXCEPTION;
        !           755:             break;
        !           756: 
        !           757:         case STATUS_STACK_OVERFLOW:
        !           758:             dwFormatId = MSG_STACK_OVERFLOW_EXCEPTION;
        !           759:             break;
        !           760: 
        !           761:         case STATUS_INTEGER_DIVIDE_BY_ZERO:
        !           762:             dwFormatId = MSG_INTEGER_DIVIDE_BY_ZERO_EXCEPTION;
        !           763:             break;
        !           764: 
        !           765:         case STATUS_PRIVILEGED_INSTRUCTION:
        !           766:             dwFormatId = MSG_PRIVILEGED_INSTRUCTION_EXCEPTION;
        !           767:             break;
        !           768: 
        !           769:         case STATUS_ILLEGAL_INSTRUCTION:
        !           770:             dwFormatId = MSG_ILLEGAL_INSTRUCTION_EXCEPTION;
        !           771:             break;
        !           772: 
        !           773:         case STATUS_IN_PAGE_ERROR:
        !           774:             dwFormatId = MSG_IN_PAGE_IO_EXCEPTION;
        !           775:             break;
        !           776: 
        !           777:         case STATUS_DATATYPE_MISALIGNMENT:
        !           778:             dwFormatId = MSG_DATATYPE_EXCEPTION;
        !           779:             break;
        !           780: 
        !           781:         case STATUS_POSSIBLE_DEADLOCK:
        !           782:             dwFormatId = MSG_DEADLOCK_EXCEPTION;
        !           783:             break;
        !           784: 
        !           785:         case STATUS_VDM_EVENT:
        !           786:             dwFormatId = MSG_VDM_EXCEPTION;
        !           787:             break;
        !           788: 
        !           789:         case STATUS_BREAKPOINT:
        !           790:             dwFormatId = MSG_BREAKPOINT_EXCEPTION;
        !           791:             break;
        !           792: 
        !           793:         default:
        !           794:             lprintfs( "\r\n" );
        !           795:             break;
        !           796:     }
        !           797: 
        !           798:     FormatMessage( FORMAT_MESSAGE_FROM_HMODULE | FORMAT_MESSAGE_ARGUMENT_ARRAY,
        !           799:                    NULL,
        !           800:                    dwFormatId,
        !           801:                    0, // GetUserDefaultLangID(),
        !           802:                    buf,
        !           803:                    sizeof(buf),
        !           804:                    NULL
        !           805:                  );
        !           806: 
        !           807:     return buf;
        !           808: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.