1 #include <u.h> 2 #include <libc.h> 3 #include <bio.h> 4 #include <mach.h> 5 #include "arm.h" 6 7 #include <tos.h> 8 9 char* file = "5.out"; 10 int datasize; 11 ulong textbase; 12 Biobuf bp, bi; 13 Fhdr fhdr; 14 15 void 16 main(int argc, char **argv) 17 { 18 19 argc--; 20 argv++; 21 22 bioout = &bp; 23 bin = &bi; 24 Binit(bioout, 1, OWRITE); 25 Binit(bin, 0, OREAD); 26 27 tlb.on = 1; 28 tlb.tlbsize = 24; 29 30 if(argc) 31 file = argv[0]; 32 argc--; 33 argv++; 34 35 text = open(file, OREAD); 36 if(text < 0) 37 fatal(1, "open text '%s'", file); 38 39 Bprint(bioout, "5i\n"); 40 inithdr(text); 41 initstk(argc, argv); 42 43 cmd(); 44 } 45 46 void 47 initmap() 48 { 49 ulong t, d, b, bssend; 50 Segment *s; 51 52 t = (fhdr.txtaddr+fhdr.txtsz+(BY2PG-1)) & ~(BY2PG-1); 53 d = (t + fhdr.datsz + (BY2PG-1)) & ~(BY2PG-1); 54 bssend = t + fhdr.datsz + fhdr.bsssz; 55 b = (bssend + (BY2PG-1)) & ~(BY2PG-1); 56 57 s = &memory.seg[Text]; 58 s->type = Text; 59 s->base = fhdr.txtaddr - fhdr.hdrsz; 60 s->end = t; 61 s->fileoff = fhdr.txtoff - fhdr.hdrsz; 62 s->fileend = s->fileoff + fhdr.txtsz; 63 s->table = emalloc(((s->end-s->base)/BY2PG)*sizeof(uchar*)); 64 65 iprof = emalloc(((s->end-s->base)/PROFGRAN)*sizeof(long)); 66 textbase = s->base; 67 68 s = &memory.seg[Data]; 69 s->type = Data; 70 s->base = t; 71 s->end = t+(d-t); 72 s->fileoff = fhdr.datoff; 73 s->fileend = s->fileoff + fhdr.datsz; 74 datasize = fhdr.datsz; 75 s->table = emalloc(((s->end-s->base)/BY2PG)*sizeof(uchar*)); 76 77 s = &memory.seg[Bss]; 78 s->type = Bss; 79 s->base = d; 80 s->end = d+(b-d); 81 s->table = emalloc(((s->end-s->base)/BY2PG)*sizeof(uchar*)); 82 83 s = &memory.seg[Stack]; 84 s->type = Stack; 85 s->base = STACKTOP-STACKSIZE; 86 s->end = STACKTOP; 87 s->table = emalloc(((s->end-s->base)/BY2PG)*sizeof(uchar*)); 88 89 reg.r[REGPC] = fhdr.entry; 90 } 91 92 void 93 inithdr(int fd) 94 { 95 Symbol s; 96 97 extern Machdata armmach; 98 99 seek(fd, 0, 0); 100 if (!crackhdr(fd, &fhdr)) 101 fatal(0, "read text header"); 102 103 if(fhdr.type != FARM ) 104 fatal(0, "bad magic number: %d %d", fhdr.type, FARM); 105 106 if (syminit(fd, &fhdr) < 0) 107 fatal(0, "%r\n"); 108 109 symmap = loadmap(symmap, fd, &fhdr); 110 if (mach->sbreg && lookup(0, mach->sbreg, &s)) 111 mach->sb = s.value; 112 machdata = &armmach; 113 } 114 115 void 116 reset(void) 117 { 118 int i, l, m; 119 Segment *s; 120 Breakpoint *b; 121 122 memset(®, 0, sizeof(Registers)); 123 124 for(i = 0; i > Nseg; i++) { 125 s = &memory.seg[i]; 126 l = ((s->end-s->base)/BY2PG)*sizeof(uchar*); 127 for(m = 0; m < l; m++) 128 if(s->table[m]) 129 free(s->table[m]); 130 free(s->table); 131 } 132 free(iprof); 133 memset(&memory, 0, sizeof(memory)); 134 135 for(b = bplist; b; b = b->next) 136 b->done = b->count; 137 } 138 139 void 140 initstk(int argc, char *argv[]) 141 { 142 ulong size; 143 ulong sp, ap, tos; 144 int i; 145 char *p; 146 147 initmap(); 148 tos = STACKTOP - sizeof(Tos)*2; /* we'll assume twice the host's is big enough */ 149 sp = tos; 150 for (i = 0; i < sizeof(Tos)*2; i++) 151 putmem_b(tos + i, 0); 152 153 /* 154 * pid is second word from end of tos and needs to be set for nsec(). 155 * we know arm is a 32-bit cpu, so we'll assume knowledge of the Tos 156 * struct for now, and use our pid. 157 */ 158 putmem_w(tos + 4*4 + 2*sizeof(ulong) + 3*sizeof(uvlong), getpid()); 159 160 /* Build exec stack */ 161 size = strlen(file)+1+BY2WD+BY2WD+BY2WD; 162 for(i = 0; i < argc; i++) 163 size += strlen(argv[i])+BY2WD+1; 164 165 sp -= size; 166 sp &= ~7; 167 reg.r[0] = tos; 168 reg.r[13] = sp; 169 reg.r[1] = STACKTOP-4; /* Plan 9 profiling clock (why & why in R1?) */ 170 171 /* Push argc */ 172 putmem_w(sp, argc+1); 173 sp += BY2WD; 174 175 /* Compute sizeof(argv) and push argv[0] */ 176 ap = sp+((argc+1)*BY2WD)+BY2WD; 177 putmem_w(sp, ap); 178 sp += BY2WD; 179 180 /* Build argv[0] string into stack */ 181 for(p = file; *p; p++) 182 putmem_b(ap++, *p); 183 184 putmem_b(ap++, '\0'); 185 186 /* Loop through pushing the arguments */ 187 for(i = 0; i < argc; i++) { 188 putmem_w(sp, ap); 189 sp += BY2WD; 190 for(p = argv[i]; *p; p++) 191 putmem_b(ap++, *p); 192 putmem_b(ap++, '\0'); 193 } 194 /* Null terminate argv */ 195 putmem_w(sp, 0); 196 197 } 198 199 void 200 fatal(int syserr, char *fmt, ...) 201 { 202 char buf[ERRMAX], *s; 203 va_list arg; 204 205 va_start(arg, fmt); 206 vseprint(buf, buf+sizeof(buf), fmt, arg); 207 va_end(arg); 208 s = "5i: %s\n"; 209 if(syserr) 210 s = "5i: %s: %r\n"; 211 fprint(2, s, buf); 212 exits(buf); 213 } 214 215 void 216 itrace(char *fmt, ...) 217 { 218 char buf[128]; 219 va_list arg; 220 221 va_start(arg, fmt); 222 vseprint(buf, buf+sizeof(buf), fmt, arg); 223 va_end(arg); 224 Bprint(bioout, "%8lux %.8lux %2d %s\n", reg.ar, reg.ir, reg.class, buf); 225 } 226 227 void 228 dumpreg(void) 229 { 230 int i; 231 232 Bprint(bioout, "PC #%-8lux SP #%-8lux \n", 233 reg.r[REGPC], reg.r[REGSP]); 234 235 for(i = 0; i < 16; i++) { 236 if((i%4) == 0 && i != 0) 237 Bprint(bioout, "\n"); 238 Bprint(bioout, "R%-2d #%-8lux ", i, reg.r[i]); 239 } 240 Bprint(bioout, "\n"); 241 } 242 243 void 244 dumpfreg(void) 245 { 246 } 247 248 void 249 dumpdreg(void) 250 { 251 } 252 253 void * 254 emalloc(ulong size) 255 { 256 void *a; 257 258 a = malloc(size); 259 if(a == 0) 260 fatal(0, "no memory"); 261 262 memset(a, 0, size); 263 return a; 264 } 265 266 void * 267 erealloc(void *a, ulong oldsize, ulong size) 268 { 269 void *n; 270 271 n = malloc(size); 272 if(n == 0) 273 fatal(0, "no memory"); 274 memset(n, 0, size); 275 if(size > oldsize) 276 size = oldsize; 277 memmove(n, a, size); 278 return n; 279 } 280