How to identify STACK and HEAP segments in /proc/$PID/maps file? - c

I could identify the text, ds and bss segments in /proc/$PID/maps file (by guessing or with the help of access-specifiers of a particular segment). But heap and stack segments are given sequently. Is there a way to identify which segment belongs to stack and which belongs to heap?
----- How to identify the demarkation between heap and stack in this example ----------
0a8a0000-0ab2e000 rw-p 0a8a0000 00:00 0 [heap]
< b648e000-b648f000 ---p b648e000 00:00 0
< b648f000-b6496000 rw-p b648f000 00:00 0
< b6496000-b6497000 ---p b6496000 00:00 0
< b6497000-b649e000 rw-p b6497000 00:00 0
< b649e000-b649f000 ---p b649e000 00:00 0
< b649f000-b64a6000 rw-p b649f000 00:00 0
< b64a6000-b64a7000 ---p b64a6000 00:00 0
< b64a7000-b64ae000 rw-p b64a7000 00:00 0
< b64ae000-b64af000 ---p b64ae000 00:00 0
< b64af000-b657a000 rw-p b64af000 00:00 0
< b657a000-b657b000 ---p b657a000 00:00 0
< b657b000-b65a5000 rw-p b657b000 00:00 0
< b65a5000-b65a6000 ---p b65a5000 00:00 0
< b65a6000-b67ca000 rw-p b65a6000 00:00 0
< b67ca000-b67cb000 ---p b67ca000 00:00 0
< b67cb000-b69ff000 rw-p b67cb000 00:00 0
< b69ff000-b6a00000 ---p b69ff000 00:00 0
< b6a00000-b6bff000 rw-p b6a00000 00:00 0
< b6bff000-b6c00000 ---p b6bff000 00:00 0
< b6c00000-b6dff000 rw-p b6c00000 00:00 0
< b6dff000-b6e00000 ---p b6dff000 00:00 0
< b6e00000-b6fff000 rw-p b6e00000 00:00 0
< b6fff000-b7000000 ---p b6fff000 00:00 0
< b7000000-b70fd000 rw-p b7000000 00:00 0
< b70fd000-b70fe000 ---p b70fd000 00:00 0
< b70fe000-b72fd000 rw-p b70fe000 00:00 0
< b72fd000-b72fe000 ---p b72fd000 00:00 0
< b72fe000-b7548000 rw-p b72fe000 00:00 0
< b7548000-b7549000 ---p b7548000 00:00 0
< b7549000-b7f37000 rw-p b7549000 00:00 0
< b7f4b000-b7f4c000 ---p b7f4b000 00:00 0
< b7f4c000-b7f51000 rw-p b7f4c000 00:00 0
< bfbae000-bfbc3000 rw-p bffea000 00:00 0 [stack]

The /proc/PID/maps file containing the currently mapped memory regions and
their access permissions.
The format is:
address perms offset dev inode pathname
08048000-08049000 r-xp 00000000 03:00 8312 /opt/test
08049000-0804a000 rw-p 00001000 03:00 8312 /opt/test
0804a000-0806b000 rw-p 00000000 00:00 0 [heap]
a7cb1000-a7cb2000 ---p 00000000 00:00 0
a7cb2000-a7eb2000 rw-p 00000000 00:00 0
a7eb2000-a7eb3000 ---p 00000000 00:00 0
a7eb3000-a7ed5000 rw-p 00000000 00:00 0 [stack:1001]
a7ed5000-a8008000 r-xp 00000000 03:00 4222 /lib/libc.so.6
a8008000-a800a000 r--p 00133000 03:00 4222 /lib/libc.so.6
a800a000-a800b000 rw-p 00135000 03:00 4222 /lib/libc.so.6
a800b000-a800e000 rw-p 00000000 00:00 0
a800e000-a8022000 r-xp 00000000 03:00 14462 /lib/libpthread.so.0
a8022000-a8023000 r--p 00013000 03:00 14462 /lib/libpthread.so.0
a8023000-a8024000 rw-p 00014000 03:00 14462 /lib/libpthread.so.0
a8024000-a8027000 rw-p 00000000 00:00 0
a8027000-a8043000 r-xp 00000000 03:00 8317 /lib/ld-linux.so.2
a8043000-a8044000 r--p 0001b000 03:00 8317 /lib/ld-linux.so.2
a8044000-a8045000 rw-p 0001c000 03:00 8317 /lib/ld-linux.so.2
aff35000-aff4a000 rw-p 00000000 00:00 0 [stack]
ffffe000-fffff000 r-xp 00000000 00:00 0 [vdso]
where "address" is the address space in the process that it occupies, "perms"
is a set of permissions:
r = read
w = write
x = execute
s = shared
p = private (copy on write)
"offset" is the offset into the mapping, "dev" is the device (major:minor), and
"inode" is the inode on that device. 0 indicates that no inode is associated
with the memory region, as the case would be with BSS (uninitialized data).
The "pathname" shows the name associated file for this mapping. If the mapping
is not associated with a file:
[heap] = the heap of the program
[stack] = the stack of the main process
[stack:1001] = the stack of the thread with tid 1001
[vdso] = the "virtual dynamic shared object",
the kernel system call handler
or if empty, the mapping is anonymous.
(Source https://www.kernel.org/doc/Documentation/filesystems/proc.txt)

Related

zero sized heap memory in page aligned allocation`

I'm trying to study how Linux would behave if I were to allocate a 10 bytes of memory at every page boundary for a total of ten pages. Here is the program I could come up with:
1 #include <stdlib.h>$
2 #include <stdio.h>$
3 #include <time.h>$
4 #include <unistd.h>$
5 #include <string.h>$
6 $
7 #define PAGESIZE getpagesize()$
8 int main () {$
9 int *ArrP[10] = {NULL};$
10 int pgSz = PAGESIZE;$
11 int randnum;$
12 $
13
14 for (int i = 0; i < (sizeof(ArrP)/sizeof(int*)); i++) {$
15 if(posix_memalign((void **)&ArrP[i], pgSz, 10)) {$
16 perror("error getting page aligned mem: ");$
17 exit(1);$
18 }$
19 else$
20 printf("ArrP[%d] = %lu\n", i, ArrP[i]);$
21 }$
22 $
23 srand(time(0));$
24 while(1) {$
25 for (int i = 0; i <(sizeof(ArrP)/sizeof(int*)); i++) {$
26 randnum = rand();$
27 memcpy(ArrP[i], &randnum, sizeof(int));$
28 }$
29 }$
30 return 0;$
31 }$
However when I run it, the /proc/pid/maps file shows a heap size of 0.
here's the content of that file:
555555554000-555555555000 r--p 00000000 08:01 1966744 /home/AB1/ProgPractice/InternalFragmentation
555555555000-555555556000 r-xp 00001000 08:01 1966744 /home/AB1/ProgPractice/InternalFragmentation
555555556000-555555557000 r--p 00002000 08:01 1966744 /home/AB1/ProgPractice/InternalFragmentation
555555557000-555555558000 r--p 00002000 08:01 1966744 /home/AB1/ProgPractice/InternalFragmentation
555555558000-555555559000 rw-p 00003000 08:01 1966744 /home/AB1/ProgPractice/InternalFragmentation
555555559000-55555557a000 rw-p 00000000 00:00 0 [heap]
7ffff7dd8000-7ffff7dfd000 r--p 00000000 08:01 2234184 /usr/lib/libc-2.30.so
7ffff7dfd000-7ffff7f4a000 r-xp 00025000 08:01 2234184 /usr/lib/libc-2.30.so
7ffff7f4a000-7ffff7f94000 r--p 00172000 08:01 2234184 /usr/lib/libc-2.30.so
7ffff7f94000-7ffff7f95000 ---p 001bc000 08:01 2234184 /usr/lib/libc-2.30.so
7ffff7f95000-7ffff7f98000 r--p 001bc000 08:01 2234184 /usr/lib/libc-2.30.so
7ffff7f98000-7ffff7f9b000 rw-p 001bf000 08:01 2234184 /usr/lib/libc-2.30.so
7ffff7f9b000-7ffff7fa1000 rw-p 00000000 00:00 0
7ffff7fce000-7ffff7fd1000 r--p 00000000 00:00 0 [vvar]
7ffff7fd1000-7ffff7fd2000 r-xp 00000000 00:00 0 [vdso]
7ffff7fd2000-7ffff7fd4000 r--p 00000000 08:01 2234140 /usr/lib/ld-2.30.so
7ffff7fd4000-7ffff7ff3000 r-xp 00002000 08:01 2234140 /usr/lib/ld-2.30.so
7ffff7ff3000-7ffff7ffb000 r--p 00021000 08:01 2234140 /usr/lib/ld-2.30.so
7ffff7ffc000-7ffff7ffd000 r--p 00029000 08:01 2234140 /usr/lib/ld-2.30.so
7ffff7ffd000-7ffff7ffe000 rw-p 0002a000 08:01 2234140 /usr/lib/ld-2.30.so
7ffff7ffe000-7ffff7fff000 rw-p 00000000 00:00 0
7ffffffde000-7ffffffff000 rw-p 00000000 00:00 0 [stack]
ffffffffff600000-ffffffffff601000 --xp 00000000 00:00 0 [vsyscall]
I've disabled ASLR but it doesn't make a difference. Any suggestions

Understanding memory maps

I'm very new to C programming and investigating continuously increasing RSS size. The suspicion is there is some memory leak. I looked at the /proc/<pid>/maps and found the following:
f8000000-fb180000 rw-p 00000000 00:00 0
fb180000-fd580000 ---p 00000000 00:00 0
fd580000-fdc80000 rw-p 00000000 00:00 0
fdc80000-100000000 ---p 00000000 00:00 0
100000000-1005a0000 rw-p 00000000 00:00 0
1005a0000-140000000 ---p 00000000 00:00 0
7fb45d1dd000-7fb45d1e0000 ---p 00000000 00:00 0
7fb45e0ec000-7fb45e0ef000 ---p 00000000 00:00 0
7fb45e0ef000-7fb45e1ed000 rw-p 00000000 00:00 0
7fb45e1ed000-7fb45e1f0000 ---p 00000000 00:00 0
7fb45e1f0000-7fb45e2ee000 rw-p 00000000 00:00 0
7fb45e2ee000-7fb45e2f1000 ---p 00000000 00:00 0
7fb45e2f1000-7fb45e3ef000 rw-p 00000000 00:00 0
7fb45e3ef000-7fb45e3f2000 ---p 00000000 00:00 0
7fb45e3f2000-7fb45e4f0000 rw-p 00000000 00:00 0
7fb45e4f0000-7fb45e4f3000 ---p 00000000 00:00 0
7fb45e4f3000-7fb45e5f1000 rw-p 00000000 00:00 0
7fb45e5f1000-7fb45e5f4000 ---p 00000000 00:00 0
7fb45e5f4000-7fb45e6f2000 rw-p 00000000 00:00 0
7fb45e6f2000-7fb45e6f5000 ---p 00000000 00:00 0
7fb45e6f5000-7fb45e7f3000 rw-p 00000000 00:00 0
7fb45e7f3000-7fb45e7f6000 ---p 00000000 00:00 0
7fb45e7f6000-7fb45e8f4000 rw-p 00000000 00:00 0
7fb45e8f4000-7fb45e8f7000 ---p 00000000 00:00 0
//Tons of the similar entries...
7fb71652b000-7fb71652c000 rw-p 0001a000 08:01 2187 /lib/x86_64-linux-gnu/libpthread-2.27.so
7fb716568000-7fb71656f000 r--s 00000000 08:01 5020 /usr/lib/x86_64-linux-gnu/gconv/gconv-modules.cache
7fb716759000-7fb71675a000 rw-p 00000000 00:00 0
7ffc5f781000-7ffc5f7a2000 rw-p 00000000 00:00 0 [stack]
7ffc5f7c7000-7ffc5f7ca000 r--p 00000000 00:00 0 [vvar]
7ffc5f7ca000-7ffc5f7cc000 r-xp 00000000 00:00 0 [vdso]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
The thing that I noticed was that the vast majority of /proc/<pid>/maps were entries like:
7fb45e7f3000-7fb45e7f6000 ---p 00000000 00:00 0
What does this mean? Doesn't it mean that system allocator release the memory it acquires?
Is there a way to examine the memory content at address, e.g. 7fb45e5f4000-7fb45e6f2000 at run-time?
I tried to attach to the running process with gdb and looked at the memory.
(gdb) x /1xg 0x7fb45e1ed000
0x5e1ed000: Cannot access memory at address 0x5e1ed000
Entries like
7fb45e0ec000-7fb45e0ef000 ---p 00000000 00:00 0
7fb45e0ef000-7fb45e1ed000 rw-p 00000000 00:00 0
look like thread stacks and their associated guard pages.
It looks like you create a lot of threads, but neither reap them via pthread_join(), or detach them via pthread_detach() (or create them in detached state).
Non-detached threads must be reaped to return their resources (stack, specifically) to the OS.

Litmus test for checking if address range is in process address space?

I am wondering if there is any simple/neat way in C to detect if a given memory range (A, A+len) falls under the process address space?
EDIT:
My use case is more for reverse engineering and locating some strings (or fixed sized structs) in memory. So even a hacky test will work right for me to narrow down my search.
On Linux, read /proc/$pid/maps. It contains a textual description of the memory ranges mapped by a process, e.g.
00400000-0040b000 r-xp 00000000 08:00 35402 /bin/cat
0060a000-0060b000 r--p 0000a000 08:00 35402 /bin/cat
0060b000-0060c000 rw-p 0000b000 08:00 35402 /bin/cat
006ab000-006cc000 rw-p 00000000 00:00 0 [heap]
7f9a73235000-7f9a734fe000 r--p 00000000 08:00 949 /usr/lib/locale/locale-archive
7f9a734fe000-7f9a736b8000 r-xp 00000000 08:00 18124 /lib/x86_64-linux-gnu/libc-2.19.so
7f9a736b8000-7f9a738b8000 ---p 001ba000 08:00 18124 /lib/x86_64-linux-gnu/libc-2.19.so
7f9a738b8000-7f9a738bc000 r--p 001ba000 08:00 18124 /lib/x86_64-linux-gnu/libc-2.19.so
7f9a738bc000-7f9a738be000 rw-p 001be000 08:00 18124 /lib/x86_64-linux-gnu/libc-2.19.so
7f9a738be000-7f9a738c3000 rw-p 00000000 00:00 0
7f9a738c3000-7f9a738e6000 r-xp 00000000 08:00 17952 /lib/x86_64-linux-gnu/ld-2.19.so
7f9a73ad9000-7f9a73adc000 rw-p 00000000 00:00 0
7f9a73ae3000-7f9a73ae5000 rw-p 00000000 00:00 0
7f9a73ae5000-7f9a73ae6000 r--p 00022000 08:00 17952 /lib/x86_64-linux-gnu/ld-2.19.so
7f9a73ae6000-7f9a73ae7000 rw-p 00023000 08:00 17952 /lib/x86_64-linux-gnu/ld-2.19.so
7f9a73ae7000-7f9a73ae8000 rw-p 00000000 00:00 0
7ffde1b80000-7ffde1ba1000 rw-p 00000000 00:00 0 [stack]
7ffde1bd5000-7ffde1bd7000 r--p 00000000 00:00 0 [vvar]
7ffde1bd7000-7ffde1bd9000 r-xp 00000000 00:00 0 [vdso]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
There's a lot of information here, but what matters to you is the first two columns. The first one is an address range, and the second one is the access privileges it's mapped with.
Note that this has a distinct advantage over any approach based around triggering segfaults: it can be read from another process, and doesn't require any code to be added to the target process.

Non-existent physical address error with mmap

I'm trying to mmap a file, and it seems to succeed but when I access it, I get an SIGBUS error.
Code:
int main(int argc, char* argv[]) {
int pid = getpid();
char cmd [1024];
int file;
if (argc != 2) {
printf("Wrong arguments\n");
return 1;
}
printf("%s", argv[1]);
int numpages = atoi(argv[1]);
sprintf(cmd, "cat /proc/%d/maps", pid);
system(cmd);
long page_size = sysconf(_SC_PAGESIZE);
file = open(argv[1], O_RDWR, (mode_t)0600);
ftruncate(file, page_size * numpages);
if(file == -1) {
perror("file open failed!\n");
return 1;
}
printf("\n\n mapping file - numpages: %d \n\n", numpages);
printf("mapping %ld KB\n", page_size * numpages/1024);
int* mapped_file = mmap(0, page_size * numpages, PROT_READ | PROT_WRITE, MAP_PRIVATE, file, 0 );
if (mapped_file == MAP_FAILED) {
perror("Map failed");
return 1;
}
printf("mapped file at %p\n\n", mapped_file);
int* current_pos = mapped_file;
system(cmd);
int j;
for (j=0; j<numpages; j++) {
printf("%d ", *current_pos);
current_pos += page_size/4;
}
if (munmap (mapped_file, page_size * numpages) == -1) {
perror ("munmap");
return 1;
}
if (close(file) == -1) {
perror("close");
return 1;
}
return 0;
}
Output:
(gdb) run 64
Starting program: /home/jords/engcode/workspace/SE370Assignment3/A3Program3 64
00400000-00401000 r-xp 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00600000-00601000 r--p 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00601000-00602000 rw-p 00001000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
7ffff7a48000-7ffff7bd2000 r-xp 00000000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7bd2000-7ffff7dd1000 ---p 0018a000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7dd1000-7ffff7dd5000 r--p 00189000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7dd5000-7ffff7dd6000 rw-p 0018d000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7dd6000-7ffff7ddc000 rw-p 00000000 00:00 0
7ffff7ddc000-7ffff7dfd000 r-xp 00000000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7ffff7fd0000-7ffff7fd3000 rw-p 00000000 00:00 0
7ffff7ff8000-7ffff7ffb000 rw-p 00000000 00:00 0
7ffff7ffb000-7ffff7ffc000 r-xp 00000000 00:00 0 [vdso]
7ffff7ffc000-7ffff7ffd000 r--p 00020000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7ffff7ffd000-7ffff7fff000 rw-p 00021000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7ffffffde000-7ffffffff000 rw-p 00000000 00:00 0 [stack]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
64
mapping file - numpages: 64
mapping 256 KB
mapped file at 0x7ffff7ff4000
00400000-00401000 r-xp 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00600000-00601000 r--p 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00601000-00602000 rw-p 00001000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
7ffff7a48000-7ffff7bd2000 r-xp 00000000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7bd2000-7ffff7dd1000 ---p 0018a000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7dd1000-7ffff7dd5000 r--p 00189000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7dd5000-7ffff7dd6000 rw-p 0018d000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7ffff7dd6000-7ffff7ddc000 rw-p 00000000 00:00 0
7ffff7ddc000-7ffff7dfd000 r-xp 00000000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7ffff7fd0000-7ffff7fd3000 rw-p 00000000 00:00 0
7ffff7ff4000-7ffff7ff8000 rw-p 00000000 08:03 3288973 /home/jords/engcode/workspace/SE370Assignment3/64
7ffff7ff8000-7ffff7ffb000 rw-p 00000000 00:00 0
7ffff7ffb000-7ffff7ffc000 r-xp 00000000 00:00 0 [vdso]
7ffff7ffc000-7ffff7ffd000 r--p 00020000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7ffff7ffd000-7ffff7fff000 rw-p 00021000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7ffffffde000-7ffffffff000 rw-p 00000000 00:00 0 [stack]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
Program received signal SIGBUS, Bus error.
0x0000000000400abb in main (argc=2, argv=0x7fffffffe058) at A3Program3.c:49
49 printf("%d", mapped_file[0]);
(gdb)
It's confusing me, since you can clearly see in the maps output that the file has been mapped and the address is correct - but it gives an error whenever I try to access it.
EDIT: Valgrind:
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
==16295==
==16295== Process terminating with default action of signal 7 (SIGBUS)
==16295== Non-existent physical address at address 0x4024000
==16295== at 0x400AB7: main (A3Program3.c:49)
==16295==
Update: So I have stopped it crashing now (thanks :)) with the ftruncate call, but it's printing all zeros:
jords#jords-desktop ~/engcode/workspace/SE370Assignment3 (master) $ ./A3Program3 64
00400000-00401000 r-xp 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00600000-00601000 r--p 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00601000-00602000 rw-p 00001000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
7f96ec7a1000-7f96ec92b000 r-xp 00000000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ec92b000-7f96ecb2a000 ---p 0018a000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ecb2a000-7f96ecb2e000 r--p 00189000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ecb2e000-7f96ecb2f000 rw-p 0018d000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ecb2f000-7f96ecb35000 rw-p 00000000 00:00 0
7f96ecb35000-7f96ecb56000 r-xp 00000000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7f96ecd2a000-7f96ecd2d000 rw-p 00000000 00:00 0
7f96ecd52000-7f96ecd55000 rw-p 00000000 00:00 0
7f96ecd55000-7f96ecd56000 r--p 00020000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7f96ecd56000-7f96ecd58000 rw-p 00021000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7fff9be10000-7fff9be31000 rw-p 00000000 00:00 0 [stack]
7fff9bf0b000-7fff9bf0c000 r-xp 00000000 00:00 0 [vdso]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
64
mapping file - numpages: 64
mapping 256 KB
mapped file at 0x7f96eccea000
00400000-00401000 r-xp 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00600000-00601000 r--p 00000000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
00601000-00602000 rw-p 00001000 08:03 3288976 /home/jords/engcode/workspace/SE370Assignment3/A3Program3
7f96ec7a1000-7f96ec92b000 r-xp 00000000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ec92b000-7f96ecb2a000 ---p 0018a000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ecb2a000-7f96ecb2e000 r--p 00189000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ecb2e000-7f96ecb2f000 rw-p 0018d000 00:10 8103 /lib/x86_64-linux-gnu/libc-2.13.so
7f96ecb2f000-7f96ecb35000 rw-p 00000000 00:00 0
7f96ecb35000-7f96ecb56000 r-xp 00000000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7f96eccea000-7f96ecd2a000 rw-p 00000000 08:03 3288973 /home/jords/engcode/workspace/SE370Assignment3/64
7f96ecd2a000-7f96ecd2d000 rw-p 00000000 00:00 0
7f96ecd52000-7f96ecd55000 rw-p 00000000 00:00 0
7f96ecd55000-7f96ecd56000 r--p 00020000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7f96ecd56000-7f96ecd58000 rw-p 00021000 00:10 8090 /lib/x86_64-linux-gnu/ld-2.13.so
7fff9be10000-7fff9be31000 rw-p 00000000 00:00 0 [stack]
7fff9bf0b000-7fff9bf0c000 r-xp 00000000 00:00 0 [vdso]
ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall]
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
I think this is because the file is not being read correctly, so all I'm reading is padded zeros. But I'm not sure why that would be
Update, worked it out, it was actually reading the file correctly I was just making a mistake in terms of how to read it. Thanks everyone
The problem is that you open the file with O_TRUNC which truncates it, and since mmap can only map the existing contents of a file it will give you a sigbus. Use truncate() (and friends) to truncate the file to the correct size before mapping it.
From mmap's man page:
SIGBUS Attempted access to a portion of the buffer that does not correspond to the file (for example, beyond the end of the file, including the case where another process has truncated the file).
There's a bug, but it won't explain the crash in mapped_file[0].
sysconf(_SC_PAGESIZE) gives you the page size in bytes.
At each iteration of current_pos += page_size you're incrementing your pointer by sysconf(_SC_PAGESIZE)*sizeof(int) so you quickly get outside the mapped region.
Also, the page_size * 4 in mmap looks questionable: surely num_pages ought to come into the equation?

Stack Overflow problem in a recursive program in C

I am getting a stack overflow in one of the recursive functions i am running..
Here is the code..
void* buddyMalloc(int req_size)
{
// Do something here
return buddy_findout(original_index,req_size); // This is the recursive call
}
void *buddy_findout(int current_index,int req_size)
{
char *selected = NULL;
if(front!=NULL)
{
if(current_index==original_index)
{
// Do something here
return selected;
}
else
{
// Do Something here
return buddy_findout(current_index+1,req_size);
}
}
else
{
return buddy_findout(current_index-1,req_size);
}
}
Consider the initial value of index to be 4. and it first do index-1 till it reaches 0 index. and then it comes back to index 4 by incrementing..This is wht i want to implement.
But it gives a stack overflow with memory map in the command prompt :
Here is the output from my shell :
*** glibc detected *** ./473_mem: free(): invalid pointer: 0x00c274c0 ***
======= Backtrace: =========
/lib/tls/i686/cmov/libc.so.6[0xb50ff1]
/lib/tls/i686/cmov/libc.so.6[0xb526f2]
/lib/tls/i686/cmov/libc.so.6(cfree+0x6d)[0xb557cd]
./473_mem[0x8048b44]
./473_mem[0x8048b74]
./473_mem[0x8048b74]
./473_mem[0x8048944]
./473_mem[0x8048c87]
./473_mem[0x8048d31]
./473_mem[0x8048f79]
/lib/tls/i686/cmov/libc.so.6(__libc_start_main+0xe6)[0xafcb56]
./473_mem[0x8048671]
======= Memory map: ========
0017c000-00198000 r-xp 00000000 08:01 5224 /lib/libgcc_s.so.1
00198000-00199000 r--p 0001b000 08:01 5224 /lib/libgcc_s.so.1
00199000-0019a000 rw-p 0001c000 08:01 5224 /lib/libgcc_s.so.1
00260000-00284000 r-xp 00000000 08:01 1927 /lib/tls/i686/cmov/libm-2.10.1.so
00284000-00285000 r--p 00023000 08:01 1927 /lib/tls/i686/cmov/libm-2.10.1.so
00285000-00286000 rw-p 00024000 08:01 1927 /lib/tls/i686/cmov/libm-2.10.1.so
006cd000-006e8000 r-xp 00000000 08:01 6662 /lib/ld-2.10.1.so
006e8000-006e9000 r--p 0001a000 08:01 6662 /lib/ld-2.10.1.so
006e9000-006ea000 rw-p 0001b000 08:01 6662 /lib/ld-2.10.1.so
00aa9000-00aaa000 r-xp 00000000 00:00 0 [vdso]
00ae6000-00c24000 r-xp 00000000 08:01 1900 /lib/tls/i686/cmov/libc-2.10.1.so
00c24000-00c25000 ---p 0013e000 08:01 1900 /lib/tls/i686/cmov/libc-2.10.1.so
00c25000-00c27000 r--p 0013e000 08:01 1900 /lib/tls/i686/cmov/libc-2.10.1.so
00c27000-00c28000 rw-p 00140000 08:01 1900 /lib/tls/i686/cmov/libc-2.10.1.so
00c28000-00c2b000 rw-p 00000000 00:00 0
08048000-0804a000 r-xp 00000000 00:14 2176 /media/windows-share/OS/Project2/473_mem
0804a000-0804b000 r--p 00001000 00:14 2176 /media/windows-share/OS/Project2/473_mem
0804b000-0804c000 rw-p 00002000 00:14 2176 /media/windows-share/OS/Project2/473_mem
08483000-084a4000 rw-p 00000000 00:00 0 [heap]
b7600000-b7621000 rw-p 00000000 00:00 0
b7621000-b7700000 ---p 00000000 00:00 0
b7716000-b7819000 rw-p 00000000 00:00 0
b7827000-b782a000 rw-p 00000000 00:00 0
bfb96000-bfbab000 rw-p 00000000 00:00 0 [stack]
Aborted
Thanks in advance
adi
Look at your compiler docs to see if it has "tail recursion" optimization.
(Though now your stack overflow problem becomes an infinite loop problem!)
gcc -foptimize-sibling-calls ...
Where is front set?
In call:
else
{
return buddy_findout(current_index-1,req_size);
}
}
When front is NULL You just come back to same function with smaller current_index and keep looping and looping. There's no stop condition for current_index == 0

Resources