ひでみのアイデア帳

くだらないことなんだけど、忘れないために・・・

SystemVerilogお勉強(6)

まぁ、やりたいことはこれだよなぁ→本番アプリを動かしてみる

前回のお勉強のはただ、メモリを叩けるだけだよね。

それだと面白くない。

本番アプリを動かせるくらいにはしたいよねぇ〜。

Linuxだと、ドライバ経由でmmapするのは面倒だとしても直接/dev/memを開くようなアプリだとあっさりと作れそうだなぁ。

次の部分をエミュレートしちゃえばいいんのかなぁ〜。

unsigned int *addr;
fd = open("/dev/mem", O_RDWR | O_SYNC );
addr = mmap( NULL, MAP_LENG, PROT_READ | PROT_WRITE, MAP_SHARED, fd, offset & 0xFFFF0000);
printf("%08x\n", addr[0]);
addr[1] = 0x12335678;
munmap(addr, MAP_LENG);
clode(fd);

あぁ、でも、/dev/dpiとか作ったとしても、addrでアクセスする部分をエミュレートするのは難しそうだなぁ。

ここはテスト用と本番用のコードを作るほうが良さげかな?

ってことは・・・

mmapを単純にmallocに置き換えて、write/readはmem_wrte/mem_readでデータをZynqのDDRに入れるようにする・・・

それだけでいいのかな?

SystemVerilogソース

  reg [31:0] data;
  reg [31:0] addr;
  reg MemWriteEnable = 0;
  function int svMemWrite(input int _addr, input int _data) ;
    data = _data;
    addr = _addr;
    MemWriteEnable = 1;
    return  0;
  endfunction

  always begin
    wait(MemWriteEnable == 1);
    tb.zynq_sys.design_1_i.processing_system7_0.inst.write_mem(data, addr, 4);
    MemWriteEnable = 0;
  end

Cソース

void mem_write(unsigned int addr, unsigned int *data, int leng){
  for(i=0; i<leng; i++){
    svMemWrite(addr+i*4, data[i]);
  }
}

unsigned int data = 0xDEADBEEF;
mem_write(0x10000000, &data, 1);

これなら本番アプリを少し修正するだけで使えそうだなぁ。

試してないし、環境を整えるのは面倒なので勉強会での課題にしよう。