Hey i have a very time consuming problem, and i thought i might find someone here with better experience than mine that could help me out.
I am reverse-engineering an application which at some point uses the NdrClientCall2 api to use a remote procedure of some other service (which i dont know which one that is)
Now before i hear comments about not trying anything my self There are some really good applications to accomplish what i want like NtTrace, Strace and roughly oSpy can achieve the same result aswell eventually. But my application has some really hard anti-debugging techniques which force me to do everything manually.
What eventually i want to achieve is know what procedure is being called and on what service \ process.
Here is the NdrClientCall2 Decleration by MSDN
CLIENT_CALL_RETURN RPC_VAR_ENTRY NdrClientCall2(
__in PMIDL_STUB_DESC pStubDescriptor,
__in PFORMAT_STRING pFormat,
__in_out ...
);
so it uses the PMIDL_STUB_DESC struct which its definition is as the following:
typedef struct _MIDL_STUB_DESC {
void *RpcInterfaceInformation;
void* (__RPC_API *pfnAllocate)(size_t);
void (__RPC_API *pfnFree)(void*);
union {
handle_t *pAutoHandle;
handle_t *pPrimitiveHandle;
PGENERIC_BINDING_INFO pGenericBindingInfo;
} IMPLICIT_HANDLE_INFO;
const NDR_RUNDOWN *apfnNdrRundownRoutines;
const GENERIC_BINDING_ROUTINE_PAIR *aGenericBindingRoutinePairs;
const EXPR_EVAL *apfnExprEval;
const XMIT_ROUTINE_QUINTUPLE *aXmitQuintuple;
const unsigned char *pFormatTypes;
int fCheckBounds;
unsigned long Version;
MALLOC_FREE_STRUCT *pMallocFreeStruct;
long MIDLVersion;
const COMM_FAULT_OFFSETS *CommFaultOffsets;
const USER_MARSHAL_ROUTINE_QUADRUPLE *aUserMarshalQuadruple;
const NDR_NOTIFY_ROUTINE *NotifyRoutineTable;
ULONG_PTR mFlags;
const NDR_CS_ROUTINES *CsRoutineTables;
void *Reserved4;
ULONG_PTR Reserved5;
} MIDL_STUB_DESC, *PMIDL_STUB_DESC;
And here is how it looks like in windbg, when i put a breakpoint in the NdrClientCall2 function
0:006> .echo "Arguments:"; dds esp+4 L5
Arguments:
06d9ece4 74cc2158 SspiCli!sspirpc_StubDesc
06d9ece8 74cc2322 SspiCli!sspirpc__MIDL_ProcFormatString+0x17a
06d9ecec 06d9ed00
06d9ecf0 91640000
06d9ecf4 91640000
0:006> .echo "PMIDL_STUB_DESC:"; dds poi(esp+4) L20
PMIDL_STUB_DESC:
74cc2158 74cc2690 SspiCli!sspirpc_ServerInfo+0x24
74cc215c 74cca1cd SspiCli!MIDL_user_allocate
74cc2160 74cca1e6 SspiCli!MIDL_user_free
74cc2164 74ce0590 SspiCli!SecpCheckSignatureRoutineRefCount+0x4
74cc2168 00000000
74cc216c 00000000
74cc2170 00000000
74cc2174 00000000
74cc2178 74cc1c52 SspiCli!sspirpc__MIDL_TypeFormatString+0x2
74cc217c 00000001
74cc2180 00060001
74cc2184 00000000
74cc2188 0700022b
74cc218c 00000000
74cc2190 00000000
74cc2194 00000000
74cc2198 00000001
74cc219c 00000000
74cc21a0 00000000
74cc21a4 00000000
74cc21a8 48000000
74cc21ac 00000000
74cc21b0 001c0000
74cc21b4 00000032
74cc21b8 00780008
74cc21bc 41080646
74cc21c0 00000000
74cc21c4 000b0000
74cc21c8 00020004
74cc21cc 00080048
74cc21d0 21500008
74cc21d4 0008000c
0:006> .echo "PFORMAT_STRING:"; db poi(esp+8)
PFORMAT_STRING:
74cc2322 00 48 00 00 00 00 06 00-4c 00 30 40 00 00 00 00 .H......L.0@....
74cc2332 ec 00 bc 00 47 13 08 47-01 00 01 00 00 00 08 00 ....G..G........
74cc2342 00 00 14 01 0a 01 04 00-6e 00 58 01 08 00 08 00 ........n.X.....
74cc2352 0b 00 0c 00 20 01 0a 01-10 00 f6 00 0a 01 14 00 .... ...........
74cc2362 f6 00 48 00 18 00 08 00-48 00 1c 00 08 00 0b 00 ..H.....H.......
74cc2372 20 00 2c 01 0b 01 24 00-a2 01 0b 00 28 00 b8 01 .,...$.....(...
74cc2382 13 41 2c 00 a2 01 13 20-30 00 f8 01 13 41 34 00 .A,.... 0....A4.
74cc2392 60 01 12 41 38 00 f6 00-50 21 3c 00 08 00 12 21 `..A8...P!<....!
So how exactly do i figure out what is the remote process it is going to communicate with, or what pipe it is using to communicate?
As far as i understand from the MSDN, it is supposed to call a remote procedure. if i understand that right, it means it should call a remote function as if its an exported dll function. How can i set a breakpoint there?
P.S:
The main reason im posing this function is because the NdrClientCall2 seems to be pretty huge.