hello}
im trying to get the addresses of the opengl driver, either nvidia or ati, or other.... i tried a method called tib hooking or whatever, it seems it uses some member in the TEB structure of a determined thread in a process, so you have to be in the thread context.  im not sure anyways but it is not working for me at the moment. i looked in a debugger to see how it gets to the driver address of glbegin for example

from opengl32.dll -->
5F1228F0 >  64:A1 18000000  MOV EAX,DWORD PTR FS:[18] //EAX=0x7FFDE000
5F1228F6  - FFA0 CC070000   JMP DWORD PTR DS: ; nvoglnt.6981C250 // EDX=69E00002 nvoglnt.69E00002

--> to stack
6981C250    64:A1 880E0000  MOV EAX,DWORD PTR FS:
6981C256    FF20            JMP DWORD PTR DS: //EAX=013800BC

--> to nvoglnt.dll
6962D940    ---> glbegin's driver address


well but at the moment i couldnt get them by a coding method so i am just hardcoding them. but well i want to get them automatically, i appreciate your help  :D



typedef struct _TEB
{
   NT_TIB                  Tib;
   PVOID                   EnvironmentPointer;
   CLIENT_ID               Cid;
   PVOID                   ActiveRpcInfo;
   PVOID                   ThreadLocalStoragePointer;
   PPEB                    Peb;
   ULONG                   LastErrorValue;
   ULONG                   CountOfOwnedCriticalSections;
   PVOID                   CsrClientThread;
   PVOID                   Win32ThreadInfo;
   ULONG                   Win32ClientInfo[0x1F];
   PVOID                   WOW32Reserved;
   ULONG                   CurrentLocale;
   ULONG                   FpSoftwareStatusRegister;
   PVOID                   SystemReserved1[0x36];
   PVOID                   Spare1;
   ULONG                   ExceptionCode;
   ULONG                   SpareBytes1[0x28];
   PVOID                   SystemReserved2[0xA];
   ULONG                   GdiRgn;
   ULONG                   GdiPen;
   ULONG                   GdiBrush;
   CLIENT_ID               RealClientId;
   PVOID                   GdiCachedProcessHandle;
   ULONG                   GdiClientPID;
   ULONG                   GdiClientTID;
   PVOID                   GdiThreadLocaleInfo;
   PVOID                   UserReserved[5];
   PVOID                   GlDispatchTable[0x118];
   ULONG                   GlReserved1[0x1A];
   PVOID                   GlReserved2;
   PVOID                   GlSectionInfo;
   PVOID                   GlSection;
   PVOID                   GlTable;
   PVOID                   GlCurrentRC;
   PVOID                   GlContext;
   NTSTATUS               LastStatusValue;
   UNICODE_STRING          StaticUnicodeString;
   WCHAR                   StaticUnicodeBuffer[0x105];
   PVOID                   DeallocationStack;
   PVOID                   TlsSlots[0x40];
   LIST_ENTRY              TlsLinks;
   PVOID                   Vdm;
   PVOID                   ReservedForNtRpc;
   PVOID                   DbgSsReserved[0x2];
   ULONG                   HardErrorDisabled;
   PVOID                   Instrumentation[0x10];
   PVOID                   WinSockData;
   ULONG                   GdiBatchCount;
   ULONG                   Spare2;
   ULONG                   Spare3;
   ULONG                   Spare4;
   PVOID                   ReservedForOle;
   ULONG                   WaitingOnLoaderLock;
   PVOID                   StackCommit;
   PVOID                   StackCommitMax;
   PVOID                   StackReserved;
} TEB, *PTEB;

PTEB myTEB;
__asm
{
         push eax
         mov eax, fs:[0x18]
         mov myTEB, eax
         pop eax
}


thank you !! :-D



Posted on 2010-07-06 14:02:06 by corso
What's your reason for trying to do it this way, which will crash and burn eventually, instead of linking to an import library?
Posted on 2010-07-06 15:41:49 by f0dder
well, in first place i didnt know a way to do this. i was just grabbing the addresses from the debugger.
but now i want to make this automatically, what is the simpler way to make this?
or explain that of the linking to an import library... i didnt get the idea
Posted on 2010-07-06 16:32:12 by corso
Seems like you don't understand the concept of import binding, in which case I'd like to inform you that you are attempting to perform a somewhat advanced technique. I strongly suggest that you start with the basics first. In its current state, even if you manage to make these hard-coded addresses work on windows XP, ASLR will make sure it won't work on Visa/7.

And what is the ultimate goal of all this? What are you trying to accomplish? To me, it looks like it's going to be either malicious or educational. If it's educational, you really need to learn the basics first.

...Or maybe I completely misunderstand what you are trying to do? ^^' Please explain.
Posted on 2010-07-06 17:49:11 by ti_mo_n
hi this is the code for my logger, I need to get opengl addresses from driver, such as glbegin, glenable, etc
I am not getting them as is visible in the code. I was told to use this method of the tib hooking that is supposed to work,
so the question is how to get the addresses using tib, do you know or you DO NOT know how to make it?
but probably i could get help with my code below, what is missing, etc .. since i didnt work with this structure (tib)
if you know another method, simpler perhaps, I am expectant. but I will have still the doubt on this one..  :sad:
(not that of the hardcoding the addresses  :D)


DWORD thread_OGL(LPVOID parms)
{
  _CONTEXT Cxt;
  Cxt.ContextFlags=CONTEXT_FULL|CONTEXT_DEBUG_REGISTERS;

  LDT_ENTRY SelEntry;

  HWND hApp; //use findwindow
  DWORD ProcId;
  DWORD ThId=GetWindowThreadProcessId(hApp,&ProcId);

  HANDLE hProc=OpenProcess(PROCESS_ALL_ACCESS,FALSE,ProcId);
 
  HANDLE hTh=OpenThread(THREAD_ALL_ACCESS,FALSE,ThId);

  SuspendThread(hTh);
 
  GetThreadContext(hTh, &Cxt);
  GetThreadSelectorEntry(hTh, Cxt.SegFs, &SelEntry);

  ResumeThread(hTh);

  DWORD* dwFSBase = (DWORD*)((SelEntry.HighWord.Bits.BaseHi<<24)|(SelEntry.HighWord.Bits.BaseMid<<16)|SelEntry.BaseLow);
  DPrint("dwFSBase 0x%X",dwFSBase);

  //mov eax, fs:[18h] ; // *TIB
  //mov eax, ; // CurrentThreadId
  PTEB myTEB;

  __asm{
         mov eax, dwFSBase
         //mov eax, fs:[18h]
 mov myTEB, eax
  }

  DWORD addr1 = (DWORD)myTEB->GlDispatchTable[0x01];
  DPrint("addr1 0x%X",addr1);

  CloseHandle(hTh);
  CloseHandle(hProc);
  return 0;
}



Posted on 2010-07-06 20:08:13 by corso
As the others I'd also like to know the ultimate goal so we can know if this forced methodology of using the undocumented TIB fields is really needed. In your code it seems you are getting the dispatch table of a thread from a foreign process, and because of that you of course CANNOT read it straight as you're doing. To read the TIB you should follow the remarks section of GetThreadSelectorEntry documentation:
Remarks

GetThreadSelectorEntry is only functional on x86-based systems. For systems that are not x86-based, the function returns FALSE.

Debuggers use this function to convert segment-relative addresses to linear virtual addresses. The ReadProcessMemory and WriteProcessMemory functions use linear virtual addresses.
http://msdn.microsoft.com/en-us/library/ms679363%28VS.85%29.aspx
Posted on 2010-07-06 20:20:17 by LocoDelAssembly
 I didnt consider necessary to mention that this code is to start a thread in some process. it belongs to a dll project so, the way
this logger works is like loading the logger.dll using some loader/injector, into the application you want and then you can get the addresses
from your opengl driver (nvidia, ati, etc). that's why I need to enter in the context of the process, so then i can read the thread's tib, it is ok?

that gldispatchtable I dont even know what it is, since it is undocumented as you say, or at least I didnt find information..

when I log the TIB's address for that thread it is non-static value, something like 0x7fffe000 but can change.. I need to know how to get
to the opengl functions, I know I can access them from tib,,,I supposed that GLdispatchtable was to access them. how can I access them so  :D ?




Posted on 2010-07-06 22:04:44 by corso
If you can inject the DLL then use LoadLibrary("Opengl32.dll") (call once) + GetProcAddress (call many) to get pointers to them. These will be pointers to Opengl32.dll though, not the video card-specific DLL (but note that it is very unlikely that an application skips Opengl32.dll to call, say, glBegin).

If you still want the TIB way, once your DLL is running inside the target process you can read just in the same way you saw in Opengl32.dll assembly listing (or getting a pointer to the FS selector of the thread that created the window first and then do the part in case that using your injected thread's TIB doesn't produce expected results). Then you would use some inter process communication method to pass the pointers to your logger* (but remember that those addresses are invalid in the memory space of the logger process, any access through them should be with Read/WriteProcessMemory). Note that the DLL is not really necessary for this, your code seems to be OK except for the part where the TIB is read, as you should use ReadProcessMemory for that instead.

*I've assumed you want the logging to be made outside the target application process, if you can actually make everything from your injected DLL and thread then forget about inter process communication and Read/WriteProcessMemory, you're already in the context of the target process.
Posted on 2010-07-06 22:50:16 by LocoDelAssembly
well i tried to do the same as in opengl32, that is it:

5F1228F0 >  64:A1 18000000  MOV EAX,DWORD PTR FS:[18] //EAX=0x7FFDE000
5F1228F6  - FFA0 CC070000   JMP DWORD PTR DS: ; nvoglnt.6981C250 // EDX=69E00002 nvoglnt.69E00002

then jumps to here
6981C250    64:A1 880E0000  MOV EAX,DWORD PTR FS:
6981C256    FF20            JMP DWORD PTR DS: //EAX=013800BC

and then jumps to here
6962D940    53              PUSH EBX

that 0x7cc is the index for glbegin, but as you see in the dump, it loads an address from other index after.
if I log the first one it is null result
the correct TIB I get it using the fs selector for the thread.. I checked the addresss in debugger and in my log and it is the same
address, so I assume that is not the problem
till now i couldn't log at least one function   :sad:


DWORD thread_OGL(LPVOID parms)
{
  _CONTEXT Cxt;
  Cxt.ContextFlags=CONTEXT_FULL|CONTEXT_DEBUG_REGISTERS;

  LDT_ENTRY SelEntry;

  HWND hApp; // USE FINDWINDOW
  DWORD ProcId;
  DWORD ThId=GetWindowThreadProcessId(hApp,&ProcId);

  HANDLE hProc=OpenProcess(PROCESS_ALL_ACCESS,FALSE,ProcId);
 
  HANDLE hTh=OpenThread(THREAD_ALL_ACCESS,FALSE,ThId);

  SuspendThread(hTh);
 
  GetThreadContext(hTh, &Cxt);
  GetThreadSelectorEntry(hTh, Cxt.SegFs, &SelEntry);

  ResumeThread(hTh);

  DWORD* dwFSBase = (DWORD*)((SelEntry.HighWord.Bits.BaseHi<<24)|(SelEntry.HighWord.Bits.BaseMid<<16)|SelEntry.BaseLow);
  DPrint("dwFSBase 0x%X",dwFSBase);

  DWORD dwglBegin;
  PTEB myTEB;
  WORD fsSel;

  __asm{
         mov eax, dwFSBase
          mov , eax
          mov , fs

         mov ebx,
          mov dwglBegin, ebx
  }

  DPrint("dwglBegin 0x%X",dwglBegin);

  CloseHandle(hTh);
  CloseHandle(hProc);
  return 0;
}
Posted on 2010-07-07 09:54:18 by corso
I didnt try in a pc with another card than nvidiaS, for that, I think the second jump happens only with nvidia drivers, im not sure
no ideas? I will ask in other forums.

Posted on 2010-07-09 17:47:52 by corso