I am trying to compile one driver in VS, but it shows -
Severity Code Description Project File Line Suppression State
Error LNK2019 unresolved external symbol __imp__PsGetProcessWow64Process#4 referenced in function _GetProcessModule#8 Garhal C:\Users\Raitis\source\repos\GarHal_CSGO\Garhal\memory.obj 1
Quickly enough, I found a place, where this PsGetProcessWow64Process is being used https://prnt.sc/uffavf
But it is defined, and it's even an official ntos.h function. Just pressing F12 on it finds it easily - https://prnt.sc/uffbjg
Screenshot from error list - https://prnt.sc/uffc6t
The problem is that this in undocumented functions and the linker is having a hard time finding where is the function to put a pointer to it in the generated binary, so first include ntifs.h before ntddk.h like this
#include <ntifs.h>
#include <ntddk.h>
it must be before ntddk or you will get weird errors
then add this line :
NTKERNELAPI PVOID PsGetProcessWow64Process(__in PEPROCESS Process);
which is the signature of the function and now you are ready to call that function
another way to get it is using function pointers and resolving it at run time
#include <ntddk.h>
typedef struct _PEB32 {
UCHAR InheritedAddressSpace;
UCHAR ReadImageFileExecOptions;
UCHAR BeingDebugged;
UCHAR Spare;
ULONG Mutant;
ULONG ImageBaseAddress;
ULONG/*PPEB_LDR_DATA32*/ Ldr;
} PEB32, *PPEB32;
typedef PPEB32 (NTAPI * pfn_PsGetProcessWow64Process) (PEPROCESS Process);
pfn_PsGetProcessWow64Process PsGetProcessWow64Process = NULL;
RtlInitUnicodeString (&usFunctionName, L"PsGetProcessWow64Process");
PsGetProcessWow64Process = (pfn_PsGetProcessWow64Process) (SIZE_T)MmGetSystemRoutineAddress (&usFunctionName);
pPEB32 = PsGetProcessWow64Process (pEProcess);
Related
I'm writing a simple code in C language, and this works.
Which compiles and excutes with no errors, gives the expected output.
#include <stdio.h>
int main(void) {
struct SiteTemplate {
int views;
};
int visit(struct SiteTemplate *site) {
site -> views++;
return 0;
}
struct SiteTemplate site;
site.views = 0;
visit(&site);
printf("%d\n", site.views);
return 0;
}
But in my VS Code, with C_Cpp linting is on, my IDE shows the following error and other problems with it.
declaration is incompatible with previous "visit" (declared at line 8)
Having a screenshot of it:
This error linting is really confusing me since my code works with gcc, it doesn't show any error when compiling.
And also, if I move my struct and function definition to the global level instead of inside main(), then the errors don't exist anymore... But what's the error declaration is incompatible? Or is there any problem with my code?
Click here to view the another screenshot to save whitespaces of this page.
By the way, the version of my VS Code is 1.52.0, with default C_Cpp linting.
Nested function definition is not standard C, it's supported by compiler extensions. According to C standard, any function definition needs to appear outside of any other function definition.
I have a 218KB .dll and a 596KB .so file, both with identical names. I want to link to the .dll to avoid the "unresolved external symbol" error that the linker returns, but I can't find a way to link to the DLL file.
According to this Pelles C forum topic, I need to use the .def file to create a .lib... but I don't have a .def file. This forum topic shows how to use polink to create a .lib from the command line, so I ran polink /? to get some more options. I noticed a /MAKEDEF option, but running this with both the .dll and the .so gives a "No library file specified" fatal error.
I have been trying to do this for three hours, and am out of ideas. I have got to the point where my web searches turn up my own help-requests. There must be a way to do this... How can I link to a .dll?
With information found in the header #include and your details, here is a way to replace the missing function by calling them dynamically from your software.
1- the following prototype is in #include :
typedef float (* XPLMFlightLoop_f)(float inElapsedSinceLastCall, float inElapsedTimeSinceLastFlightLoop, int inCounter, void * inRefcon);
2- some const that you can fill as needed:
const char *sDllPathName = "<Your XPLM_API DLL>.dll";
const char *sXPLMRegisterFlightLoopCallbackName = "XPLMRegisterFlightLoopCallback";
In order to confirm the sXPLMRegisterFlightLoopCallbackName, you can
use the freeware Dependency Walker and check name and format of
the exported functions.
3- declare the prototype of the external function:
Be aware to the calling convention __cdecl or __stdcall
In the current case, the keyword XPLM_API is defined in the XPLMDefs.h as follow:
#define XPLM_API __declspec(dllexport) // meaning __cdecl calling convention
typedef void (__cdecl *XPLMRegisterFlightLoopCallback_PROC)(XPLMFlightLoop_f, float, void *);
4- clone the function to call it in your software:
#include <windows.h>
void XPLMRegisterFlightLoopCallback(XPLMFlightLoop_f inFlightLoop, float inInterval, void * inRefcon)
{
HINSTANCE hInstDLL;
XPLMRegisterFlightLoopCallback_PROC pMyDynamicProc = NULL;
// Load your DLL in memory
hInstDLL = LoadLibrary(sDllPathName);
if (hInstDLL!=NULL)
{
// Search for the XPLM Function
pMyDynamicProc = (XPLMRegisterFlightLoopCallback_PROC) GetProcAddress(hInstDLL, sXPLMRegisterFlightLoopCallbackName);
if (pMyDynamicProc != NULL)
{
// Call the XPLM Function with the orignal parameter
(pMyDynamicProc)(inFlightLoop,inInterval,inRefcon);
return;
}
}
// Do something when DLL is missing or function not found
}
5- just add your described call:
...
XPLMRegisterFlightLoopCallback(callbackfunction, 0, NULL);
...
I have used rust-bindgen to generate rust interface code.
Now in the C code you can find this:
extern const struct mps_key_s _mps_key_ARGS_END;
#define MPS_KEY_ARGS_END (&_mps_key_ARGS_END)
Note that in the hole rest of the code _mps_key_ARGS_END does not appear again.
The macro MPS_KEY_ARGS_END gets used regularly amung other simular mps_key_s.
Now the code produced by rust-bindgen is this:
pub static _mps_key_ARGS_END: Struct_mps_key_s;
Now in C code here is a example usage:
extern void _mps_args_set_key(mps_arg_s args[MPS_ARGS_MAX], unsigned i,
mps_key_t key);
_mps_args_set_key(args, 0, MPS_KEY_ARGS_END);
In rust it looks like this:
pub fn _mps_args_set_key(args: [mps_arg_s, ..32u], i: ::libc::c_uint,
key: mps_key_t);
Now I try to call it like this:
_mps_args_set_key(args, 0 as u32, _mps_key_ARGS_END );
But I get a error:
error: mismatched types: expected *const Struct_mps_key_s, found
Struct_mps_key_s (expected *-ptr, found enum Struct_mps_key_s)
I am not a good C programmer, and I dont even understand where these C static even get there values from.
Thanks for your help.
Edit:
Update based on the answer of Chris Morgan.
I added this code (note, I replaced *const mps_key_s with mps_key_t):
pub static MPS_KEY_ARGS_END: mps_key_t = &_mps_key_ARGS_END;
Just for some extra information on why Im using mps_key_t, in C:
typedef const struct mps_key_s *mps_key_t;
In rust:
pub type mps_key_t = *const Struct_mps_key_s;
This seams seam to work better then befor but now Im getting a bad crash:
error: internal compiler error: unexpected failure note: the compiler
hit an unexpected failure path. this is a bug. note: we would
appreciate a bug report:
http://doc.rust-lang.org/complement-bugreport.html note: run with
RUST_BACKTRACE=1 for a backtrace task 'rustc' failed at 'expected
item, found foreign item _mps_key_ARGS_END::_mps_key_ARGS_END
(id=1102)',
/home/rustbuild/src/rust-buildbot/slave/nightly-linux/build/src/libsyntax/ast_map/mod.rs:327
#define MPS_KEY_ARGS_END (&_mps_key_ARGS_END)
The & part indicates that it is taking a pointer to the object, that the type of MPS_KEY_ARGS_END will be mps_key_s const*. In Rust, that is *const mps_key_s (a raw pointer), and can be achieved in the same way as in C, &_mps_key_ARGS_END. You can define MPS_KEY_ARGS_END in a way that you can use conveniently like this:
static MPS_KEY_ARGS_END: *const mps_key_s = &_mps_key_ARGS_END;
I'm trying to use gate_desc *idt_table in a kernel module. The set_trap_gate() function defined in desc.h uses this pointer. In desc.h is also a definition : extern gate_desc idt_table[].
I tried different things:
use idt_table in my module without definition or affectation
affect idt_table with my (valid) idt_table address
I get either an id_table undefined warning during compilation or incomplete type for idt_table.
creating a new var named for instance gate_desc *it = (gate_desc *)#; And copy the set_trap_gate, set_gate, write_idt_entry, pack_gate functions from sched.h to my module file (renaming them, and using it instead of idt_table). This compiles fine but when inserting my module I get an unknown symbol in module (ret -1) error.
(there is no reference in my module to idt_table, and the functions I use from sched do use my variable).
I tried to see where in the files included by sched.h was defined idt_table, but couldn't find it!
Does someone know how I could use, the idt_table pointer from sched.h (affecting it with the corrct address) or create a new pointer?
Theoretically, you could implement a non-init-section set_trap_gate() via:
void set_trap_gate(int n, void *addr)
{
struct { uint16_t lim; struct desc_struct *idt_table; }
__attribute__((packed)) idt;
__asm__ ("sidt %0" : : "m"(idt) : "memory");
_set_gate(idt.idt_table + n, 15, 0, addr);
}
But that'd be CPU-local, i.e. it's not guaranteed to modify any other IDT but the one of the CPU it's running on. Also, it might fall foul of writeprotected memory.
What exactly is it you're trying to achieve ?
I had a problem with a part of my code, which after some iterations seemed to read NaN as value of a double of a struct. I think I found the error, but am still wondering why gcc (version 3.2.3 on a embedded Linux with busybox) did not warn me. Here are the important parts of the code:
A c file and its header for functions to acquire data over USB:
// usb_control.h
typedef struct{
double mean;
short *values;
} DATA_POINTS;
typedef struct{
int size;
DATA_POINTS *channel1;
//....7 more channels
} DATA_STRUCT;
DATA_STRUCT *create_data_struct(int N); // N values per channel
int free_data_struct(DATA_STRUCT *data);
int aqcu_data(DATA_STRUCT *data, int N);
A c and header file with helper function (math, bitshift,etc...):
// helper.h
int mean(DATA_STRUCT *data);
// helper.c (this is where the error is obviously)
double mean(DATA_STRUCT *data)
{
// sum in for loop
data->channel1->mean = sum/data->N;
// ...7 more channels
// a printf here displayed the mean values corretly
}
The main file
// main.c
#include "helper.h"
#include "usb_control.h"
// Allocate space for data struct
DATA_STRUCT *data = create_data_struct(N);
// get data for different delays
for (delay = 0; delay < 500; delay += pw){
acqu_data(data, N);
mean(data);
printf("%.2f",data->channel1->mean); // done for all 8 channels
// printf of the mean values first is correct. Than after 5 iterations
// it is always NaN for channel1. The other channels are displayed correctly;
}
There were no segfaults nor any other missbehavior, just the NaN for channel1 in the main file.
After finding the error, which was not easy, it was of course east to fix. The return type of mean(){} was wrong in the definition. Instead of double mean() it has to be int mean() as the prototype defines. When all the functions are put into one file, gcc warns me that there is a redefinition of the function mean(). But as I compile each c file seperately and link them afterwards gcc seems to miss that.
So my questions would be. Why didn't I get any warnings, even non with gcc -Wall? Or is there still another error hidden which is just not causing problems now?
Regards,
christian
When each .c file is compiled separately, the only information the compiler knows is the function prototype you have given.
Because every file is compiled separately, there is no way the compiler process of main.c knows the definition of mean in helper.c is wrong.
After the .c file is compiled, the signature will be stripped, so the linker cannot know the mean is wrong either.
A simple fix is always include the interface .h file in the implementation .c file
// in helper.c:
#include "helper.h"
double mean(DATA_STRUCT *data);
Then the compiler process of helper.c will notice that inconsistent type and warn you.
A mean usually is a real value so double is ok. Here you define mean as returning double, but the prototype says int mean(...).
The only way gcc can be aware of the fact that there's a redefinition, is if the redefinition occurs for real... When you compile files separately likely the mean prototype is missing... it is not shown in your code fragment at least: you should include helper.h also into helper.c. Doing so, gcc -c helper.c must give you a warning. I have gcc 4.3.2, but I am almost sure it must be so also for the version you have. In the main, you just use mean, so here the gcc trusts what is said in helper.h. When you link, there is no more information about the size of arguments and returning value, and bad things happen (like reading an int as a double).
Another detail: you say you get NaN for an int of the struct... well, in the struct there's a double, and int can't be NaN!