This commit is contained in:
Kip Macsai-Goren 2021-06-18 10:46:43 -04:00
commit e463247364
32 changed files with 1833 additions and 1027 deletions

View File

@ -61,26 +61,26 @@
// Peripheral Addresses // Peripheral Addresses
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Bus Interface width // Bus Interface width
`define AHBW 64 `define AHBW 64

View File

@ -62,26 +62,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Bus Interface width // Bus Interface width
`define AHBW 64 `define AHBW 64

View File

@ -54,26 +54,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Test modes // Test modes

View File

@ -62,26 +62,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Test modes // Test modes

View File

@ -62,26 +62,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Test modes // Test modes

View File

@ -61,26 +61,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Bus Interface width // Bus Interface width
`define AHBW 32 `define AHBW 32

View File

@ -63,26 +63,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Test modes // Test modes

View File

@ -65,26 +65,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Test modes // Test modes

View File

@ -65,26 +65,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Test modes // Test modes

View File

@ -61,26 +61,26 @@
// Peripheral memory space extends from BASE to BASE+RANGE // Peripheral memory space extends from BASE to BASE+RANGE
// Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits // Range should be a thermometer code with 0's in the upper bits and 1s in the lower bits
`define BOOTTIMSUPPORTED 1'b1 `define BOOTTIM_SUPPORTED 1'b1
`define BOOTTIMBASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder `define BOOTTIM_BASE 32'h00000000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
`define BOOTTIMRANGE 32'h00003FFF `define BOOTTIM_RANGE 32'h00003FFF
//`define BOOTTIMBASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder //`define BOOTTIM_BASE 32'h00001000 // spec had been 0x1000 to 0x2FFF, but dh truncated to 0x1000 to 0x1FFF because upper half seems to be all zeros and this is easier for decoder
//`define BOOTTIMRANGE 32'h00000FFF //`define BOOTTIM_RANGE 32'h00000FFF
`define TIMSUPPORTED 1'b1 `define TIM_SUPPORTED 1'b1
`define TIMBASE 32'h80000000 `define TIM_BASE 32'h80000000
`define TIMRANGE 32'h07FFFFFF `define TIM_RANGE 32'h07FFFFFF
`define CLINTSUPPORTED 1'b1 `define CLINT_SUPPORTED 1'b1
`define CLINTBASE 32'h02000000 `define CLINT_BASE 32'h02000000
`define CLINTRANGE 32'h0000FFFF `define CLINT_RANGE 32'h0000FFFF
`define GPIOSUPPORTED 1'b1 `define GPIO_SUPPORTED 1'b1
`define GPIOBASE 32'h10012000 `define GPIO_BASE 32'h10012000
`define GPIORANGE 32'h000000FF `define GPIO_RANGE 32'h000000FF
`define UARTSUPPORTED 1'b1 `define UART_SUPPORTED 1'b1
`define UARTBASE 32'h10000000 `define UART_BASE 32'h10000000
`define UARTRANGE 32'h00000007 `define UART_RANGE 32'h00000007
`define PLICSUPPORTED 1'b1 `define PLIC_SUPPORTED 1'b1
`define PLICBASE 32'h0C000000 `define PLIC_BASE 32'h0C000000
`define PLICRANGE 32'h03FFFFFF `define PLIC_RANGE 32'h03FFFFFF
// Test modes // Test modes

View File

@ -28,11 +28,11 @@ configs = [
cmd="vsim -do wally-busybear-batch.do -c > {}", cmd="vsim -do wally-busybear-batch.do -c > {}",
grepstr="# loaded 100000 instructions" grepstr="# loaded 100000 instructions"
), ),
# TestCase( TestCase(
# name="buildroot", name="buildroot",
# cmd="vsim -do wally-buildroot-batch.do -c > {}", cmd="vsim -do wally-buildroot-batch.do -c > {}",
# grepstr="# loaded 100000 instructions" grepstr="# loaded 600000 instructions"
# ), ),
TestCase( TestCase(
name="rv32ic", name="rv32ic",
cmd="vsim > {} -c <<!\ndo wally-pipelined-batch.do ../config/rv32ic rv32ic\n!", cmd="vsim > {} -c <<!\ndo wally-pipelined-batch.do ../config/rv32ic rv32ic\n!",

File diff suppressed because it is too large Load Diff

View File

@ -35,7 +35,7 @@ vopt +acc work.testbench -o workopt
vsim workopt -suppress 8852,12070 vsim workopt -suppress 8852,12070
do ./wave-dos/linux-waves.do #do ./wave-dos/linux-waves.do
#-- Run the Simulation #-- Run the Simulation

View File

@ -31,7 +31,7 @@ module dcache(
input logic StallW, input logic StallW,
input logic FlushW, input logic FlushW,
// Upper bits of physical address // Upper bits of physical address
input logic [`XLEN-1:12] UpperPAdrM, input logic [`PA_BITS-1:12] UpperPAdrM,
// Lower 12 bits of virtual address, since it's faster this way // Lower 12 bits of virtual address, since it's faster this way
input logic [11:0] LowerVAdrM, input logic [11:0] LowerVAdrM,
// Write to the dcache // Write to the dcache
@ -41,7 +41,7 @@ module dcache(
input logic [`XLEN-1:0] ReadDataW, input logic [`XLEN-1:0] ReadDataW,
input logic MemAckW, input logic MemAckW,
// Access requested from the ebu unit // Access requested from the ebu unit
output logic [`XLEN-1:0] MemPAdrM, output logic [`PA_BITS-1:0] MemPAdrM,
output logic MemReadM, MemWriteM, output logic MemReadM, MemWriteM,
// High if the dcache is requesting a stall // High if the dcache is requesting a stall
output logic DCacheStallW, output logic DCacheStallW,
@ -56,7 +56,7 @@ module dcache(
// Input signals to cache memory // Input signals to cache memory
logic FlushMem; logic FlushMem;
logic [`XLEN-1:12] DCacheMemUpperPAdr; logic [`PA_BITS-1:12] DCacheMemUpperPAdr;
logic [11:0] DCacheMemLowerAdr; logic [11:0] DCacheMemLowerAdr;
logic DCacheMemWriteEnable; logic DCacheMemWriteEnable;
logic [DCACHELINESIZE-1:0] DCacheMemWriteData; logic [DCACHELINESIZE-1:0] DCacheMemWriteData;
@ -98,7 +98,7 @@ module dcachecontroller #(parameter LINESIZE = 256) (
// Input the address to read // Input the address to read
// The upper bits of the physical pc // The upper bits of the physical pc
input logic [`XLEN-1:12] DCacheMemUpperPAdr, input logic [`PA_BITS-1:12] DCacheMemUpperPAdr,
// The lower bits of the virtual pc // The lower bits of the virtual pc
input logic [11:0] DCacheMemLowerAdr, input logic [11:0] DCacheMemLowerAdr,
@ -122,7 +122,7 @@ module dcachecontroller #(parameter LINESIZE = 256) (
input logic [`XLEN-1:0] ReadDataW, input logic [`XLEN-1:0] ReadDataW,
input logic MemAckW, input logic MemAckW,
// The read we request from main memory // The read we request from main memory
output logic [`XLEN-1:0] MemPAdrM, output logic [`PA_BITS-1:0] MemPAdrM,
output logic MemReadM, MemWriteM output logic MemReadM, MemWriteM
); );
@ -144,7 +144,7 @@ module dcachecontroller #(parameter LINESIZE = 256) (
logic FetchState, BeginFetchState; logic FetchState, BeginFetchState;
logic [LOGWPL:0] FetchWordNum, NextFetchWordNum; logic [LOGWPL:0] FetchWordNum, NextFetchWordNum;
logic [`XLEN-1:0] LineAlignedPCPF; logic [`PA_BITS-1:0] LineAlignedPCPF;
flopr #(1) FetchStateFlop(clk, reset, BeginFetchState | (FetchState & ~EndFetchState), FetchState); flopr #(1) FetchStateFlop(clk, reset, BeginFetchState | (FetchState & ~EndFetchState), FetchState);
flopr #(LOGWPL+1) FetchWordNumFlop(clk, reset, NextFetchWordNum, FetchWordNum); flopr #(LOGWPL+1) FetchWordNumFlop(clk, reset, NextFetchWordNum, FetchWordNum);

View File

@ -40,7 +40,7 @@ module dmem (
input logic [`XLEN-1:0] WriteDataM, input logic [`XLEN-1:0] WriteDataM,
input logic [1:0] AtomicM, input logic [1:0] AtomicM,
input logic CommitM, input logic CommitM,
output logic [`XLEN-1:0] MemPAdrM, output logic [`PA_BITS-1:0] MemPAdrM,
output logic MemReadM, MemWriteM, output logic MemReadM, MemWriteM,
output logic [1:0] AtomicMaskedM, output logic [1:0] AtomicMaskedM,
output logic DataMisalignedM, output logic DataMisalignedM,
@ -142,20 +142,20 @@ module dmem (
// Handle atomic load reserved / store conditional // Handle atomic load reserved / store conditional
generate generate
if (`A_SUPPORTED) begin // atomic instructions supported if (`A_SUPPORTED) begin // atomic instructions supported
logic [`XLEN-1:2] ReservationPAdrW; logic [`PA_BITS-1:2] ReservationPAdrW;
logic ReservationValidM, ReservationValidW; logic ReservationValidM, ReservationValidW;
logic lrM, scM, WriteAdrMatchM; logic lrM, scM, WriteAdrMatchM;
assign lrM = MemReadM && AtomicM[0]; assign lrM = MemReadM && AtomicM[0];
assign scM = MemRWM[0] && AtomicM[0]; assign scM = MemRWM[0] && AtomicM[0];
assign WriteAdrMatchM = MemRWM[0] && (MemPAdrM[`XLEN-1:2] == ReservationPAdrW) && ReservationValidW; assign WriteAdrMatchM = MemRWM[0] && (MemPAdrM[`PA_BITS-1:2] == ReservationPAdrW) && ReservationValidW;
assign SquashSCM = scM && ~WriteAdrMatchM; assign SquashSCM = scM && ~WriteAdrMatchM;
always_comb begin // ReservationValidM (next value of valid reservation) always_comb begin // ReservationValidM (next value of valid reservation)
if (lrM) ReservationValidM = 1; // set valid on load reserve if (lrM) ReservationValidM = 1; // set valid on load reserve
else if (scM || WriteAdrMatchM) ReservationValidM = 0; // clear valid on store to same address or any sc else if (scM || WriteAdrMatchM) ReservationValidM = 0; // clear valid on store to same address or any sc
else ReservationValidM = ReservationValidW; // otherwise don't change valid else ReservationValidM = ReservationValidW; // otherwise don't change valid
end end
flopenrc #(`XLEN-2) resadrreg(clk, reset, FlushW, lrM, MemPAdrM[`XLEN-1:2], ReservationPAdrW); // could drop clear on this one but not valid flopenrc #(`PA_BITS-2) resadrreg(clk, reset, FlushW, lrM, MemPAdrM[`PA_BITS-1:2], ReservationPAdrW); // could drop clear on this one but not valid
flopenrc #(1) resvldreg(clk, reset, FlushW, lrM, ReservationValidM, ReservationValidW); flopenrc #(1) resvldreg(clk, reset, FlushW, lrM, ReservationValidM, ReservationValidW);
flopenrc #(1) squashreg(clk, reset, FlushW, ~StallW, SquashSCM, SquashSCW); flopenrc #(1) squashreg(clk, reset, FlushW, ~StallW, SquashSCM, SquashSCW);
end else begin // Atomic operations not supported end else begin // Atomic operations not supported

View File

@ -47,7 +47,7 @@ module ahblite (
output logic [`XLEN-1:0] InstrRData, output logic [`XLEN-1:0] InstrRData,
output logic InstrAckF, output logic InstrAckF,
// Signals from Data Cache // Signals from Data Cache
input logic [`XLEN-1:0] MemPAdrM, input logic [`PA_BITS-1:0] MemPAdrM,
input logic MemReadM, MemWriteM, input logic MemReadM, MemWriteM,
input logic [`XLEN-1:0] WriteDataM, input logic [`XLEN-1:0] WriteDataM,
input logic [1:0] MemSizeM, input logic [1:0] MemSizeM,

View File

@ -105,10 +105,19 @@ module ifu (
logic PMPLoadAccessFaultM, PMPStoreAccessFaultM; // *** these are just so that the mmu has somewhere to put these outputs, they're unused in this stage logic PMPLoadAccessFaultM, PMPStoreAccessFaultM; // *** these are just so that the mmu has somewhere to put these outputs, they're unused in this stage
// if you're allowed to parameterize outputs/ inputs existence, these are an easy delete. // if you're allowed to parameterize outputs/ inputs existence, these are an easy delete.
logic [`PA_BITS-1:0] PCPFmmu;
generate
if (`XLEN==32)
assign PCPF = PCPFmmu[31:0];
else
assign PCPF = {8'b0, PCPFmmu};
endgenerate
mmu #(.ENTRY_BITS(`ITLB_ENTRY_BITS), .IMMU(1)) itlb(.TLBAccessType(2'b10), .VirtualAddress(PCF), mmu #(.ENTRY_BITS(`ITLB_ENTRY_BITS), .IMMU(1)) itlb(.TLBAccessType(2'b10), .VirtualAddress(PCF),
.PTEWriteVal(PageTableEntryF), .PageTypeWriteVal(PageTypeF), .PTEWriteVal(PageTableEntryF), .PageTypeWriteVal(PageTypeF),
.TLBWrite(ITLBWriteF), .TLBFlush(ITLBFlushF), .TLBWrite(ITLBWriteF), .TLBFlush(ITLBFlushF),
.PhysicalAddress(PCPF), .TLBMiss(ITLBMissF), .PhysicalAddress(PCPFmmu), .TLBMiss(ITLBMissF),
.TLBHit(ITLBHitF), .TLBPageFault(ITLBInstrPageFaultF), .TLBHit(ITLBHitF), .TLBPageFault(ITLBInstrPageFaultF),
.AtomicAccessM(1'b0), .WriteAccessM(1'b0), .ReadAccessM(1'b0), // *** is this the right way force these bits constant? should they be someething else? .AtomicAccessM(1'b0), .WriteAccessM(1'b0), .ReadAccessM(1'b0), // *** is this the right way force these bits constant? should they be someething else?

View File

@ -57,7 +57,7 @@ module mmu #(parameter ENTRY_BITS = 3,
input logic TLBFlush, input logic TLBFlush,
// Physical address outputs // Physical address outputs
output logic [`XLEN-1:0] PhysicalAddress, output logic [`PA_BITS-1:0] PhysicalAddress,
output logic TLBMiss, output logic TLBMiss,
output logic TLBHit, output logic TLBHit,

View File

@ -35,14 +35,18 @@ module pmaadrdec (
output logic HSEL output logic HSEL
); );
logic match; logic Match;
logic SizeValid;
// determine if an address is in a range starting at the base // determine if an address is in a range starting at the base
// for example, if Base = 0x04002000 and range = 0x00000FFF, // for example, if Base = 0x04002000 and range = 0x00000FFF,
// then anything address between 0x04002000 and 0x04002FFF should match (HSEL=1) // then anything address between 0x04002000 and 0x04002FFF should match (HSEL=1)
assign Match = &((HADDR ~^ Base) | Range);
assign match = &((HADDR ~^ Base) | Range); // determine if legal size of access is being made (byte, halfword, word, doubleword)
assign HSEL = match & Supported; assign SizeValid = SizeMask[Size[1:0]];
assign HSEL = Match && Supported && AccessValid && SizeValid;
endmodule endmodule

View File

@ -46,14 +46,7 @@ module pmachecker (
output logic PMAStoreAccessFaultM output logic PMAStoreAccessFaultM
); );
// Signals are high if the memory access is within the given region // logic BootTim, Tim, CLINT, GPIO, UART, PLIC;
logic BootTim, Tim, CLINT, GPIO, UART, PLIC;
logic [5:0] Regions;
// Actual HSEL signals sent to uncore
logic HSELBootTim, HSELTim, HSELCLINT, HSELGPIO, HSELUART, HSELPLIC;
logic ValidBootTim, ValidTim, ValidCLINT, ValidGPIO, ValidUART, ValidPLIC;
logic PMAAccessFault; logic PMAAccessFault;
logic AccessRW, AccessRWX, AccessRX; logic AccessRW, AccessRWX, AccessRX;
@ -62,45 +55,24 @@ module pmachecker (
assign AccessRWX = ReadAccessM | WriteAccessM | ExecuteAccessF; assign AccessRWX = ReadAccessM | WriteAccessM | ExecuteAccessF;
assign AccessRX = ReadAccessM | ExecuteAccessF; assign AccessRX = ReadAccessM | ExecuteAccessF;
// Determine which region of physical memory (if any) is being accessed // Determine which region of physical memory (if any) is being accessed
pmaadrdec boottimdec(HADDR, `BOOTTIMBASE, `BOOTTIMRANGE, `BOOTTIMSUPPORTED, AccessRX, HSIZE, 4'b1111, BootTim); // *** linux tests fail early when Access is anything other than 1b1
pmaadrdec timdec(HADDR, `TIMBASE, `TIMRANGE, `TIMSUPPORTED, AccessRWX, HSIZE, 4'b1111, Tim); pmaadrdec boottimdec(HADDR, `BOOTTIM_BASE, `BOOTTIM_RANGE, `BOOTTIM_SUPPORTED, 1'b1/*AccessRX*/, HSIZE, 4'b1111, HSELRegions[5]);
pmaadrdec clintdec(HADDR, `CLINTBASE, `CLINTRANGE, `CLINTSUPPORTED, AccessRW, HSIZE, (`XLEN==64 ? 4'b1000 : 4'b0100), CLINT); pmaadrdec timdec(HADDR, `TIM_BASE, `TIM_RANGE, `TIM_SUPPORTED, 1'b1/*AccessRWX*/, HSIZE, 4'b1111, HSELRegions[4]);
pmaadrdec gpiodec(HADDR, `GPIOBASE, `GPIORANGE, `GPIOSUPPORTED, AccessRW, HSIZE, 4'b0100, GPIO); pmaadrdec clintdec(HADDR, `CLINT_BASE, `CLINT_RANGE, `CLINT_SUPPORTED, AccessRW, HSIZE, 4'b1111, HSELRegions[3]);
pmaadrdec uartdec(HADDR, `UARTBASE, `UARTRANGE, `UARTSUPPORTED, AccessRW, HSIZE, 4'b0001, UART); pmaadrdec gpiodec(HADDR, `GPIO_BASE, `GPIO_RANGE, `GPIO_SUPPORTED, AccessRW, HSIZE, 4'b0100, HSELRegions[2]);
pmaadrdec plicdec(HADDR, `PLICBASE, `PLICRANGE, `PLICSUPPORTED, AccessRW, HSIZE, 4'b0100, PLIC); pmaadrdec uartdec(HADDR, `UART_BASE, `UART_RANGE, `UART_SUPPORTED, AccessRW, HSIZE, 4'b0001, HSELRegions[1]);
pmaadrdec plicdec(HADDR, `PLIC_BASE, `PLIC_RANGE, `PLIC_SUPPORTED, AccessRW, HSIZE, 4'b0100, HSELRegions[0]);
// Swizzle region bits
assign Regions = {BootTim, Tim, CLINT, GPIO, UART, PLIC};
// Only RAM memory regions are cacheable // Only RAM memory regions are cacheable
assign Cacheable = BootTim | Tim; assign Cacheable = HSELRegions[5] | HSELRegions[4];
assign Idempotent = Tim; assign Idempotent = HSELRegions[4];
assign AtomicAllowed = Tim; assign AtomicAllowed = HSELRegions[4];
assign ValidBootTim = '1;
assign ValidTim = '1;
assign ValidCLINT = ~ExecuteAccessF && ((HSIZE == 3'b011 && `XLEN==64) || (HSIZE == 3'b010 && `XLEN==32));
assign ValidGPIO = ~ExecuteAccessF && (HSIZE == 3'b010);
assign ValidUART = ~ExecuteAccessF && (HSIZE == 3'b000);
assign ValidPLIC = ~ExecuteAccessF && (HSIZE == 3'b010);
assign HSELBootTim = BootTim && ValidBootTim;
assign HSELTim = Tim && ValidTim;
assign HSELCLINT = CLINT && ValidCLINT;
assign HSELGPIO = GPIO && ValidGPIO;
assign HSELUART = UART && ValidUART; // only byte writes to UART are supported
assign HSELPLIC = PLIC && ValidPLIC;
// Swizzle region bits
assign HSELRegions = {HSELBootTim, HSELTim, HSELCLINT, HSELGPIO, HSELUART, HSELPLIC};
assign PMAAccessFault = ~|HSELRegions;
// Detect access faults // Detect access faults
assign PMAAccessFault = (~|HSELRegions) && AccessRWX;
assign PMAInstrAccessFaultF = ExecuteAccessF && PMAAccessFault; assign PMAInstrAccessFaultF = ExecuteAccessF && PMAAccessFault;
assign PMALoadAccessFaultM = ReadAccessM && PMAAccessFault; assign PMALoadAccessFaultM = ReadAccessM && PMAAccessFault;
assign PMAStoreAccessFaultM = WriteAccessM && PMAAccessFault; assign PMAStoreAccessFaultM = WriteAccessM && PMAAccessFault;
assign PMASquashBusAccess = PMAAccessFault && AccessRWX; assign PMASquashBusAccess = PMAAccessFault;
endmodule endmodule

View File

@ -78,7 +78,7 @@ module tlb #(parameter ENTRY_BITS = 3,
input logic TLBFlush, input logic TLBFlush,
// Physical address outputs // Physical address outputs
output logic [`XLEN-1:0] PhysicalAddress, output logic [`PA_BITS-1:0] PhysicalAddress,
output logic TLBMiss, output logic TLBMiss,
output logic TLBHit, output logic TLBHit,
@ -202,11 +202,9 @@ module tlb #(parameter ENTRY_BITS = 3,
// Output the hit physical address if translation is currently on. // Output the hit physical address if translation is currently on.
generate generate
if (`XLEN == 32) begin if (`XLEN == 32) begin
// *** If we want rv32 to use the full 34 bit physical address space, this mux2 #(`PA_BITS) addressmux({2'b0, VirtualAddress}, PhysicalAddressFull, Translate, PhysicalAddress);
// must be changed
mux2 #(`XLEN) addressmux(VirtualAddress, PhysicalAddressFull[31:0], Translate, PhysicalAddress);
end else begin end else begin
mux2 #(`XLEN) addressmux(VirtualAddress, {8'b0, PhysicalAddressFull}, Translate, PhysicalAddress); mux2 #(`PA_BITS) addressmux(VirtualAddress[`PA_BITS-1:0], PhysicalAddressFull, Translate, PhysicalAddress);
end end
endgenerate endgenerate

View File

@ -39,7 +39,7 @@ module csr #(parameter
input logic InterruptM, input logic InterruptM,
input logic CSRReadM, CSRWriteM, TrapM, MTrapM, STrapM, UTrapM, mretM, sretM, uretM, input logic CSRReadM, CSRWriteM, TrapM, MTrapM, STrapM, UTrapM, mretM, sretM, uretM,
input logic TimerIntM, ExtIntM, SwIntM, input logic TimerIntM, ExtIntM, SwIntM,
input logic [63:0] MTIME, MTIMECMP, input logic [63:0] MTIME_CLINT, MTIMECMP_CLINT,
input logic InstrValidW, FloatRegWriteW, LoadStallD, input logic InstrValidW, FloatRegWriteW, LoadStallD,
input logic BPPredDirWrongM, input logic BPPredDirWrongM,
input logic BTBPredPCWrongM, input logic BTBPredPCWrongM,

View File

@ -30,8 +30,8 @@
// Ben 06/17/21: I brought in MTIME, MTIMECMP from CLINT. *** this probably isn't perfect though because it doesn't yet provide the ability to change these through CSR writes; overall this whole thing might need some rethinking // Ben 06/17/21: I brought in MTIME, MTIMECMP from CLINT. *** this probably isn't perfect though because it doesn't yet provide the ability to change these through CSR writes; overall this whole thing might need some rethinking
module csrc #(parameter module csrc #(parameter
MCYCLE = 12'hB00, MCYCLE = 12'hB00,
MTIMEadr = 12'hB01, // address not specified in privileged spec. Consider moving to CLINT to match SiFive MTIME = 12'hB01, // address not specified in privileged spec. Consider moving to CLINT to match SiFive
MTIMECMPadr = 12'hB21, // not specified in privileged spec. Move to CLINT MTIMECMP = 12'hB21, // not specified in privileged spec. Move to CLINT
MINSTRET = 12'hB02, MINSTRET = 12'hB02,
MHPMCOUNTERBASE = 12'hB00, MHPMCOUNTERBASE = 12'hB00,
//MHPMCOUNTER3 = 12'hB03, //MHPMCOUNTER3 = 12'hB03,
@ -39,8 +39,8 @@ module csrc #(parameter
// ... more counters // ... more counters
//MHPMCOUNTER31 = 12'hB1F, //MHPMCOUNTER31 = 12'hB1F,
MCYCLEH = 12'hB80, MCYCLEH = 12'hB80,
MTIMEHadr = 12'hB81, // address not specified in privileged spec. Consider moving to CLINT to match SiFive MTIMEH = 12'hB81, // address not specified in privileged spec. Consider moving to CLINT to match SiFive
MTIMECMPHadr = 12'hBA1, // not specified in privileged spec. Move to CLINT MTIMECMPH = 12'hBA1, // not specified in privileged spec. Move to CLINT
MINSTRETH = 12'hB82, MINSTRETH = 12'hB82,
MHPMCOUNTERHBASE = 12'hB80, MHPMCOUNTERHBASE = 12'hB80,
//MHPMCOUNTER3H = 12'hB83, //MHPMCOUNTER3H = 12'hB83,
@ -82,7 +82,7 @@ module csrc #(parameter
input logic [1:0] PrivilegeModeW, input logic [1:0] PrivilegeModeW,
input logic [`XLEN-1:0] CSRWriteValM, input logic [`XLEN-1:0] CSRWriteValM,
input logic [31:0] MCOUNTINHIBIT_REGW, MCOUNTEREN_REGW, SCOUNTEREN_REGW, input logic [31:0] MCOUNTINHIBIT_REGW, MCOUNTEREN_REGW, SCOUNTEREN_REGW,
input logic [63:0] MTIME, MTIMECMP, input logic [63:0] MTIME_CLINT, MTIMECMP_CLINT,
output logic [`XLEN-1:0] CSRCReadValM, output logic [`XLEN-1:0] CSRCReadValM,
output logic IllegalCSRCAccessM output logic IllegalCSRCAccessM
); );
@ -230,13 +230,13 @@ module csrc #(parameter
if (CSRAdrM >= MHPMCOUNTERBASE+3 && CSRAdrM < MHPMCOUNTERBASE+`COUNTERS) CSRCReadValM = HPMCOUNTER_REGW[CSRAdrM-MHPMCOUNTERBASE]; if (CSRAdrM >= MHPMCOUNTERBASE+3 && CSRAdrM < MHPMCOUNTERBASE+`COUNTERS) CSRCReadValM = HPMCOUNTER_REGW[CSRAdrM-MHPMCOUNTERBASE];
else if (CSRAdrM >= HPMCOUNTERBASE+3 && CSRAdrM < HPMCOUNTERBASE+`COUNTERS) CSRCReadValM = HPMCOUNTER_REGW[CSRAdrM-HPMCOUNTERBASE]; else if (CSRAdrM >= HPMCOUNTERBASE+3 && CSRAdrM < HPMCOUNTERBASE+`COUNTERS) CSRCReadValM = HPMCOUNTER_REGW[CSRAdrM-HPMCOUNTERBASE];
else case (CSRAdrM) else case (CSRAdrM)
MTIMEadr: CSRCReadValM = MTIME; MTIME: CSRCReadValM = MTIME_CLINT;
MTIMECMPadr: CSRCReadValM = MTIMECMP; MTIMECMP: CSRCReadValM = MTIMECMP_CLINT;
MCYCLE: CSRCReadValM = CYCLE_REGW; MCYCLE: CSRCReadValM = CYCLE_REGW;
MINSTRET: CSRCReadValM = INSTRET_REGW; MINSTRET: CSRCReadValM = INSTRET_REGW;
//MHPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW; //MHPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW;
//MHPMCOUNTER4: CSRCReadValM = HPMCOUNTER4_REGW; //MHPMCOUNTER4: CSRCReadValM = HPMCOUNTER4_REGW;
TIME: CSRCReadValM = MTIME; TIME: CSRCReadValM = MTIME_CLINT;
CYCLE: CSRCReadValM = CYCLE_REGW; CYCLE: CSRCReadValM = CYCLE_REGW;
INSTRET: CSRCReadValM = INSTRET_REGW; INSTRET: CSRCReadValM = INSTRET_REGW;
//HPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW; //HPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW;
@ -259,24 +259,24 @@ module csrc #(parameter
else if (CSRAdrM >= MHPMCOUNTERHBASE+3 && CSRAdrM < MHPMCOUNTERHBASE+`COUNTERS) CSRCReadValM = HPMCOUNTERH_REGW[CSRAdrM-MHPMCOUNTERHBASE]; else if (CSRAdrM >= MHPMCOUNTERHBASE+3 && CSRAdrM < MHPMCOUNTERHBASE+`COUNTERS) CSRCReadValM = HPMCOUNTERH_REGW[CSRAdrM-MHPMCOUNTERHBASE];
else if (CSRAdrM >= HPMCOUNTERHBASE+3 && CSRAdrM < HPMCOUNTERHBASE+`COUNTERS) CSRCReadValM = HPMCOUNTERH_REGW[CSRAdrM-HPMCOUNTERHBASE]; else if (CSRAdrM >= HPMCOUNTERHBASE+3 && CSRAdrM < HPMCOUNTERHBASE+`COUNTERS) CSRCReadValM = HPMCOUNTERH_REGW[CSRAdrM-HPMCOUNTERHBASE];
else case (CSRAdrM) else case (CSRAdrM)
MTIMEadr: CSRCReadValM = MTIME[31:0]; MTIME: CSRCReadValM = MTIME_CLINT[31:0];
MTIMECMPadr: CSRCReadValM = MTIMECMP[31:0]; MTIMECMP: CSRCReadValM = MTIMECMP_CLINT[31:0];
MCYCLE: CSRCReadValM = CYCLE_REGW[31:0]; MCYCLE: CSRCReadValM = CYCLE_REGW[31:0];
MINSTRET: CSRCReadValM = INSTRET_REGW[31:0]; MINSTRET: CSRCReadValM = INSTRET_REGW[31:0];
//MHPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW[31:0]; //MHPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW[31:0];
//MHPMCOUNTER4: CSRCReadValM = HPMCOUNTER4_REGW[31:0]; //MHPMCOUNTER4: CSRCReadValM = HPMCOUNTER4_REGW[31:0];
TIME: CSRCReadValM = MTIME[31:0]; TIME: CSRCReadValM = MTIME_CLINT[31:0];
CYCLE: CSRCReadValM = CYCLE_REGW[31:0]; CYCLE: CSRCReadValM = CYCLE_REGW[31:0];
INSTRET: CSRCReadValM = INSTRET_REGW[31:0]; INSTRET: CSRCReadValM = INSTRET_REGW[31:0];
//HPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW[31:0]; //HPMCOUNTER3: CSRCReadValM = HPMCOUNTER3_REGW[31:0];
//HPMCOUNTER4: CSRCReadValM = HPMCOUNTER4_REGW[31:0]; //HPMCOUNTER4: CSRCReadValM = HPMCOUNTER4_REGW[31:0];
MTIMEHadr: CSRCReadValM = MTIME[63:32]; MTIMEH: CSRCReadValM = MTIME_CLINT[63:32];
MTIMECMPHadr: CSRCReadValM = MTIMECMP[63:32]; MTIMECMPH: CSRCReadValM = MTIMECMP_CLINT[63:32];
MCYCLEH: CSRCReadValM = CYCLE_REGW[63:32]; MCYCLEH: CSRCReadValM = CYCLE_REGW[63:32];
MINSTRETH: CSRCReadValM = INSTRET_REGW[63:32]; MINSTRETH: CSRCReadValM = INSTRET_REGW[63:32];
//MHPMCOUNTER3H: CSRCReadValM = HPMCOUNTER3_REGW[63:32]; //MHPMCOUNTER3H: CSRCReadValM = HPMCOUNTER3_REGW[63:32];
//MHPMCOUNTER4H: CSRCReadValM = HPMCOUNTER4_REGW[63:32]; //MHPMCOUNTER4H: CSRCReadValM = HPMCOUNTER4_REGW[63:32];
TIMEH: CSRCReadValM = MTIME[63:32]; TIMEH: CSRCReadValM = MTIME_CLINT[63:32];
CYCLEH: CSRCReadValM = CYCLE_REGW[63:32]; CYCLEH: CSRCReadValM = CYCLE_REGW[63:32];
INSTRETH: CSRCReadValM = INSTRET_REGW[63:32]; INSTRETH: CSRCReadValM = INSTRET_REGW[63:32];
//HPMCOUNTER3H: CSRCReadValM = HPMCOUNTER3_REGW[63:32]; //HPMCOUNTER3H: CSRCReadValM = HPMCOUNTER3_REGW[63:32];

View File

@ -52,7 +52,7 @@ module privileged (
input logic LoadMisalignedFaultM, input logic LoadMisalignedFaultM,
input logic StoreMisalignedFaultM, input logic StoreMisalignedFaultM,
input logic TimerIntM, ExtIntM, SwIntM, input logic TimerIntM, ExtIntM, SwIntM,
input logic [63:0] MTIME, MTIMECMP, input logic [63:0] MTIME_CLINT, MTIMECMP_CLINT,
input logic [`XLEN-1:0] InstrMisalignedAdrM, MemAdrM, input logic [`XLEN-1:0] InstrMisalignedAdrM, MemAdrM,
input logic [4:0] SetFflagsM, input logic [4:0] SetFflagsM,

View File

@ -32,8 +32,8 @@ module imem (
output logic InstrAccessFaultF); output logic InstrAccessFaultF);
/* verilator lint_off UNDRIVEN */ /* verilator lint_off UNDRIVEN */
logic [`XLEN-1:0] RAM[`TIMBASE>>(1+`XLEN/32):(`TIMRANGE+`TIMBASE)>>(1+`XLEN/32)]; logic [`XLEN-1:0] RAM[`TIM_BASE>>(1+`XLEN/32):(`TIM_RANGE+`TIM_BASE)>>(1+`XLEN/32)];
logic [`XLEN-1:0] bootram[`BOOTTIMBASE>>(1+`XLEN/32):(`BOOTTIMRANGE+`BOOTTIMBASE)>>(1+`XLEN/32)]; logic [`XLEN-1:0] bootram[`BOOTTIM_BASE>>(1+`XLEN/32):(`BOOTTIM_RANGE+`BOOTTIM_BASE)>>(1+`XLEN/32)];
/* verilator lint_on UNDRIVEN */ /* verilator lint_on UNDRIVEN */
logic [31:0] adrbits; // needs to be 32 bits to index RAM logic [31:0] adrbits; // needs to be 32 bits to index RAM
logic [`XLEN-1:0] rd; logic [`XLEN-1:0] rd;
@ -44,27 +44,27 @@ module imem (
else assign adrbits = AdrF[31:3]; else assign adrbits = AdrF[31:3];
endgenerate endgenerate
assign #2 rd = (AdrF < (`TIMBASE >> 1)) ? bootram[adrbits] : RAM[adrbits]; // busybear: 2 memory options assign #2 rd = (AdrF < (`TIM_BASE >> 1)) ? bootram[adrbits] : RAM[adrbits]; // busybear: 2 memory options
// hack right now for unaligned 32-bit instructions // hack right now for unaligned 32-bit instructions
// eventually this will need to cause a stall like a cache miss // eventually this will need to cause a stall like a cache miss
// when the instruction wraps around a cache line // when the instruction wraps around a cache line
// could be optimized to only stall when the instruction wrapping is 32 bits // could be optimized to only stall when the instruction wrapping is 32 bits
assign #2 rd2 = (AdrF < (`TIMBASE >> 1)) ? bootram[adrbits+1][15:0] : RAM[adrbits+1][15:0]; //busybear: 2 memory options assign #2 rd2 = (AdrF < (`TIM_BASE >> 1)) ? bootram[adrbits+1][15:0] : RAM[adrbits+1][15:0]; //busybear: 2 memory options
generate generate
if (`XLEN==32) begin if (`XLEN==32) begin
assign InstrF = AdrF[1] ? {rd2[15:0], rd[31:16]} : rd; assign InstrF = AdrF[1] ? {rd2[15:0], rd[31:16]} : rd;
// First, AdrF needs to get its last bit appended back onto it // First, AdrF needs to get its last bit appended back onto it
// Then not-XORing it with TIMBASE checks if it matches TIMBASE exactly // Then not-XORing it with TIM_BASE checks if it matches TIM_BASE exactly
// Then ORing it with TIMRANGE introduces some leeway into the previous check, by allowing the lower bits to be either high or low // Then ORing it with TIM_RANGE introduces some leeway into the previous check, by allowing the lower bits to be either high or low
assign InstrAccessFaultF = (~&(({AdrF,1'b0} ~^ `TIMBASE) | `TIMRANGE)) & (~&(({AdrF,1'b0} ~^ `BOOTTIMBASE) | `BOOTTIMRANGE)); assign InstrAccessFaultF = (~&(({AdrF,1'b0} ~^ `TIM_BASE) | `TIM_RANGE)) & (~&(({AdrF,1'b0} ~^ `BOOTTIM_BASE) | `BOOTTIM_RANGE));
end else begin end else begin
assign InstrF = AdrF[2] ? (AdrF[1] ? {rd2[15:0], rd[63:48]} : rd[63:32]) assign InstrF = AdrF[2] ? (AdrF[1] ? {rd2[15:0], rd[63:48]} : rd[63:32])
: (AdrF[1] ? rd[47:16] : rd[31:0]); : (AdrF[1] ? rd[47:16] : rd[31:0]);
// //
assign InstrAccessFaultF = (|AdrF[`XLEN-1:32] | ~&({AdrF[31:1],1'b0} ~^ `TIMBASE | `TIMRANGE)) & (|AdrF[`XLEN-1:32] | ~&({AdrF[31:1],1'b0} ~^ `BOOTTIMBASE | `BOOTTIMRANGE)); assign InstrAccessFaultF = (|AdrF[`XLEN-1:32] | ~&({AdrF[31:1],1'b0} ~^ `TIM_BASE | `TIM_RANGE)) & (|AdrF[`XLEN-1:32] | ~&({AdrF[31:1],1'b0} ~^ `BOOTTIM_BASE | `BOOTTIM_RANGE));
end end
endgenerate endgenerate
endmodule endmodule

View File

@ -58,7 +58,7 @@ module uncore (
output logic [31:0] GPIOPinsOut, GPIOPinsEn, output logic [31:0] GPIOPinsOut, GPIOPinsEn,
input logic UARTSin, input logic UARTSin,
output logic UARTSout, output logic UARTSout,
output logic [63:0] MTIME, MTIMECMP output logic [63:0] MTIME_CLINT, MTIMECMP_CLINT
); );
logic [`XLEN-1:0] HWDATA; logic [`XLEN-1:0] HWDATA;
@ -76,26 +76,15 @@ module uncore (
// unswizzle HSEL signals // unswizzle HSEL signals
assign {HSELBootTim, HSELTim, HSELCLINT, HSELGPIO, HSELUART, HSELPLIC} = HSELRegions; assign {HSELBootTim, HSELTim, HSELCLINT, HSELGPIO, HSELUART, HSELPLIC} = HSELRegions;
/* PMA checker now handles decoding addresses. *** This can be deleted.
// AHB Address decoder
adrdec timdec(HADDR, `TIMBASE, `TIMRANGE, HSELTim);
adrdec boottimdec(HADDR, `BOOTTIMBASE, `BOOTTIMRANGE, HSELBootTim);
adrdec clintdec(HADDR, `CLINTBASE, `CLINTRANGE, HSELCLINT);
adrdec plicdec(HADDR, `PLICBASE, `PLICRANGE, HSELPLIC);
adrdec gpiodec(HADDR, `GPIOBASE, `GPIORANGE, HSELGPIO);
adrdec uartdec(HADDR, `UARTBASE, `UARTRANGE, PreHSELUART);
assign HSELUART = PreHSELUART && (HSIZE == 3'b000); // only byte writes to UART are supported
*/
// subword accesses: converts HWDATAIN to HWDATA // subword accesses: converts HWDATAIN to HWDATA
subwordwrite sww(.*); subwordwrite sww(.*);
// tightly integrated memory // tightly integrated memory
dtim #(.BASE(`TIMBASE), .RANGE(`TIMRANGE)) dtim (.*); dtim #(.BASE(`TIM_BASE), .RANGE(`TIM_RANGE)) dtim (.*);
dtim #(.BASE(`BOOTTIMBASE), .RANGE(`BOOTTIMRANGE)) bootdtim(.HSELTim(HSELBootTim), .HREADTim(HREADBootTim), .HRESPTim(HRESPBootTim), .HREADYTim(HREADYBootTim), .*); dtim #(.BASE(`BOOTTIM_BASE), .RANGE(`BOOTTIM_RANGE)) bootdtim(.HSELTim(HSELBootTim), .HREADTim(HREADBootTim), .HRESPTim(HRESPBootTim), .HREADYTim(HREADYBootTim), .*);
// memory-mapped I/O peripherals // memory-mapped I/O peripherals
clint clint(.HADDR(HADDR[15:0]), .*); clint clint(.HADDR(HADDR[15:0]), .MTIME(MTIME_CLINT), .MTIMECMP(MTIMECMP_CLINT), .*);
plic plic(.HADDR(HADDR[27:0]), .*); plic plic(.HADDR(HADDR[27:0]), .*);
gpio gpio(.HADDR(HADDR[7:0]), .*); // *** may want to add GPIO interrupts gpio gpio(.HADDR(HADDR[7:0]), .*); // *** may want to add GPIO interrupts
uart uart(.HADDR(HADDR[2:0]), .TXRDYb(), .RXRDYb(), .INTR(UARTIntr), .SIN(UARTSin), .SOUT(UARTSout), uart uart(.HADDR(HADDR[2:0]), .TXRDYb(), .RXRDYb(), .INTR(UARTIntr), .SIN(UARTSin), .SOUT(UARTSout),

View File

@ -34,7 +34,7 @@ module wallypipelinedhart (
input logic TimerIntM, ExtIntM, SwIntM, input logic TimerIntM, ExtIntM, SwIntM,
input logic InstrAccessFaultF, input logic InstrAccessFaultF,
input logic DataAccessFaultM, input logic DataAccessFaultM,
input logic [63:0] MTIME, MTIMECMP, input logic [63:0] MTIME_CLINT, MTIMECMP_CLINT,
// Bus Interface // Bus Interface
input logic [15:0] rd2, // bogus, delete when real multicycle fetch works input logic [15:0] rd2, // bogus, delete when real multicycle fetch works
input logic [`AHBW-1:0] HRDATA, input logic [`AHBW-1:0] HRDATA,
@ -135,7 +135,8 @@ module wallypipelinedhart (
logic MemReadM, MemWriteM; logic MemReadM, MemWriteM;
logic [1:0] AtomicMaskedM; logic [1:0] AtomicMaskedM;
logic [2:0] Funct3M; logic [2:0] Funct3M;
logic [`XLEN-1:0] MemAdrM, MemPAdrM, WriteDataM; logic [`XLEN-1:0] MemAdrM, WriteDataM;
logic [`PA_BITS-1:0] MemPAdrM;
logic [`XLEN-1:0] ReadDataW; logic [`XLEN-1:0] ReadDataW;
logic [`XLEN-1:0] InstrPAdrF; logic [`XLEN-1:0] InstrPAdrF;
logic [`XLEN-1:0] InstrRData; logic [`XLEN-1:0] InstrRData;

View File

@ -63,7 +63,7 @@ module wallypipelinedsoc (
logic [5:0] HSELRegions; logic [5:0] HSELRegions;
logic InstrAccessFaultF, DataAccessFaultM; logic InstrAccessFaultF, DataAccessFaultM;
logic TimerIntM, SwIntM; // from CLINT logic TimerIntM, SwIntM; // from CLINT
logic [63:0] MTIME, MTIMECMP; // from CLINT to CSRs logic [63:0] MTIME_CLINT, MTIMECMP_CLINT; // from CLINT to CSRs
logic ExtIntM; // from PLIC logic ExtIntM; // from PLIC
logic [2:0] HADDRD; logic [2:0] HADDRD;
logic [3:0] HSIZED; logic [3:0] HSIZED;

View File

@ -1,711 +0,0 @@
`include "wally-config.vh"
module testbench();
logic clk, reset;
logic [31:0] GPIOPinsIn;
logic [31:0] GPIOPinsOut, GPIOPinsEn;
// instantiate device to be tested
logic [31:0] CheckInstrD;
logic [`AHBW-1:0] HRDATA;
logic [31:0] HADDR;
logic [`AHBW-1:0] HWDATA;
logic HWRITE;
logic [2:0] HSIZE;
logic [2:0] HBURST;
logic [3:0] HPROT;
logic [1:0] HTRANS;
logic HMASTLOCK;
logic HCLK, HRESETn;
logic [`AHBW-1:0] HRDATAEXT;
logic HREADYEXT, HRESPEXT;
logic UARTSout;
assign GPIOPinsIn = 0;
assign UARTSin = 1;
// instantiate processor and memories
wallypipelinedsoc dut(.*);
/**
* Walk the page table stored in dtim according to sv39 logic and translate a
* virtual address to a physical address.
*
* See section 4.3.2 of the RISC-V Privileged specification for a full
* explanation of the below algorithm.
*/
function logic [`XLEN-1:0] adrTranslator(
input logic [`XLEN-1:0] adrIn);
begin
logic SvMode, PTE_R, PTE_X;
logic [`XLEN-1:0] SATP, PTE;
logic [55:0] BaseAdr, PAdr;
logic [8:0] VPN [0:2];
logic [11:0] Offset;
int i;
// Grab the SATP register from privileged unit
SATP = dut.hart.priv.csr.SATP_REGW;
// Split the virtual address into page number segments and offset
VPN[2] = adrIn[38:30];
VPN[1] = adrIn[29:21];
VPN[0] = adrIn[20:12];
Offset = adrIn[11:0];
// We do not support sv48; only sv39
SvMode = SATP[63];
// Only perform translation if translation is on and the processor is not
// in machine mode
if (SvMode && (dut.hart.priv.PrivilegeModeW != `M_MODE)) begin
BaseAdr = SATP[43:0] << 12;
for (i = 2; i >= 0; i--) begin
PAdr = BaseAdr + (VPN[i] << 3);
// dtim.RAM is 64-bit addressed. PAdr specifies a byte. We right shift
// by 3 (the PTE size) to get the requested 64-bit PTE.
PTE = dut.uncore.dtim.RAM[PAdr >> 3];
PTE_R = PTE[1];
PTE_X = PTE[3];
if (PTE_R || PTE_X) begin
// Leaf page found
break;
end else begin
// Go to next level of table
BaseAdr = PTE[53:10] << 12;
end
end
// Determine which parts of the PTE page number to use based on the
// level of the page table we reached.
if (i == 2) begin
// Gigapage
assign adrTranslator = {8'b0, PTE[53:28], VPN[1], VPN[0], Offset};
end else if (i == 1) begin
// Megapage
assign adrTranslator = {8'b0, PTE[53:19], VPN[0], Offset};
end else begin
// Kilopage
assign adrTranslator = {8'b0, PTE[53:10], Offset};
end
end else begin
// Direct translation if address translation is not on
assign adrTranslator = adrIn;
end
end
endfunction
// initialize test
initial
begin
reset <= 1; # 22; reset <= 0;
end
// read pc trace file
integer data_file_PC, scan_file_PC;
initial begin
data_file_PC = $fopen({`LINUX_TEST_VECTORS,"parsedPC.txt"}, "r");
if (data_file_PC == 0) begin
$display("file couldn't be opened");
$stop;
end
end
integer data_file_PCW, scan_file_PCW;
initial begin
data_file_PCW = $fopen({`LINUX_TEST_VECTORS,"parsedPC.txt"}, "r");
if (data_file_PCW == 0) begin
$display("file couldn't be opened");
$stop;
end
end
// read register trace file
integer data_file_rf, scan_file_rf;
initial begin
data_file_rf = $fopen({`LINUX_TEST_VECTORS,"parsedRegs.txt"}, "r");
if (data_file_rf == 0) begin
$display("file couldn't be opened");
$stop;
end
end
// read CSR trace file
integer data_file_csr, scan_file_csr;
initial begin
data_file_csr = $fopen({`LINUX_TEST_VECTORS,"parsedCSRs2.txt"}, "r");
if (data_file_csr == 0) begin
$display("file couldn't be opened");
$stop;
end
end
// read memreads trace file
integer data_file_memR, scan_file_memR;
initial begin
data_file_memR = $fopen({`LINUX_TEST_VECTORS,"parsedMemRead.txt"}, "r");
if (data_file_memR == 0) begin
$display("file couldn't be opened");
$stop;
end
end
// read memwrite trace file
integer data_file_memW, scan_file_memW;
initial begin
data_file_memW = $fopen({`LINUX_TEST_VECTORS,"parsedMemWrite.txt"}, "r");
if (data_file_memW == 0) begin
$display("file couldn't be opened");
$stop;
end
end
// initial loading of memories
initial begin
$readmemh({`LINUX_TEST_VECTORS,"bootmem.txt"}, dut.uncore.bootdtim.RAM, 'h1000 >> 3); // load at address 0x1000, start of boot TIM
$readmemh({`LINUX_TEST_VECTORS,"ram.txt"}, dut.uncore.dtim.RAM);
$readmemb(`TWO_BIT_PRELOAD, dut.hart.ifu.bpred.bpred.Predictor.DirPredictor.PHT.memory);
$readmemb(`BTB_PRELOAD, dut.hart.ifu.bpred.bpred.TargetPredictor.memory.memory);
end
integer warningCount = 0;
integer instrs;
//logic[63:0] adrTranslation[4:0];
//string translationType[4:0] = {"rf", "writeAdr", "PCW", "PC", "readAdr"};
//initial begin
// for(int i=0; i<5; i++) begin
// adrTranslation[i] = 64'b0;
// end
//end
//function logic equal(logic[63:0] adr, logic[63:0] adrExpected, integer func);
// if (adr[11:0] !== adrExpected[11:0]) begin
// equal = 1'b0;
// end else begin
// equal = 1'b1;
// if ((adr+adrTranslation[func]) !== adrExpected) begin
// adrTranslation[func] = adrExpected - adr;
// $display("warning: probably new address translation %x for %s at instr %0d", adrTranslation[func], translationType[func], instrs);
// warningCount += 1;
// end
// end
//endfunction
// pretty sure this isn't necessary anymore, but keeping this for now since its easier
function logic equal(logic[63:0] adr, logic[63:0] adrExpected, integer func);
equal = adr === adrExpected;
endfunction
`define ERROR \
#10; \
$display("processed %0d instructions with %0d warnings", instrs, warningCount); \
$stop;
logic [63:0] pcExpected;
logic [63:0] regExpected;
integer regNumExpected;
logic [`XLEN-1:0] PCW;
flopenr #(`XLEN) PCWReg(clk, reset, ~dut.hart.ieu.dp.StallW, dut.hart.ifu.PCM, PCW);
genvar i;
generate
for(i=1; i<32; i++) begin
always @(dut.hart.ieu.dp.regf.rf[i]) begin
if ($time == 0) begin
scan_file_rf = $fscanf(data_file_rf, "%x\n", regExpected);
if (dut.hart.ieu.dp.regf.rf[i] != regExpected) begin
$display("%0t ps, instr %0d: rf[%0d] does not equal rf expected: %x, %x", $time, instrs, i, dut.hart.ieu.dp.regf.rf[i], regExpected);
`ERROR
end
end else begin
scan_file_rf = $fscanf(data_file_rf, "%d\n", regNumExpected);
scan_file_rf = $fscanf(data_file_rf, "%x\n", regExpected);
if (i != regNumExpected) begin
$display("%0t ps, instr %0d: wrong register changed: %0d, %0d expected to switch to %x from %x", $time, instrs, i, regNumExpected, regExpected, dut.hart.ieu.dp.regf.rf[regNumExpected]);
`ERROR
end
if (~equal(dut.hart.ieu.dp.regf.rf[i],regExpected, 0)) begin
$display("%0t ps, instr %0d: rf[%0d] does not equal rf expected: %x, %x", $time, instrs, i, dut.hart.ieu.dp.regf.rf[i], regExpected);
`ERROR
end
//if (dut.hart.ieu.dp.regf.rf[i] !== regExpected) begin
// force dut.hart.ieu.dp.regf.rf[i] = regExpected;
// release dut.hart.ieu.dp.regf.rf[i];
//end
end
end
end
endgenerate
// RAM and bootram are addressed in 64-bit blocks - this logic handles R/W
// including subwords. Brief explanation on signals:
//
// readMask: bitmask of bits to read / write, left-shifted to align with
// nearest 64-bit boundary - examples
// HSIZE = 0 -> readMask = 11111111
// HSIZE = 1 -> readMask = 1111111111111111
//
// In the linux boot, the processor spends the first ~5 instructions in
// bootram, before jr jumps to main RAM
logic [63:0] readMask;
assign readMask = ((1 << (8*(1 << HSIZE))) - 1) << 8 * HADDR[2:0];
logic [`XLEN-1:0] readAdrExpected, readAdrTranslated;
always @(dut.HRDATA) begin
#2;
if (dut.hart.MemRWM[1]
&& (dut.hart.ebu.CaptureDataM)
&& dut.HRDATA !== {64{1'bx}}) begin
//$display("%0t", $time);
if($feof(data_file_memR)) begin
$display("no more memR data to read");
`ERROR
end
scan_file_memR = $fscanf(data_file_memR, "%x\n", readAdrExpected);
scan_file_memR = $fscanf(data_file_memR, "%x\n", HRDATA);
assign readAdrTranslated = adrTranslator(readAdrExpected);
if (~equal(HADDR,readAdrTranslated,4)) begin
$display("%0t ps, instr %0d: HADDR does not equal readAdrExpected: %x, %x", $time, instrs, HADDR, readAdrTranslated);
`ERROR
end
if ((readMask & HRDATA) !== (readMask & dut.HRDATA)) begin
if (HADDR inside `LINUX_FIX_READ) begin
//$display("warning %0t ps, instr %0d, adr %0d: forcing HRDATA to expected: %x, %x", $time, instrs, HADDR, HRDATA, dut.HRDATA);
force dut.uncore.HRDATA = HRDATA;
#9;
release dut.uncore.HRDATA;
warningCount += 1;
end else begin
$display("%0t ps, instr %0d: ExpectedHRDATA does not equal dut.HRDATA: %x, %x from address %x, %x", $time, instrs, HRDATA, dut.HRDATA, HADDR, HSIZE);
`ERROR
end
end
//end else if(dut.hart.MemRWM[1]) begin
// $display("%x, %x, %x, %t", HADDR, dut.PCF, dut.HRDATA, $time);
end
end
logic [`XLEN-1:0] writeDataExpected, writeAdrExpected, writeAdrTranslated;
// this might need to change
//always @(HWDATA or HADDR or HSIZE or HWRITE) begin
always @(negedge HWRITE) begin
//#1;
if ($time != 0) begin
if($feof(data_file_memW)) begin
$display("no more memW data to read");
`ERROR
end
scan_file_memW = $fscanf(data_file_memW, "%x\n", writeDataExpected);
scan_file_memW = $fscanf(data_file_memW, "%x\n", writeAdrExpected);
assign writeAdrTranslated = adrTranslator(writeAdrExpected);
if (writeDataExpected != HWDATA && ~dut.uncore.HSELPLICD) begin
$display("%0t ps, instr %0d: HWDATA does not equal writeDataExpected: %x, %x", $time, instrs, HWDATA, writeDataExpected);
`ERROR
end
if (~equal(writeAdrTranslated,HADDR,1) && ~dut.uncore.HSELPLICD) begin
$display("%0t ps, instr %0d: HADDR does not equal writeAdrExpected: %x, %x", $time, instrs, HADDR, writeAdrTranslated);
`ERROR
end
end
end
integer totalCSR = 0;
logic [99:0] StartCSRexpected[63:0];
string StartCSRname[99:0];
initial begin
while(1) begin
scan_file_csr = $fscanf(data_file_csr, "%s\n", StartCSRname[totalCSR]);
if(StartCSRname[totalCSR] == "---") begin
break;
end
scan_file_csr = $fscanf(data_file_csr, "%x\n", StartCSRexpected[totalCSR]);
totalCSR = totalCSR + 1;
end
end
always @(dut.hart.priv.csr.genblk1.csrm.MCAUSE_REGW) begin
if (dut.hart.priv.csr.genblk1.csrm.MCAUSE_REGW == 2 && instrs > 1) begin
$display("!!!!!! illegal instruction !!!!!!!!!!");
$display("(as a reminder, MCAUSE and MEPC are set by this)");
$display("at %0t ps, instr %0d, HADDR %x", $time, instrs, HADDR);
`ERROR
end
if (dut.hart.priv.csr.genblk1.csrm.MCAUSE_REGW == 5 && instrs != 0) begin
$display("!!!!!! illegal (physical) memory access !!!!!!!!!!");
$display("(as a reminder, MCAUSE and MEPC are set by this)");
$display("at %0t ps, instr %0d, HADDR %x", $time, instrs, HADDR);
`ERROR
end
end
`define CHECK_CSR2(CSR, PATH) \
string CSR; \
logic [63:0] expected``CSR``; \
//CSR checking \
always @(``PATH``.``CSR``_REGW) begin \
if ($time > 1) begin \
if ("SEPC" == `"CSR`") begin #1; end \
if ("SCAUSE" == `"CSR`") begin #2; end \
if ("SSTATUS" == `"CSR`") begin #3; end \
scan_file_csr = $fscanf(data_file_csr, "%s\n", CSR); \
scan_file_csr = $fscanf(data_file_csr, "%x\n", expected``CSR``); \
if(CSR.icompare(`"CSR`")) begin \
$display("%0t ps, instr %0d: %s changed, expected %s", $time, instrs, `"CSR`", CSR); \
end \
if(``PATH``.``CSR``_REGW != ``expected``CSR) begin \
$display("%0t ps, instr %0d: %s does not equal %s expected: %x, %x", $time, instrs, `"CSR`", CSR, ``PATH``.``CSR``_REGW, ``expected``CSR); \
`ERROR \
end \
end else begin \
if (!(`BUILDROOT == 1 && "MSTATUS" == `"CSR`")) begin \
for(integer j=0; j<totalCSR; j++) begin \
if(!StartCSRname[j].icompare(`"CSR`")) begin \
if(``PATH``.``CSR``_REGW != StartCSRexpected[j]) begin \
$display("%0t ps, instr %0d: %s does not equal %s expected: %x, %x", $time, instrs, `"CSR`", StartCSRname[j], ``PATH``.``CSR``_REGW, StartCSRexpected[j]); \
`ERROR \
end \
end \
end \
end \
end \
end
`define CHECK_CSR(CSR) \
`CHECK_CSR2(CSR, dut.hart.priv.csr)
`define CSRM dut.hart.priv.csr.genblk1.csrm
`define CSRS dut.hart.priv.csr.genblk1.csrs.genblk1
//`CHECK_CSR(FCSR)
`CHECK_CSR2(MCAUSE, `CSRM)
`CHECK_CSR(MCOUNTEREN)
`CHECK_CSR(MEDELEG)
`CHECK_CSR(MEPC)
//`CHECK_CSR(MHARTID)
`CHECK_CSR(MIDELEG)
`CHECK_CSR(MIE)
//`CHECK_CSR(MIP)
`CHECK_CSR2(MISA, `CSRM)
`CHECK_CSR2(MSCRATCH, `CSRM)
`CHECK_CSR(MSTATUS)
`CHECK_CSR2(MTVAL, `CSRM)
`CHECK_CSR(MTVEC)
//`CHECK_CSR2(PMPADDR0, `CSRM)
//`CHECK_CSR2(PMdut.PCFG0, `CSRM)
`CHECK_CSR(SATP)
`CHECK_CSR2(SCAUSE, `CSRS)
`CHECK_CSR(SCOUNTEREN)
`CHECK_CSR(SEPC)
`CHECK_CSR(SIE)
`CHECK_CSR2(SSCRATCH, `CSRS)
`CHECK_CSR(SSTATUS)
`CHECK_CSR2(STVAL, `CSRS)
`CHECK_CSR(STVEC)
logic speculative;
initial begin
speculative = 0;
end
logic [63:0] lastCheckInstrD, lastPC, lastPC2;
string PCtextW, PCtext2W;
logic [31:0] InstrWExpected;
logic [63:0] PCWExpected;
always @(PCW or dut.hart.ieu.InstrValidW) begin
if(dut.hart.ieu.InstrValidW && PCW != 0) begin
if($feof(data_file_PCW)) begin
$display("no more PC data to read");
`ERROR
end
scan_file_PCW = $fscanf(data_file_PCW, "%s\n", PCtextW);
PCtext2W = "";
while (PCtext2W != "***") begin
PCtextW = {PCtextW, " ", PCtext2W};
scan_file_PC = $fscanf(data_file_PCW, "%s\n", PCtext2W);
end
scan_file_PCW = $fscanf(data_file_PCW, "%x\n", InstrWExpected);
// then expected PC value
scan_file_PCW = $fscanf(data_file_PCW, "%x\n", PCWExpected);
if(~equal(PCW,PCWExpected,2)) begin
$display("%0t ps, instr %0d: PCW does not equal PCW expected: %x, %x", $time, instrs, PCW, PCWExpected);
`ERROR
end
//if(it.InstrW != InstrWExpected) begin
// $display("%0t ps, instr %0d: InstrW does not equal InstrW expected: %x, %x", $time, instrs, it.InstrW, InstrWExpected);
//end
end
end
string PCtext, PCtext2;
initial begin
instrs = 0;
end
logic [31:0] InstrMask;
logic forcedInstr;
logic [63:0] lastPCD;
always @(dut.hart.ifu.PCD or dut.hart.ifu.InstrRawD or reset or negedge dut.hart.ifu.StallE) begin
if(~HWRITE) begin
#2;
if (~reset && dut.hart.ifu.InstrRawD[15:0] !== {16{1'bx}} && dut.hart.ifu.PCD !== 64'h0 && ~dut.hart.ifu.StallE) begin
if (dut.hart.ifu.PCD !== lastPCD) begin
lastCheckInstrD = CheckInstrD;
lastPC <= dut.hart.ifu.PCD;
lastPC2 <= lastPC;
if (speculative && (lastPC != pcExpected)) begin
speculative = ~equal(dut.hart.ifu.PCD,pcExpected,3);
if(dut.hart.ifu.PCD===pcExpected) begin
if((dut.hart.ifu.InstrRawD[6:0] == 7'b1010011) || // for now, NOP out any float instrs
(dut.hart.ifu.PCD == 32'h80001dc6) || // as well as stores to PLIC
(dut.hart.ifu.PCD == 32'h80001de0) ||
(dut.hart.ifu.PCD == 32'h80001de2)) begin
$display("warning: NOPing out %s at PC=%0x, instr %0d, time %0t", PCtext, dut.hart.ifu.PCD, instrs, $time);
force CheckInstrD = 32'b0010011;
force dut.hart.ifu.InstrRawD = 32'b0010011;
while (clk != 0) #1;
while (clk != 1) #1;
release dut.hart.ifu.InstrRawD;
release CheckInstrD;
warningCount += 1;
forcedInstr = 1;
end
else begin
forcedInstr = 0;
end
end
end
else begin
if($feof(data_file_PC)) begin
$display("no more PC data to read");
`ERROR
end
scan_file_PC = $fscanf(data_file_PC, "%s\n", PCtext);
PCtext2 = "";
while (PCtext2 != "***") begin
PCtext = {PCtext, " ", PCtext2};
scan_file_PC = $fscanf(data_file_PC, "%s\n", PCtext2);
end
scan_file_PC = $fscanf(data_file_PC, "%x\n", CheckInstrD);
if(dut.hart.ifu.PCD === pcExpected) begin
if((dut.hart.ifu.InstrRawD[6:0] == 7'b1010011) || // for now, NOP out any float instrs
(dut.hart.ifu.PCD == 32'h80001dc6) || // as well as stores to PLIC
(dut.hart.ifu.PCD == 32'h80001de0) ||
(dut.hart.ifu.PCD == 32'h80001de2)) begin
$display("warning: NOPing out %s at PC=%0x, instr %0d, time %0t", PCtext, dut.hart.ifu.PCD, instrs, $time);
force CheckInstrD = 32'b0010011;
force dut.hart.ifu.InstrRawD = 32'b0010011;
while (clk != 0) #1;
while (clk != 1) #1;
release dut.hart.ifu.InstrRawD;
release CheckInstrD;
warningCount += 1;
forcedInstr = 1;
end
else begin
forcedInstr = 0;
end
end
// then expected PC value
scan_file_PC = $fscanf(data_file_PC, "%x\n", pcExpected);
if (instrs <= 10 || (instrs <= 100 && instrs % 10 == 0) ||
(instrs <= 1000 && instrs % 100 == 0) || (instrs <= 10000 && instrs % 1000 == 0) ||
(instrs <= 100000 && instrs % 10000 == 0) || (instrs <= 1000000 && instrs % 100000 == 0)) begin
$display("loaded %0d instructions", instrs);
end
instrs += 1;
// are we at a branch/jump?
if (`BPRED_ENABLED) begin
speculative = dut.hart.ifu.bpred.bpred.BPPredWrongE;
end else begin
casex (lastCheckInstrD[31:0])
32'b00000000001000000000000001110011, // URET
32'b00010000001000000000000001110011, // SRET
32'b00110000001000000000000001110011, // MRET
32'bXXXXXXXXXXXXXXXXXXXXXXXXX1101111, // JAL
32'bXXXXXXXXXXXXXXXXXXXXXXXXX1100111, // JALR
32'bXXXXXXXXXXXXXXXXXXXXXXXXX1100011, // B
32'bXXXXXXXXXXXXXXXX110XXXXXXXXXXX01, // C.BEQZ
32'bXXXXXXXXXXXXXXXX111XXXXXXXXXXX01, // C.BNEZ
32'bXXXXXXXXXXXXXXXX101XXXXXXXXXXX01: // C.J
speculative = 1;
32'bXXXXXXXXXXXXXXXX1001000000000010, // C.EBREAK:
32'bXXXXXXXXXXXXXXXXX000XXXXX1110011: // Something that's not CSRR*
speculative = 0; // tbh don't really know what should happen here
32'b000110000000XXXXXXXXXXXXX1110011, // CSR* SATP, *
32'bXXXXXXXXXXXXXXXX1000XXXXX0000010, // C.JR
32'bXXXXXXXXXXXXXXXX1001XXXXX0000010: // C.JALR //this is RV64 only so no C.JAL
speculative = 1;
default:
speculative = 0;
endcase
end
//check things!
if ((~speculative) && (~equal(dut.hart.ifu.PCD,pcExpected,3))) begin
$display("%0t ps, instr %0d: PC does not equal PC expected: %x, %x", $time, instrs, dut.hart.ifu.PCD, pcExpected);
`ERROR
end
InstrMask = CheckInstrD[1:0] == 2'b11 ? 32'hFFFFFFFF : 32'h0000FFFF;
if ((~forcedInstr) && (~speculative) && ((InstrMask & dut.hart.ifu.InstrRawD) !== (InstrMask & CheckInstrD))) begin
$display("%0t ps, instr %0d: InstrD does not equal CheckInstrD: %x, %x, PC: %x", $time, instrs, dut.hart.ifu.InstrRawD, CheckInstrD, dut.hart.ifu.PCD);
`ERROR
end
end
end
lastPCD = dut.hart.ifu.PCD;
end
end
end
// Track names of instructions
string InstrFName, InstrDName, InstrEName, InstrMName, InstrWName;
logic [31:0] InstrW;
instrTrackerTB it(clk, reset,
dut.hart.ifu.icache.controller.FinalInstrRawF,
dut.hart.ifu.InstrD, dut.hart.ifu.InstrE,
dut.hart.ifu.InstrM, dut.hart.ifu.InstrW,
InstrFName, InstrDName, InstrEName, InstrMName, InstrWName);
// generate clock to sequence tests
always
begin
clk <= 1; # 5; clk <= 0; # 5;
end
endmodule
module instrTrackerTB(
input logic clk, reset,
input logic [31:0] InstrF,InstrD,InstrE,InstrM,InstrW,
output string InstrFName, InstrDName, InstrEName, InstrMName, InstrWName);
// stage Instr to Writeback for visualization
//flopr #(32) InstrWReg(clk, reset, InstrM, InstrW);
instrNameDecTB fdec(InstrF, InstrFName);
instrNameDecTB ddec(InstrD, InstrDName);
instrNameDecTB edec(InstrE, InstrEName);
instrNameDecTB mdec(InstrM, InstrMName);
instrNameDecTB wdec(InstrW, InstrWName);
endmodule
// decode the instruction name, to help the test bench
module instrNameDecTB(
input logic [31:0] instr,
output string name);
logic [6:0] op;
logic [2:0] funct3;
logic [6:0] funct7;
logic [11:0] imm;
assign op = instr[6:0];
assign funct3 = instr[14:12];
assign funct7 = instr[31:25];
assign imm = instr[31:20];
// it would be nice to add the operands to the name
// create another variable called decoded
always_comb
casez({op, funct3})
10'b0000000_000: name = "BAD";
10'b0000011_000: name = "LB";
10'b0000011_001: name = "LH";
10'b0000011_010: name = "LW";
10'b0000011_011: name = "LD";
10'b0000011_100: name = "LBU";
10'b0000011_101: name = "LHU";
10'b0000011_110: name = "LWU";
10'b0010011_000: if (instr[31:15] == 0 && instr[11:7] ==0) name = "NOP/FLUSH";
else name = "ADDI";
10'b0010011_001: if (funct7[6:1] == 6'b000000) name = "SLLI";
else name = "ILLEGAL";
10'b0010011_010: name = "SLTI";
10'b0010011_011: name = "SLTIU";
10'b0010011_100: name = "XORI";
10'b0010011_101: if (funct7[6:1] == 6'b000000) name = "SRLI";
else if (funct7[6:1] == 6'b010000) name = "SRAI";
else name = "ILLEGAL";
10'b0010011_110: name = "ORI";
10'b0010011_111: name = "ANDI";
10'b0010111_???: name = "AUIPC";
10'b0100011_000: name = "SB";
10'b0100011_001: name = "SH";
10'b0100011_010: name = "SW";
10'b0100011_011: name = "SD";
10'b0011011_000: name = "ADDIW";
10'b0011011_001: name = "SLLIW";
10'b0011011_101: if (funct7 == 7'b0000000) name = "SRLIW";
else if (funct7 == 7'b0100000) name = "SRAIW";
else name = "ILLEGAL";
10'b0111011_000: if (funct7 == 7'b0000000) name = "ADDW";
else if (funct7 == 7'b0100000) name = "SUBW";
else name = "ILLEGAL";
10'b0111011_001: name = "SLLW";
10'b0111011_101: if (funct7 == 7'b0000000) name = "SRLW";
else if (funct7 == 7'b0100000) name = "SRAW";
else name = "ILLEGAL";
10'b0110011_000: if (funct7 == 7'b0000000) name = "ADD";
else if (funct7 == 7'b0000001) name = "MUL";
else if (funct7 == 7'b0100000) name = "SUB";
else name = "ILLEGAL";
10'b0110011_001: if (funct7 == 7'b0000000) name = "SLL";
else if (funct7 == 7'b0000001) name = "MULH";
else name = "ILLEGAL";
10'b0110011_010: if (funct7 == 7'b0000000) name = "SLT";
else if (funct7 == 7'b0000001) name = "MULHSU";
else name = "ILLEGAL";
10'b0110011_011: if (funct7 == 7'b0000000) name = "SLTU";
else if (funct7 == 7'b0000001) name = "DIV";
else name = "ILLEGAL";
10'b0110011_100: if (funct7 == 7'b0000000) name = "XOR";
else if (funct7 == 7'b0000001) name = "MUL";
else name = "ILLEGAL";
10'b0110011_101: if (funct7 == 7'b0000000) name = "SRL";
else if (funct7 == 7'b0000001) name = "DIVU";
else if (funct7 == 7'b0100000) name = "SRA";
else name = "ILLEGAL";
10'b0110011_110: if (funct7 == 7'b0000000) name = "OR";
else if (funct7 == 7'b0000001) name = "REM";
else name = "ILLEGAL";
10'b0110011_111: if (funct7 == 7'b0000000) name = "AND";
else if (funct7 == 7'b0000001) name = "REMU";
else name = "ILLEGAL";
10'b0110111_???: name = "LUI";
10'b1100011_000: name = "BEQ";
10'b1100011_001: name = "BNE";
10'b1100011_100: name = "BLT";
10'b1100011_101: name = "BGE";
10'b1100011_110: name = "BLTU";
10'b1100011_111: name = "BGEU";
10'b1100111_000: name = "JALR";
10'b1101111_???: name = "JAL";
10'b1110011_000: if (imm == 0) name = "ECALL";
else if (imm == 1) name = "EBREAK";
else if (imm == 2) name = "URET";
else if (imm == 258) name = "SRET";
else if (imm == 770) name = "MRET";
else name = "ILLEGAL";
10'b1110011_001: name = "CSRRW";
10'b1110011_010: name = "CSRRS";
10'b1110011_011: name = "CSRRC";
10'b1110011_101: name = "CSRRWI";
10'b1110011_110: name = "CSRRSI";
10'b1110011_111: name = "CSRRCI";
10'b0001111_???: name = "FENCE";
default: name = "ILLEGAL";
endcase
endmodule

View File

@ -582,8 +582,8 @@ string tests32f[] = '{
InstrFName, InstrDName, InstrEName, InstrMName, InstrWName); InstrFName, InstrDName, InstrEName, InstrMName, InstrWName);
// initialize tests // initialize tests
localparam integer MemStartAddr = `TIMBASE>>(1+`XLEN/32); localparam integer MemStartAddr = `TIM_BASE>>(1+`XLEN/32);
localparam integer MemEndAddr = (`TIMRANGE+`TIMBASE)>>1+(`XLEN/32); localparam integer MemEndAddr = (`TIM_RANGE+`TIM_BASE)>>1+(`XLEN/32);
initial initial
begin begin
@ -655,9 +655,9 @@ string tests32f[] = '{
errors = (i == SIGNATURESIZE+1); // error if file is empty errors = (i == SIGNATURESIZE+1); // error if file is empty
i = 0; i = 0;
if (`XLEN == 32) if (`XLEN == 32)
testadr = (`TIMBASE+tests[test+1].atohex())/4; testadr = (`TIM_BASE+tests[test+1].atohex())/4;
else else
testadr = (`TIMBASE+tests[test+1].atohex())/8; testadr = (`TIM_BASE+tests[test+1].atohex())/8;
/* verilator lint_off INFINITELOOP */ /* verilator lint_off INFINITELOOP */
while (signature[i] !== 'bx) begin while (signature[i] !== 'bx) begin
//$display("signature[%h] = %h", i, signature[i]); //$display("signature[%h] = %h", i, signature[i]);

View File

@ -494,11 +494,14 @@ module testbench();
logic [31:0] InstrMask; logic [31:0] InstrMask;
logic forcedInstr; logic forcedInstr;
logic [63:0] lastPCD; logic [63:0] lastPCD;
always @(dut.hart.ifu.PCD or dut.hart.ifu.InstrRawD or reset or negedge dut.hart.ifu.StallE) begin always @(dut.hart.ifu.PCD or dut.hart.ifu.InstrRawD or reset or negedge dut.hart.ifu.StallE) begin
if(~HWRITE) begin if(~HWRITE) begin
#2; #2;
$display("test point");
if (~reset && dut.hart.ifu.InstrRawD[15:0] !== {16{1'bx}} && dut.hart.ifu.PCD !== 64'h0 && ~dut.hart.ifu.StallE) begin if (~reset && dut.hart.ifu.InstrRawD[15:0] !== {16{1'bx}} && dut.hart.ifu.PCD !== 64'h0 && ~dut.hart.ifu.StallE) begin
if (dut.hart.ifu.PCD !== lastPCD) begin if (dut.hart.ifu.PCD !== lastPCD) begin
$display("tp2");
lastCheckInstrD = CheckInstrD; lastCheckInstrD = CheckInstrD;
lastPC <= dut.hart.ifu.PCD; lastPC <= dut.hart.ifu.PCD;
lastPC2 <= lastPC; lastPC2 <= lastPC;
@ -525,16 +528,22 @@ module testbench();
end end
end end
else begin else begin
$display("tp4");
if($feof(data_file_PC)) begin if($feof(data_file_PC)) begin
$display("no more PC data to read"); $display("no more PC data to read");
`ERROR `ERROR
end end
scan_file_PC = $fscanf(data_file_PC, "%s\n", PCtextD); scan_file_PC = $fscanf(data_file_PC, "%s\n", PCtextD);
PCtext2 = ""; PCtext2 = "";
$display("tp5 PCtextD = %s PCtext2 = %s\n", PCtextD, PCtext2);
while (PCtext2 != "***") begin while (PCtext2 != "***") begin
$display("tp6 PCtextD = %s PCtext2 = %s\n", PCtextD, PCtext2);
PCtextD = {PCtextD, " ", PCtext2}; PCtextD = {PCtextD, " ", PCtext2};
$display("tp8");
scan_file_PC = $fscanf(data_file_PC, "%s\n", PCtext2); scan_file_PC = $fscanf(data_file_PC, "%s\n", PCtext2);
$display("tp9");
end end
$display("tp7 PCtextD = %s PCtext2 = %s\n", PCtextD, PCtext2);
scan_file_PC = $fscanf(data_file_PC, "%x\n", CheckInstrD); scan_file_PC = $fscanf(data_file_PC, "%x\n", CheckInstrD);
if(dut.hart.ifu.PCD === pcExpected) begin if(dut.hart.ifu.PCD === pcExpected) begin
if((dut.hart.ifu.InstrRawD[6:0] == 7'b1010011) || // for now, NOP out any float instrs if((dut.hart.ifu.InstrRawD[6:0] == 7'b1010011) || // for now, NOP out any float instrs
@ -607,6 +616,7 @@ module testbench();
end end
end end
// Track names of instructions // Track names of instructions
string InstrFName, InstrDName, InstrEName, InstrMName, InstrWName; string InstrFName, InstrDName, InstrEName, InstrMName, InstrWName;
logic [31:0] InstrW; logic [31:0] InstrW;

View File

@ -159,9 +159,9 @@ module testbench();
i = 0; i = 0;
errors = 0; errors = 0;
if (`XLEN == 32) if (`XLEN == 32)
testadr = (`TIMBASE+tests[test+1].atohex())/4; testadr = (`TIM_BASE+tests[test+1].atohex())/4;
else else
testadr = (`TIMBASE+tests[test+1].atohex())/8; testadr = (`TIM_BASE+tests[test+1].atohex())/8;
/* verilator lint_off INFINITELOOP */ /* verilator lint_off INFINITELOOP */
while (signature[i] !== 'bx) begin while (signature[i] !== 'bx) begin
//$display("signature[%h] = %h", i, signature[i]); //$display("signature[%h] = %h", i, signature[i]);