I am trying to do some COM/OLE, here is my code :
static struct IUnknown* punk = NULL;
static IDispatch* UIRManager = NULL;
void DispatcherStart(){
CoInitialize(NULL);
HRESULT retour = GetActiveObject(&CLSID_OASIQ_,NULL,&punk);
if(retour != S_OK){
return;
}
HRESULT hr = IUnknown_QueryInterface_Proxy(punk,&IID_UIRManager_,(void**) &UIRManager); // General protection fault
...
For some reason, IUnknown_QueryInterface_Proxy cause a General protection fault. I dont see what I'm doing wrong ?
This function is called from a different thread than the main thread but since I call CoInitialize it's not the cause of error. I'm on C99 compiling a 32bit executable on W10
The C implementation of IUnknow is different than C++.
The comon way to call QueryInterface is not by using IUnknown_QueryInterface_Proxy (from RpcRT4.lib) but to do this :
HRESULT hr = (punk)->lpVtbl -> QueryInterface(punk,&IID_UIRManager_,(void**) &UIRManager);
Related
I am reading through the relevant Microsoft docs and found this example of how to create IDGI data struct then use it to read memory size but I get Segmentation fault
#include <iostream>
#include <d3d9.h>
#include <D3D9Types.h>
LPDIRECT3D9 g_pDirect3D = NULL;
LPDIRECT3DDEVICE9 g_pDirect3D_Device = NULL;
int main(void)
{
UINT x = 0; // Ordinal number that denotes the display adapter.
DWORD xWord = 0 ;
D3DADAPTER_IDENTIFIER9 pIdentifier ;
g_pDirect3D = Direct3DCreate9(D3D_SDK_VERSION);
HRESULT hResult = g_pDirect3D->GetAdapterIdentifier(x, xWord, &pIdentifier);
IDXGIDevice * pDXGIDevice;
HRESULT hr = g_pDirect3D->QueryInterface(__uuidof(IDXGIDevice), (void **)&pDXGIDevice);
IDXGIAdapter * pDXGIAdapter;
pDXGIDevice->GetAdapter(&pDXGIAdapter); // segfault at this line
return 0;
}
every thing works perfectly but when I uncomment the line before return 0; I get the error
Microsoft Basic Render Driver
Segmentation fault
why do I get that error
You can't get a IDXGIDevice reference from a IDirect3D9 reference using QueryInterface.
The return HRESULT from the QueryInterface call is probably 0x80004002 (E_NOINTERFACE), so pDXGIDevice is null and the following calls cause a crash. You should always check HRESULT values.
Otherwise, for new developments, you should forget about DirectX9 and use DirectX11 or DirectX12 (and this will enable DXGI).
I'm having issues using COM from a C program, when I call functions on an object I get
Run-Time Check Failure #0 - The value of ESP was not properly saved across a function call. This is usually a result of calling a function declared with one calling convention with a function pointer declared with a different calling convention.
Which suggests somehow I'm using the wrong calling convention, but not sure how I diagnose or fix this issue.
Here's the code I wrote to test this:
#include <shlobj.h>
int main()
{
IProgressDialog* dialog = NULL;
HRESULT hr = 0;
hr = CoInitialize(NULL);
hr = CoCreateInstance(&CLSID_ProgressDialog, NULL, CLSCTX_INPROC_SERVER, &IID_IProgressDialog, &dialog);
hr = dialog->lpVtbl->SetTitle(dialog, L"Progress"); // this line causes the run time check failure
I'm using VS2019 for this, if that matters.
Any ideas much appreciated!
HI!
I bet more than a week and I can not form a complete picture of how you can get a list of kernel objects .My algorithm is as follows :
1) Connecting NTDLL.dll (LoadLibrary)
2) GetProcAddress (variable_Library_name, "NtQueryDirectoryObject")
and the pre-announcement structures : _OBJDIR_INFORMATION,
_OBJECT_ATTRIBUTES
3) Trying to apply a function NtOpenDirectoryObject for a list of
objects
Here is a piece of code that is responsible for the use of the function NtOpenDirectoryObject:
OBJDIR_INFORMATION *ssinfo =(OBJDIR_INFORMATION* ) HeapAlloc(GetProcessHeap(), 0, 0x800);
///////////////////////
HANDLE hFile,hThread,hMapFile;
HMODULE hNtdll ,hKernel;
DWORD dwThreadId;
OBJECT_ATTRIBUTES obj;
WCHAR * uString=L"\\BaseNamedObjects";
UNICODE_STRING str;
DWORD i,a,iStrLen,b=0;
char sObjName[30],sTmp[50];
LPVOID lpMapAddress;
FARPROC pWinExec,pExitThread;
bool bFound;
char* sCommand;
/////////////////////////////////////////////////////////////////
NtQueryDirectoryObject = (NTQUERYDIRECTORYOBJECT )GetProcAddress(hinstLib,"NtQueryDirectoryObject");
InitializeObjectAttributes (&obj, &str, 0, 0, 00);
NtOpenDirectoryObject(&hFile,0x20001,&obj);
The full code (including struct definitions) is at: http://pastebin.com/pDNb3GTn
When calling a function with parameters NtOpenDirectoryObject get an exception c0000005, which means that access is blocked .
tell me please, am I doing smth wrong, and where is my mistake. Is it possible to not to use the native api? Thank you for your help
Exception c0000005 is an Access Violation. That does not mean that access was blocked. It means invalid memory was accessed, such as if a NULL/uninitialized pointer were accessed, or if you are not aligning data correctly and accessing something out of bounds of what you have allocated.
As Andrew mentioned, you are not initializing the UNICODE_STRING at all. Try this instead:
hNtdll = LoadLibrary("ntdll.dll");
NtOpenDirectoryObject = (NTOPENDIRECTORYOBJECT) GetProcAddress(hNtdll, "NtOpenDirectoryObject");
...
if (NtOpenDirectoryObject)
{
// add these three lines
str.Length = lstrlenW(uString) * sizeof(WCHAR);
str.MaximumLength = str.Length;
str.Buffer = uString;
InitializeObjectAttributes (&obj, &str, 0, NULL, NULL);
NtOpenDirectoryObject(&hFile, 0x20001, &obj);
}
I'm trying to install some sort of first-chance exception handler which can resume execution after unprotecting (VirtualProtect()) the memory page.
(I'm trying to install some watchpoints; and no, the possibility of the VirtualAlloc function to set watchpoints is not what I need; there I cannot dynamically set and unset the watching state of memory regions/pages)
I've read in the last couple of days a lot about these SEH things, but actually most I can find is for setting function local exception handlers etc....
If I'm not wrong I need to set somehow something called FS[0] (which is thread-local?).
tl;dr
I'd like to know how to install a global first-chance (= possibility to resume code and retry last instruction) exception handler which can catch hardware exceptions (like access violations).
P.s.: I can use Assembly, C or C++, but no C# etc.
Note: I have the whole thing working under POSIX systems via sigaction on SIGSEGV, but there's no such thing for Windows as far as I can seeā¦
#include <windows.h>
#include <stdio.h>
int xfilter(EXCEPTION_POINTERS *xp) {
int rc;
EXCEPTION_RECORD *xr = xp->ExceptionRecord;
CONTEXT *xc = xp->ContextRecord;
if(xr->ExceptionCode == EXCEPTION_ACCESS_VIOLATION) {
++xc->Eip;//Advanced by one(Probably xc->Eip += 2)//http://msdn.microsoft.com/en-us/library/ms679284(v=vs.85).aspx
rc = EXCEPTION_CONTINUE_EXECUTION;
} else {
rc = EXCEPTION_CONTINUE_SEARCH;
}
return rc;
}
int main() {
EXCEPTION_POINTERS * xp;
char *p = NULL;
__try {
fprintf(stderr, "%s", "before\n");
*p = 'X';//Access Violation
fprintf(stderr, "%s", "after\n");
}
__except(xfilter(xp = GetExceptionInformation())) {
fprintf(stderr, "%s", "Exception occurred\n");//NO EXECUTE WHEN EXCEPTION_CONTINUE_EXECUTION
}
return 0;
}
/* result
before
after
*/
Every example I can find is in C++, but I'm trying to keep my project in C. Is it even possible to host the CLR in a C program?
If so, can you point me to an example?
As the above comments hint, there is a set of COM APIs for hosting the CLR, and you should be able to call these COM APIs from both C and C++.
As an example, below is a quick piece of (untested) C code that shows how to start up the CLR and execute a static method of a class in a managed assembly (which takes in a string as an argument and returns an integer). The key difference between this code and its C++ counterpart is the definition of COBJMACROS and the use of the <type>_<method> macros (e.g. ICLRRuntimeHost_Start) to call into the CLR-hosting COM interface. (Note that COBJMACROS must be defined prior to #include'ing mscoree.h to make sure these utility macros get defined.)
#include <windows.h>
#define COBJMACROS
#include <mscoree.h>
int main(int argc, char **argv)
{
HRESULT status;
ICLRRuntimeHost *Host;
BOOL Started;
DWORD Result;
Host = NULL;
Started = FALSE;
status = CorBindToRuntimeEx(
NULL,
NULL,
0,
&CLSID_CLRRuntimeHost,
&IID_ICLRRuntimeHost,
(PVOID *)&Host
);
if (FAILED(status)) {
goto cleanup;
}
status = ICLRRuntimeHost_Start(Host);
if (FAILED(status)) {
goto cleanup;
}
Started = TRUE;
status = ICLRRuntimeHost_ExecuteInDefaultAppDomain(
Host,
L"c:\\path\\to\\assembly.dll",
L"MyNamespace.MyClass",
L"MyMethod",
L"some string argument to MyMethod",
&Result
);
if (FAILED(status)) {
goto cleanup;
}
// inspect Result
// ...
cleanup:
if (Started) {
ICLRRuntimeHost_Stop(Host);
}
if (Host != NULL) {
ICLRRuntimeHost_Release(Host);
}
return SUCCEEDED(status) ? 0 : 1;
}
This sample should work with .NET 2.0+, although it looks like .NET 4.0 (not yet released) has deprecated some of these APIs in favor of a new set of APIs for hosting the CLR. (And if you need this to work with .NET 1.x, you need to use ICorRuntimeHost instead of ICLRRuntimeHost.)