Get the end address of Linux kernel function on run-time - linux

I am trying to get the boundary for a kernel function (system calls for example). Now, if I understand correctly, I can get the start address of the interested function by reading /proc/kallsyms or System.map but I dont know how to get the end address of this function.
As you may know, /proc/kallsyms allow us to view the symbol table for Linux kernel so we can see the start address of all exported symbols. Can we use the start address of the next function to calculate the end address of the previous function? If we cannot do like this, could you suggest me another ways?

Generally, executables store only the start address of a function, as it is all that is required to call the function. You will have to infer the end address, rather than simply looking it up.
You could try to find the start address of the subsequent function, but that wouldn't always work either. Imagine the following:
void func_a() {
// do something
}
static void helper_function() {
// do something else
}
void func_b() {
// ...
helper_function();
// ...
}
You could get the address of func_a and func_b, but helper_function would not show up, because nothing needs to link to it. If you tried to use func_b as the end of func_a (assuming that the order in the compiled code in equivalent to the order in the source code, which is not guaranteed), you would end up accidentally including code that you didn't need to include - and might not find code that you need to find when inlining other functions into func_b.
So, how do we find this information? Well, if you think about it - the information does exist - all of the paths within func_a will eventually terminate (in a loop, return statement, tail call, etc), probably before helper_function begins.
You would need to parse out the code of func_a and build up a map of all of the possible code paths within it. Of course, you would need to do this anyway to inline other functions into it - so it shouldn't be too much harder to simply not care about the end address of the function.
One final note: in this example, you would have trouble finding helper_function in order to know to inline it, because the symbol wouldn't show up in kallsyms. The solution here is that you can track the call instructions in individual functions to determine what hidden functions exist that you didn't know about otherwise.
TL;DR: You can only find the end address by parsing the compiled code. You have to parse this anyway, so just do it once.

Related

i am playing with processes etc. but I dont know how to add "client.dll" to hex value

In cheat engine you can do "client.dll"+00D3AC5C and in reclass <client.dll>+00D3AC5C
how to do the same in python I am using ReadWriteMemory but I will soon change it for something more complex. Can you tell me please how to do it with RWM or with something other ?
According to the source code of that library, there's seemingly no way to get the base address of a process.
However you can get the base address by bypassing the library and doing it yourself via this method. Then, once you have the hex value of the base address, you can then simply add an offset to it, then use RWM's read() or get_pointer().

Locating and Editing Dynamic Symbol Table of Loaded Program?

My goal is explained in this question HERE
Is it possible to locate the address of a symbol's entry in the dynamic symbol table loaded into a program?
If we can locate it, can we edit it somehow? For example if the app made the call to a function named original_func then the control should actually come to my hook_func and from there I call the original_func.
Update:
Some code according to the answer by 'Employed Russian':
extern Elf32_Dyn _DYNAMIC[];
int i=0;
uint32_t DST_base_addr;
Elf32_Dyn *dyn;
for (dyn = _DYNAMIC; dyn->d_tag != DT_NULL; ++dyn)
{
if(dyn->d_tag==DT_SYMTAB)
{
DST_base_addr=dyn->d_un.d_ptr;
LOGE("Base address of dynamic symbol table is; 0x%x", DST_base_addr);
break;
}
}
Output: 0x148
1- Not sure what that 0x148 means. It's definitely not an absolute address.
2- Also, where can I find good listing of these useful pre-defined variables such as _DYNAMIC[] _GLOBAL_OFFSET_TABLE_ etc.? I wasn't very aware of such variables even when I went through ELF notes here and there.
Is it possible to locate the address of a symbol's entry in the dynamic symbol table loaded into a program?
Yes, it's pretty easy: iterate over elements of the _DYNAMIC[] array, until you find an element with .d_tag == DT_SYMTAB. The .d_un.d_ptr of that entry will point to the dynamic symbol table in memory.
To find a specific symbol, you will also need to refer to DT_STRTAB.
If we can locate it, can we edit it somehow?
Sure: it's just a memory location. You may need to mprotect it to be writable, but once you do, you can modify it to your heart's content.
However, most modifications will either have no effect, or cause your program to crash later.
For example if the app made the call to a function named original_func then the control should actually come to my hook_func and from there I call the original_func.
It's pretty difficult to achieve your stated goal using this particular method, and much easier methods exist.
Perhaps you are looking for this?

How to use strstrip for parsing a string in two parts

I would like to know hot to parse a string like this "hello world" into "helloworld" using the strstrip kernel function. I am developing a Linux Kernel char device and this functions causes me a Kernel Panic (or Kernel Opss).
The way I'm using this function is the following:
char result[100];
strcpy(result, "hello world");
strstrip(result);
strstrip(&result); //Also tried this
strstrip("100+200"); //Also tried this
The Kernel error is caused as soon as the strstrip line gets executed. What is the proper way to call this function?
Actually strstrip helps to remove the white spaces at the front. It does not remove all the white spaces with in the string.
Please look at the below example.
char result[100];
strcpy(result, " hello world from stack exchange");
printk("\n before: %s",result);
strcpy(result, strstrip((char*)result));
printk("\n after: %s",result);
Hope it helps.
srtstrip() is a wrapper function for strim() (http://lxr.linux.no/linux+v3.11.2/lib/string.c#L361) in modern kernels. As it will attempt to modify the string itself, you cannot call it with a static string as you have in the third attempt.
The second attempt you have is passing a pointer to an array variable which is also a pointer. So you are passing a char** which if you look at the link above you can see is not correct.
The first attempt should not cause a kernel error, but you do not appear to be receiving the return value in a a local variable. What kind of error are you receiving? I will update this answer if you can provide that information.
In the end though as Balamurugan A points out, this function does not do what you seem to think it does. strsep() (http://lxr.linux.no/linux+v3.11.2/lib/string.c#L485) may help you out here but it will only be a stepping stone to removing all spaces. You will actually have to copy the string into a new buffer word by word as there is not way to simply "shift memory contents", as it were.

capturing pipe exit status in R

I am using R's pipe() function to capture output from a shell command, but I would also like to get the exit code from the command.
I know that I could use system2 here, but I need the advantage of a pipe i.e. the ability to process output in a streaming fashion.
I am considering writing my own library to wrap the popen() and pclose() C functions to take advantage of the fact that pclose() returns the exit status, but maybe this can be avoided.
Any suggestions? Thanks!
Note
There are certainly ways to do this with temporary files, named pipes, etc but I would ideally like to avoid these workarounds. I am willing to compile a shared library with an R->C function in it (and I'm even willing to copy-paste part of the R source code), but I'm not willing to rebuild R.
Update
I started reading through the R source code and found the unchecked pclose call:
in src/main/connections.c:
static void pipe_close(Rconnection con)
{
pclose(((Rfileconn)(con->private))->fp);
con->isopen = FALSE;
}
I tried going forward with the approach of implementing an R_pclose C function that duplicates the R code for close() but saves this return value. I unfortunately ran into this static variable in src/main/connections.c
static Rconnection Connections[NCONNECTIONS];
Since I'd have to run objcopy --globalize-symbol=Connections libR.so /path/to/my/libR.so anyway to access the variable, it looks like my best solution is to rebuild R with my own patch to capture the pclose return value.
Ugly hack: you can wrap your command call into a small shell script which writes the exit code of its child to some temporary file. So when the stream has ended, you could wait until that file has non-zero size, then read the status from there. I hope someone comes up with a better solution, but at least this is a kind of solution.

gdb watchpoint on struct variables

I have a structure like this :
struct A
{
int a;
char b;
};
this structure is referenced at various places in a large code. The pointer to this struct is passed on to different functions and accordingly the variables in this structure are updated. i want to set a watchpoint on variable a in this struct as it travels across many functions. to see how a changes. How do I set this watch point ?
First set a breakpoint where you create an instance of your struct using break, like
break myfile.c:9
Then just use watch to set a watchpoint, like
watch myStructInstance.a
for variable a or
watch *0x7ffff75177f0
for a memory address. The memory address can be obtained easily by using print, like
print &myStructInstance.a
Now every time variable a or the given memory address gets modified gdb will break.
I come with the same problem when debugging my virtual memory simulator. The problem is how to keep a close look at the data inside structs.
I tried using print to check, but that's too noisy. Because I have to print out more than 15 variables.
I also tried using watchpoint, but on my machine, I can only set no more than 4 hardware watchpoints. That's not even close to my goal.
Finally, I find my solution by using user-defined function in .gdbinit file. e.g. if I want to watch array of my structure, using
define lookintoStructs
if mystruct != 0x0
print mystruct[0]
print mystruct[1]
print mystruct[2]
print mystruct[3]
print mystruct[4]
print mystruct[5]
end
end
to make it more convenient to use, I'd like to make it hook to my next instruction in gdb.
define hook-next
lookintoStructs
end
so when I call next or n in gdb, lookintoStructs could be called automatically. works fine for me.

Resources