ram.cpp 3.5 KB
Newer Older
Z
Zihao Yu 已提交
1 2
#include "common.h"

L
Lingrui98 已提交
3
#define RAMSIZE (256 * 1024 * 1024)
Z
Zihao Yu 已提交
4

5
static uint64_t ram[RAMSIZE / sizeof(uint64_t)];
Z
Zihao Yu 已提交
6
static long img_size = 0;
7
void* get_img_start() { return &ram[0]; }
Z
Zihao Yu 已提交
8
long get_img_size() { return img_size; }
Z
Zihao Yu 已提交
9 10
void* get_ram_start() { return &ram[0]; }
long get_ram_size() { return RAMSIZE; }
Z
Zihao Yu 已提交
11

12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
void addpageSv39() {
//three layers
//addr range: 0x0000000080000000 - 0x0000000088000000 for 128MB from 2GB - 2GB128MB
//the first layer: one entry for 1GB. (512GB in total by 512 entries). need the 2th entries
//the second layer: one entry for 2MB. (1GB in total by 512 entries). need the 0th-63rd entries
//the third layer: one entry for 4KB (2MB in total by 512 entries). need 64 with each one all  

#define PAGESIZE (4 * 1024)  // 4KB = 2^12B
#define ENTRYNUM (PAGESIZE / 8) //512 2^9
#define PTEVOLUME (PAGESIZE * ENTRYNUM) // 2MB
#define PTENUM (RAMSIZE / PTEVOLUME) // 128MB / 2MB = 64
#define PDDENUM 1
#define PDENUM 1
#define PDDEADDR (0x88000000 - (PAGESIZE * (PTENUM + 2))) //0x88000000 - 0x1000*66
#define PDEADDR (0x88000000 - (PAGESIZE * (PTENUM + 1))) //0x88000000 - 0x1000*65
#define PTEADDR(i) (0x88000000 - (PAGESIZE * PTENUM) + (PAGESIZE * i)) //0x88000000 - 0x100*64
28 29
#define PTEMMIONUM 128
#define PDEMMIONUM 1
30 31 32 33 34

  uint64_t pdde[ENTRYNUM];
  uint64_t pde[ENTRYNUM];
  uint64_t pte[PTENUM][ENTRYNUM];
  
35
  //special addr for mmio 0x40000000 - 0x4fffffff
36
  uint64_t pdemmio[ENTRYNUM];
37 38
  uint64_t ptemmio[PTEMMIONUM][ENTRYNUM];
  
Z
zhangzifei 已提交
39
  pdde[1] = (((PDDEADDR-PAGESIZE*1) & 0xfffff000) >> 2) | 0x1;
40

41
  for(int i = 0; i < PTEMMIONUM; i++) {
Z
zhangzifei 已提交
42
    pdemmio[i] = (((PDDEADDR-PAGESIZE*(PTEMMIONUM+PDEMMIONUM-i)) & 0xfffff000) >> 2) | 0x1;
43 44 45 46
  }
  
  for(int outidx = 0; outidx < PTEMMIONUM; outidx++) {
    for(int inidx = 0; inidx < ENTRYNUM; inidx++) {
47
      ptemmio[outidx][inidx] = (((0x40000000 + outidx*PTEVOLUME + inidx*PAGESIZE) & 0xfffff000) >> 2) | 0xf;
48 49 50 51
    }
  }
  
  //0x800000000 - 0x87ffffff
Z
zhangzifei 已提交
52 53 54
  pdde[2] = ((PDEADDR & 0xfffff000) >> 2) | 0x1;
  //pdde[2] = ((0x80000000&0xc0000000) >> 2) | 0xf;

55
  for(int i = 0; i < PTENUM ;i++) {
Z
zhangzifei 已提交
56 57
    pde[i] = ((PTEADDR(i)&0xfffff000)>>2) | 0x1;
    //pde[i] = (((0x8000000+i*2*1024*1024)&0xffe00000)>>2) | 0xf;
58 59 60 61
  }

  for(int outidx = 0; outidx < PTENUM; outidx++ ) {
    for(int inidx = 0; inidx < ENTRYNUM; inidx++ ) {
62
      pte[outidx][inidx] = (((0x80000000 + outidx*PTEVOLUME + inidx*PAGESIZE) & 0xfffff000)>>2) | 0xf;
63 64
    }
  }
65 66 67

  memcpy((char *)ram+(RAMSIZE-PAGESIZE*(PTENUM+PDDENUM+PDENUM+PDEMMIONUM+PTEMMIONUM)),ptemmio, PAGESIZE*PTEMMIONUM);
  memcpy((char *)ram+(RAMSIZE-PAGESIZE*(PTENUM+PDDENUM+PDENUM+PDEMMIONUM)), pdemmio, PAGESIZE*PDEMMIONUM);
68 69 70 71
  memcpy((char *)ram+(RAMSIZE-PAGESIZE*(PTENUM+PDDENUM+PDENUM)), pdde, PAGESIZE*PDDENUM);
  memcpy((char *)ram+(RAMSIZE-PAGESIZE*(PTENUM+PDENUM)), pde, PAGESIZE*PDENUM);
  memcpy((char *)ram+(RAMSIZE-PAGESIZE*PTENUM), pte, PAGESIZE*PTENUM);
}
Z
zhangzifei 已提交
72

Z
Zihao Yu 已提交
73
void init_ram(const char *img) {
Z
Zihao Yu 已提交
74 75 76 77 78 79 80 81 82 83 84 85 86
  assert(img != NULL);
  FILE *fp = fopen(img, "rb");
  if (fp == NULL) {
    printf("Can not open '%s'\n", img);
    assert(0);
  }

  printf("The image is %s\n", img);

  fseek(fp, 0, SEEK_END);
  img_size = ftell(fp);

  fseek(fp, 0, SEEK_SET);
87
  int ret = fread(ram, img_size, 1, fp);
Z
Zihao Yu 已提交
88 89
  assert(ret == 1);
  fclose(fp);
Z
Zihao Yu 已提交
90

Z
zhangzifei 已提交
91
  //new add
92
  addpageSv39();
Z
zhangzifei 已提交
93
  //new end
Z
Zihao Yu 已提交
94 95 96
}

extern "C" void ram_helper(
97
    uint64_t rIdx, uint64_t *rdata, uint64_t wIdx, uint64_t wdata, uint64_t wmask, uint8_t wen) {
98
  assert(rIdx < RAMSIZE / sizeof(uint64_t));
Z
Zihao Yu 已提交
99
  *rdata = ram[rIdx];
100 101 102 103
  if (wen) {
    assert(wIdx < RAMSIZE / sizeof(uint64_t));
    ram[wIdx] = (ram[wIdx] & ~wmask) | (wdata & wmask);
  }
Z
Zihao Yu 已提交
104
}