今回は、自作CPUのLiteX SoC環境に、demoアプリではない自分で作ったアプリを入れてみよう。
アプリといっても、単純にメモリへの読み書きをしてみるだけのテストだ。
memcpy()
とmemset()
というメモリへの書き込みを行うだけのテストを作ってみた。
static void console_service(void) { char *str; char *token; str = readstr(); if(str == NULL) return; token = get_token(&str); if(strcmp(token, "help") == 0) help(); else if(strcmp(token, "reboot") == 0) reboot_cmd(); else if(strcmp(token, "memset") == 0) memset_test(); else if(strcmp(token, "memcpy") == 0) memcpy_test(); prompt(); }
memcpy()
とmemset()
の本体だ。サイズは256Bへの書き込みと、128Bのmemcpy()
だ。
#define DATA_SIZE 2*1024 uint64_t data_origin[DATA_SIZE / sizeof(uint64_t)]; void memset_test(void); void memset_test(void) { long long start_cycle; long long end_cycle; asm volatile ("csrr %0, cycle":"=r"(start_cycle)); for (int i = 0; i < DATA_SIZE / sizeof(uint64_t); i++) { data_origin[i] = i; } asm volatile ("csrr %0, cycle":"=r"(end_cycle)); printf("Start = %lld, End = %lld, Cycle = %lld\n", start_cycle, end_cycle, end_cycle - start_cycle); return; } void memcpy_test(void); void memcpy_test(void) { long long start_cycle; long long end_cycle; asm volatile ("csrr %0, cycle":"=r"(start_cycle)); for (int i = 0; i < DATA_SIZE / sizeof(uint64_t) / 2; i++) { data_origin[i] = data_origin[DATA_SIZE / sizeof(uint64_t) / 2 + i]; } asm volatile ("csrr %0, cycle":"=r"(end_cycle)); printf("Start = %lld, End = %lld, Cycle = %lld\n", start_cycle, end_cycle, end_cycle - start_cycle); return; }
一応動かしてみた。が、かなりメモリアクセスが遅いなあ。AXIの部分をかなり適当に作っているから、それで遅くなっているのかもしれない...
LiteX minimal demo app built May 1 2023 23:06:43 Available commands: help - Show this command reboot - Reboot CPU memset - Execute memset_test memcpy - Execute memset_test litex-demo-app> memset Start = 113901, End = 117335, Cycle = 3434 litex-demo-app> memcpy Start = 173062, End = 175936, Cycle = 2874 litex-demo-app> memset Start = 313627, End = 317065, Cycle = 3438 litex-demo-app> memset Start = 421478, End = 424917, Cycle = 3439 litex-demo-app> memcpy Start = 509440, End = 512284, Cycle = 2844 litex-demo-app>