1 #include <stdio.h>
2 #include <string.h>
3 #include <sys/stat.h>
4 #include <unistd.h>
5
6 #include <OS.h>
7
8 const char* kInitialValue = "/dev/null";
9 const char* kChangedValue = "Argh!";
10
11 int
main(int argc,const char * const * argv)12 main(int argc, const char* const* argv)
13 {
14 thread_id parent = find_thread(NULL);
15
16 char* globalVar = NULL;
17 area_id area = create_area("cow test", (void**)&globalVar,
18 B_ANY_ADDRESS, B_PAGE_SIZE, B_NO_LOCK, B_READ_AREA | B_WRITE_AREA);
19 if (area < 0) {
20 printf("failed to create area\n");
21 return 1;
22 }
23
24 strcpy(globalVar, kInitialValue);
25
26 printf("[%ld] parent: before fork(): globalVar(%p): \"%s\"\n", parent,
27 globalVar, globalVar);
28
29 pid_t child = fork();
30 if (child == 0) {
31 // child
32 child = find_thread(NULL);
33
34 // let the kernel read access the page
35 struct stat st;
36 stat(globalVar, &st);
37
38 printf("[%ld] child: after kernel read: globalVar: \"%s\"\n",
39 child, globalVar);
40
41 // write access the page from userland
42 strcpy(globalVar, kChangedValue);
43
44 printf("[%ld] child: after change: globalVar: \"%s\"\n", child,
45 globalVar);
46
47 } else {
48 // parent
49
50 // wait for the child
51 status_t exitVal;
52 while (wait_for_thread(child, &exitVal) == B_INTERRUPTED);
53
54 // check the value
55 printf("[%ld] parent: after exit child: globalVar: \"%s\"\n",
56 parent, globalVar);
57
58 if (strcmp(globalVar, kInitialValue) == 0)
59 printf("test OK\n");
60 else
61 printf("test FAILED: child process changed parent's memory!\n");
62 }
63
64 return 0;
65 }
66