1
2
3
4
5
6
7
8
9
10#define SYS_WRITE0 0x04
11#define SYS_HEAPINFO 0x16
12#define SYS_REPORTEXC 0x18
13
14#include <stdint.h>
15#include <stdlib.h>
16#include <stdio.h>
17#include <string.h>
18#include "semicall.h"
19
20int main(int argc, char *argv[argc])
21{
22#if UINTPTR_MAX == UINT32_MAX
23 uintptr_t exit_code = 0x20026;
24#else
25 uintptr_t exit_block[2] = {0x20026, 0};
26 uintptr_t exit_code = (uintptr_t) &exit_block;
27#endif
28 struct {
29 void *heap_base;
30 void *heap_limit;
31 void *stack_base;
32 void *stack_limit;
33 } info;
34 void *ptr_to_info = (void *) &info;
35
36 __semi_call(SYS_WRITE0, (uintptr_t) "Checking HeapInfo\n");
37
38 memset(&info, 0, sizeof(info));
39 __semi_call(SYS_HEAPINFO, (uintptr_t) &ptr_to_info);
40
41 if (info.heap_base == NULL || info.heap_limit == NULL) {
42 printf("null heap: %p -> %p\n", info.heap_base, info.heap_limit);
43 exit(1);
44 }
45
46
47 if ((uintptr_t) info.heap_base >= (uintptr_t) info.heap_limit) {
48 printf("heap base %p >= heap_limit %p\n",
49 info.heap_base, info.heap_limit);
50 exit(2);
51 }
52
53 if (info.stack_base == NULL || info.stack_limit) {
54 printf("null stack: %p -> %p\n", info.stack_base, info.stack_limit);
55 exit(3);
56 }
57
58
59 if (ptr_to_info > info.stack_base) {
60 printf("info appears to be above stack: %p > %p\n", ptr_to_info,
61 info.stack_base);
62 exit(4);
63 } else if (ptr_to_info < info.stack_limit) {
64 printf("info appears to be outside stack: %p < %p\n", ptr_to_info,
65 info.stack_limit);
66 exit(5);
67 }
68
69 if (ptr_to_info > info.heap_base && ptr_to_info < info.heap_limit) {
70 printf("info appears to be inside the heap: %p in %p:%p\n",
71 ptr_to_info, info.heap_base, info.heap_limit);
72 exit(6);
73 }
74
75 printf("heap: %p -> %p\n", info.heap_base, info.heap_limit);
76 printf("stack: %p -> %p\n", info.stack_base, info.stack_limit);
77
78 __semi_call(SYS_WRITE0, (uintptr_t) "Passed HeapInfo checks");
79 __semi_call(SYS_REPORTEXC, exit_code);
80
81 return -1;
82}
83