Parlib and other user libs are built with -fPIC
[akaros.git] / tests / vmmcp.c
1 #include <stdio.h> 
2 #include <pthread.h>
3 #include <sys/types.h>
4 #include <sys/stat.h>
5 #include <fcntl.h>
6 #include <arch/arch.h>
7 #include <unistd.h>
8 #include <errno.h>
9 #include <dirent.h>
10 #include <stdlib.h>
11 #include <string.h>
12 #include <ros/syscall.h>
13 #include <sys/mman.h>
14
15 int *mmap_blob;
16 unsigned long long stack[1024];
17 volatile int shared = 0;
18 int mcp = 1;
19 #define V(x, t) (*((volatile t*)(x)))
20
21 static void *fail(void*arg)
22 {
23
24         *mmap_blob = 1337;
25         if (mcp)
26         while (V(&shared, int) < 31) {
27                 if (! (V(&shared, int) & 1))
28                         V(&shared, int) = V(&shared, int) + 1;
29 //              cpu_relax();
30         }
31         V(&shared, int) = 55;
32
33         __asm__ __volatile__("vmcall\n");
34         __asm__ __volatile__("mov $0xdeadbeef, %rbx; mov 5, %rax\n");   
35 }
36
37 unsigned long long *p512, *p1, *p2m;
38
39 void *talk_thread(void *arg)
40 {
41         printf("talk thread ..\n");
42         for(; V(&shared, int) < 32; ){
43                 if (V(&shared, int) & 1) {
44                         printf("shared %d\n", V(&shared, int) );
45                         V(&shared, int) = V(&shared, int) + 1;
46                 }
47                 cpu_relax();
48         }
49         printf("All done, read %d\n", *mmap_blob);
50         return NULL;
51 }
52
53 pthread_t *my_threads;
54 void **my_retvals;
55 int nr_threads = 2;
56
57 int main(int argc, char **argv)
58 {
59         int nr_gpcs = 1;
60         int fd = open("#c/sysctl", O_RDWR), ret;
61         void * x;
62         static char cmd[512];
63         if (fd < 0) {
64                 perror("#c/sysctl");
65                 exit(1);
66         }
67         if (ros_syscall(SYS_setup_vmm, nr_gpcs, 0, 0, 0, 0, 0) != nr_gpcs) {
68                 perror("Guest pcore setup failed");
69                 exit(1);
70         }
71         /* blob that is faulted in from the EPT first.  we need this to be in low
72          * memory (not above the normal mmap_break), so the EPT can look it up.
73          * Note that we won't get 4096.  The min is 1MB now, and ld is there. */
74         mmap_blob = mmap((int*)4096, PGSIZE, PROT_READ | PROT_WRITE,
75                          MAP_ANONYMOUS, -1, 0);
76         if (mmap_blob == MAP_FAILED) {
77                 perror("Unable to mmap");
78                 exit(1);
79         }
80
81         mcp = 1; //argc - 1;
82         if (mcp) {
83                 my_threads = malloc(sizeof(pthread_t) * nr_threads);
84                 my_retvals = malloc(sizeof(void*) * nr_threads);
85                 if (!(my_retvals && my_threads))
86                         perror("Init threads/malloc");
87
88                 pthread_can_vcore_request(FALSE);       /* 2LS won't manage vcores */
89                 pthread_need_tls(FALSE);
90                 pthread_lib_init();                                     /* gives us one vcore */
91                 vcore_request(nr_threads - 1);          /* ghetto incremental interface */
92                 for (int i = 0; i < nr_threads; i++) {
93                         x = __procinfo.vcoremap;
94                         printf("%p\n", __procinfo.vcoremap);
95                         printf("Vcore %d mapped to pcore %d\n", i,
96                                 __procinfo.vcoremap[i].pcoreid);
97                 }
98         }
99
100         if (mcp) {
101                 if (pthread_create(&my_threads[0], NULL, &talk_thread, NULL))
102                         perror("pth_create failed");
103 //              if (pthread_create(&my_threads[1], NULL, &fail, NULL))
104 //                      perror("pth_create failed");
105         }
106         printf("threads started\n");
107
108         if (0) for (int i = 0; i < nr_threads-1; i++) {
109                 int ret;
110                 if (pthread_join(my_threads[i], &my_retvals[i]))
111                         perror("pth_join failed");
112                 printf("%d %d\n", i, ret);
113         }
114         
115
116         ret = syscall(33, 1);
117         if (ret < 0) {
118                 perror("vm setup");
119                 exit(1);
120         }
121         ret = posix_memalign((void **)&p512, 4096, 3*4096);
122         if (ret) {
123                 perror("ptp alloc");
124                 exit(1);
125         }
126         p1 = &p512[512];
127         p2m = &p512[1024];
128         p512[0] = (unsigned long long)p1 | 7;
129         p1[0] = /*0x87; */(unsigned long long)p2m | 7;
130         p2m[0] = 0x87;
131         p2m[1] = 0x200000 | 0x87;
132         p2m[2] = 0x400000 | 0x87;
133         p2m[3] = 0x600000 | 0x87;
134
135         printf("p512 %p p512[0] is 0x%lx p1 %p p1[0] is 0x%x\n", p512, p512[0], p1, p1[0]);
136         sprintf(cmd, "V 0x%x 0x%x 0x%x", (unsigned long long)fail, (unsigned long long) &stack[1024], (unsigned long long) p512);
137         printf("Writing command :%s:\n", cmd);
138         ret = write(fd, cmd, strlen(cmd));
139         if (ret != strlen(cmd)) {
140                 perror(cmd);
141         }
142         printf("shared is %d, blob is %d\n", shared, *mmap_blob);
143
144         return 0;
145 }