mem.c (1608B)
1 #include <stdlib.h> 2 #include <stdio.h> 3 #include <string.h> 4 5 #include "cell.h" 6 #include "bus.h" 7 #include "mem.h" 8 9 Mem * 10 createmem(Bus *bus) 11 { 12 Mem *new = calloc(sizeof(Mem), 1); 13 new->bus = bus; 14 return new; 15 } 16 17 int 18 memstep(void *v) 19 { 20 Mem *mem = (Mem *)v; 21 Msg *ret, *msg = buspull(mem->bus, ChMem); 22 Cell *ram, *cell; 23 24 if (msg == NULL) return 1; 25 26 if ((msg->dat == NULL) 27 || (msg->dat->n < sizeof(MemCmd))) { 28 freemsg(msg); 29 fprintf(stderr, "mem: cmd too short\n"); 30 return 0; 31 } 32 MemCmd *cmd = (MemCmd *)msg->dat->p; 33 if ((cmd->addr < 0) || (cmd->addr >= MaxRAM)) { 34 fprintf(stderr, "mem: invalid addr: %x\n", 35 cmd->addr); 36 } else switch (cmd->op) { 37 case '!': //fetch 38 ram = &mem->ram[cmd->addr]; 39 cell = celldup(ram); 40 ret = createmsg(ChMem, msg->src, cell); 41 buspush(mem->bus, ret); 42 break; 43 case '@': //store 44 ram = &mem->ram[cmd->addr]; 45 ram->n = msg->dat->n - sizeof(MemCmd); 46 ram->p = realloc(ram->p, ram->n); 47 memcpy(ram->p, msg->dat->p + sizeof(MemCmd), 48 ram->n); 49 break; 50 default: 51 fprintf(stderr, "mem: invalid op: %c\n", cmd->op); 52 } 53 freemsg(msg); 54 return 0; 55 } 56 57 void 58 memfetch(int src, Mem *mem, int n) 59 { 60 MemCmd *f = malloc(sizeof(MemCmd)); 61 f->op = '!'; 62 f->addr = n; 63 Cell *c = createcell(sizeof(MemCmd), f); 64 Msg *msg = createmsg(src, ChMem, c); 65 buspush(mem->bus, msg); 66 } 67 68 void 69 memstore(int src, Mem *mem, int n, Cell *c) 70 { 71 MemCmd *s = malloc(sizeof(MemCmd) + c->n); 72 s->op = '@'; 73 s->addr = n; 74 memcpy((char *)s + sizeof(MemCmd), c->p, c->n); 75 Cell *cell = createcell(sizeof(MemCmd) + c->n, s); 76 Msg *msg = createmsg(src, ChMem, cell); 77 buspush(mem->bus, msg); 78 } 79