fix multi-tracker block device

This commit is contained in:
Howard Mao
2017-06-23 22:50:54 -07:00
parent 2b773a2e51
commit 31f5fc98e4
5 changed files with 68 additions and 35 deletions

View File

@@ -4,6 +4,18 @@ import config.{Parameters, Config}
import example.DefaultExampleConfig import example.DefaultExampleConfig
import testchipip.{WithBlockDevice, WithNBlockDeviceTrackers} import testchipip.{WithBlockDevice, WithNBlockDeviceTrackers}
class WithSimBlockDevice extends Config((site, here, up) => {
case UseSimBlockDevice => true
})
class WithBlockDeviceModel extends Config((site, here, up) => {
case UseSimBlockDevice => false
})
class BlockDeviceConfig extends Config( class BlockDeviceConfig extends Config(
new WithSimBlockDevice ++
new WithBlockDevice ++ new WithBlockDevice ++
new DefaultExampleConfig) new DefaultExampleConfig)
class WithTwoTrackers extends WithNBlockDeviceTrackers(2)
class WithFourTrackers extends WithNBlockDeviceTrackers(4)

View File

@@ -2,10 +2,12 @@ package blkdev
import diplomacy.LazyModule import diplomacy.LazyModule
import chisel3._ import chisel3._
import config.Parameters import config.{Parameters, Field}
import testchipip.GeneratorApp import testchipip.GeneratorApp
import example._ import example._
case object UseSimBlockDevice extends Field[Boolean]
class TestHarness(implicit p: Parameters) extends Module { class TestHarness(implicit p: Parameters) extends Module {
val io = IO(new Bundle { val io = IO(new Bundle {
val success = Output(Bool()) val success = Output(Bool())
@@ -13,7 +15,10 @@ class TestHarness(implicit p: Parameters) extends Module {
val dut = Module(LazyModule(new ExampleTopWithBlockDevice).module) val dut = Module(LazyModule(new ExampleTopWithBlockDevice).module)
dut.connectSimAXIMem() dut.connectSimAXIMem()
dut.connectSimBlockDevice() if (p(UseSimBlockDevice))
dut.connectSimBlockDevice()
else
dut.connectBlockDeviceModel()
io.success := dut.connectSimSerial() io.success := dut.connectSimSerial()
} }

View File

@@ -1,6 +1,6 @@
GCC=riscv64-unknown-elf-gcc GCC=riscv64-unknown-elf-gcc
OBJDUMP=riscv64-unknown-elf-objdump OBJDUMP=riscv64-unknown-elf-objdump
CFLAGS=-mcmodel=medany -std=gnu99 -O2 -fno-common -fno-builtin-printf CFLAGS=-mcmodel=medany -std=gnu99 -O2 -fno-common -fno-builtin-printf -Wall
LDFLAGS=-static -nostdlib -nostartfiles -lgcc LDFLAGS=-static -nostdlib -nostartfiles -lgcc
PROGRAMS = pwm blkdev accum charcount PROGRAMS = pwm blkdev accum charcount

View File

@@ -27,42 +27,65 @@ size_t blkdev_max_req_len(void)
return read_reg(BLKDEV_MAX_REQUEST_LENGTH); return read_reg(BLKDEV_MAX_REQUEST_LENGTH);
} }
int blkdev_read(void *addr, unsigned long offset, size_t nsectors) void blkdev_read(void *addr, unsigned long offset, size_t nsectors)
{ {
int req_tag, resp_tag; int req_tag, resp_tag, ntags, i;
size_t nsectors_per_tag;
write_reg(BLKDEV_ADDR, (unsigned long) addr); ntags = read_reg(BLKDEV_NREQUEST);
write_reg(BLKDEV_OFFSET, offset); nsectors_per_tag = nsectors / ntags;
write_reg(BLKDEV_LEN, nsectors);
write_reg(BLKDEV_WRITE, 0);
while (read_reg(BLKDEV_NREQUEST) == 0); printf("sending %d reads\n", ntags);
req_tag = read_reg(BLKDEV_REQUEST);
while (read_reg(BLKDEV_NCOMPLETE) == 0); for (i = 0; i < ntags; i++) {
write_reg(BLKDEV_ADDR, (unsigned long) addr);
write_reg(BLKDEV_OFFSET, offset);
write_reg(BLKDEV_LEN, nsectors_per_tag);
write_reg(BLKDEV_WRITE, 0);
resp_tag = read_reg(BLKDEV_COMPLETE); req_tag = read_reg(BLKDEV_REQUEST);
return (resp_tag == req_tag) ? 0 : -1; addr += (nsectors_per_tag << BLKDEV_SECTOR_SHIFT);
offset += nsectors_per_tag;
}
while (read_reg(BLKDEV_NCOMPLETE) < ntags);
for (i = 0; i < ntags; i++) {
resp_tag = read_reg(BLKDEV_COMPLETE);
printf("completed read %d\n", resp_tag);
}
} }
int blkdev_write(unsigned long offset, void *addr, size_t nsectors) void blkdev_write(unsigned long offset, void *addr, size_t nsectors)
{ {
int req_tag, resp_tag; int req_tag, resp_tag, ntags, i;
size_t nsectors_per_tag;
write_reg(BLKDEV_ADDR, (unsigned long) addr); ntags = read_reg(BLKDEV_NREQUEST);
write_reg(BLKDEV_OFFSET, offset); nsectors_per_tag = nsectors / ntags;
write_reg(BLKDEV_LEN, nsectors);
write_reg(BLKDEV_WRITE, 1);
req_tag = read_reg(BLKDEV_REQUEST); printf("sending %d writes\n", ntags);
while (read_reg(BLKDEV_NCOMPLETE) == 0); for (i = 0; i < ntags; i++) {
write_reg(BLKDEV_ADDR, (unsigned long) addr);
write_reg(BLKDEV_OFFSET, offset);
write_reg(BLKDEV_LEN, nsectors_per_tag);
write_reg(BLKDEV_WRITE, 1);
resp_tag = read_reg(BLKDEV_COMPLETE); req_tag = read_reg(BLKDEV_REQUEST);
return (resp_tag == req_tag) ? 0 : -1; addr += (nsectors_per_tag << BLKDEV_SECTOR_SHIFT);
offset += nsectors_per_tag;
}
while (read_reg(BLKDEV_NCOMPLETE) < ntags);
for (i = 0; i < ntags; i++) {
resp_tag = read_reg(BLKDEV_COMPLETE);
printf("completed write %d\n", resp_tag);
}
} }
#define TEST_NSECTORS 2 #define TEST_NSECTORS 4
#define TEST_SIZE (TEST_NSECTORS * BLKDEV_SECTOR_SIZE / sizeof(int)) #define TEST_SIZE (TEST_NSECTORS * BLKDEV_SECTOR_SIZE / sizeof(int))
unsigned int test_data[TEST_SIZE]; unsigned int test_data[TEST_SIZE];
@@ -94,15 +117,8 @@ int main(void)
asm volatile ("fence"); asm volatile ("fence");
if (blkdev_write(0, (void *) test_data, TEST_NSECTORS)) { blkdev_write(0, (void *) test_data, TEST_NSECTORS);
printf("write error\n"); blkdev_read((void *) res_data, 0, TEST_NSECTORS);
return 1;
}
if (blkdev_read((void *) res_data, 0, TEST_NSECTORS)) {
printf("read error\n");
return 1;
}
for (int i = 0; i < TEST_SIZE; i++) { for (int i = 0; i < TEST_SIZE; i++) {
if (test_data[i] != res_data[i]) { if (test_data[i] != res_data[i]) {