URL
https://opencores.org/ocsvn/forwardcom/forwardcom/trunk
Subversion Repositories forwardcom
[/] [forwardcom/] [trunk/] [code_memory.sv] - Rev 77
Go to most recent revision | Compare with Previous | Blame | View Log
//////////////////////////////////////////////////////////////////////////////////// Engineer: Agner Fog//// Create Date: 2020-05-05// Last modified: 2021-08-02// Module Name: code_cache// Project Name: ForwardCom soft core// Target Devices: Artix 7// Tool Versions: Vivado v. 2020.1// License: CERN-OHL-W v. 2 or later// Description: on-chip code memory or code cache////////////////////////////////////////////////////////////////////////////////////`include "defines.vh"// It takes two clock cycles to fetch data from on-chip ram,// Attempts to fetch in one cycle, using negedge or latch failed for timing reasons// code memory, 1024*64 bits,module code_memory (input clock, // clockinput clock_enable, // clock enable. Used when single-steppinginput read_enable, // read enable when fetching codeinput [7:0] write_enable, // write enable for each byte separately when writing code. must be 0x0F or 0xF0 or 0xFFinput [`COMMON_ADDR_WIDTH-1:0] write_addr_in,// Address lines when writing to code memoryinput [63:0] write_data_in, // Data lines when writing to code memoryinput [`CODE_ADDR_WIDTH-2:0] read_addr_in, // Address for reading from code memoryoutput reg [`CODE_DATA_WIDTH-1:0] data_out, // Data out// outputs for debugger:output reg [31:0] debug_out // debug information);// code ramreg [`CODE_DATA_WIDTH-1:0] ram[0:(2**(`CODE_ADDR_WIDTH-1)-1)];// (attempt to split this into 32-bit lines failed to implement as ram block)logic [`COMMON_ADDR_WIDTH-4:0] write_address_hi;//logic [`DATA_ADDR_WIDTH-4:0] write_address_hi;//logic [2:0] address_lo; // not usedlogic write_address_valid;always_comb begin// write_address_hi = write_addr_in[`COMMON_ADDR_WIDTH-1:3] - {1'b1,`CODE_ADDR_START'b0}; // index to 64-bit lineswrite_address_hi = write_addr_in[`COMMON_ADDR_WIDTH-1:3] - {1'b1,{(`CODE_ADDR_START-3){1'b0}}}; // index to 64-bit lineswrite_address_valid = write_addr_in[`COMMON_ADDR_WIDTH-1:`CODE_ADDR_START] != 0; // code address spaceend/*Calculation of loader address:Code memory starts at address 2**CODE_ADDR_START = 32kB = 0x8000Code memory size = 2**(CODE_ADDR_WIDTH+2) = 64kB = 0x10000Code memory end = code memory start + code memory size = 0x18000Max loader size = 2kB = 0x800 bytesLoader start address = code memory end - max loader sizeEach line in code ram is CODE_DATA_WIDTH = 64 bits = 8 bytesLoader start line = (code memory size - max loader size) / line size*/parameter max_loader_size = `MAX_LOADER_SIZE << 2; // loader size in bytesparameter code_memory_start = 2**`CODE_ADDR_START;parameter code_memory_size = 2**(`CODE_ADDR_WIDTH+2);parameter code_memory_end = code_memory_start + code_memory_size;parameter loader_start_address = code_memory_end - max_loader_size;parameter loader_start_relative = code_memory_size - max_loader_size;parameter loader_start_line = loader_start_relative / (`CODE_DATA_WIDTH >> 3);generate if (`LOADER_FILE != "")initial begin// insert loader code$readmemh(`LOADER_FILE, ram, loader_start_line);endendgenerate// code ram read and write processalways_ff @(posedge clock) if (clock_enable) begin// Write data to code RAM when loading program codeif (write_address_valid) begin // write address is in code sectionif (write_enable[0]) beginram[write_address_hi][31:0] <= write_data_in[31:0];endif (write_enable[4]) beginram[write_address_hi][63:32] <= write_data_in[63:32];endend// Read from code ram when executingif (read_enable) begindata_out <= ram[read_addr_in];end// Output for debuggerdebug_out[23:0] <= write_address_hi;debug_out[28] <= write_address_valid;endendmodule
Go to most recent revision | Compare with Previous | Blame | View Log
