I am implementing some limited remote debugging functionality for an application written in C running on a Linux box. The goal is to communicate with the application and lookup the value of an arbitrary variable or run an arbitrary function.
I am able to lookup symbols through dlsym()
calls, but I am unable to determine if the address returned refers to a function or a variable. Is there a way to determine typing information via this symbol table?
You can read the file /proc/self/maps
and parse the first three fields of each line:
<begin-addr>-<end-addr> rwxp ...
Then you search the line that contains the address you are looking for and check the permissions:
r-x
: it is code;rw-
: it is writable data;r--
: it is read-only data;rwxp
: generated code, ...).For example the following program:
#include <stdio.h>
void foo() {}
int x;
int main()
{
int y;
printf("%p\n%p\n%p\n", foo, &x, &y);
scanf("%*s");
return 0;
}
...in my system gives this output:
0x400570
0x6009e4
0x7fff4c9b4e2c
...and these are the relevant lines from /proc/<pid>/maps
:
00400000-00401000 r-xp 00000000 00:1d 641656 /tmp/a.out
00600000-00601000 rw-p 00000000 00:1d 641656 /tmp/a.out
....
7fff4c996000-7fff4c9b7000 rw-p 00000000 00:00 0 [stack]
....
So the addresses are: code, data and data.