OpenCores
URL https://opencores.org/ocsvn/m1_core/m1_core/trunk

Subversion Repositories m1_core

Compare Revisions

  • This comparison shows the changes necessary to convert path
    /m1_core/trunk/hdl/rtl
    from Rev 51 to Rev 54
    Reverse comparison

Rev 51 → Rev 54

/m1_core/m1_cpu.v
0,0 → 1,2022
/*
* Simply RISC M1 Central Processing Unit
*/
 
`include "m1_defs.vh"
 
module m1_cpu (
 
// System
input sys_clock_i, // System Clock
input sys_reset_i, // System Reset
input sys_irq_i, // Interrupt Request
 
// ALU
output[31:0] alu_a_o, // ALU Operand A
output[31:0] alu_b_o, // ALU Operand B
output[4:0] alu_func_o, // ALU Function
output alu_signed_o, // ALU operation is Signed
input[32:0] alu_result_i, // ALU Result with Carry
 
// Multiplier
output reg mul_req_o, // Multiplier Request
output[31:0] mul_a_o, // Multiplier Operand A
output[31:0] mul_b_o, // Multiplier Operand B
output mul_signed_o, // Multiplication is Signed
input mul_ack_i, // Multiplier Ack
input[63:0] mul_product_i, // Multiplier Product
 
// Divider
output reg div_req_o, // Divider Request
output[31:0] div_a_o, // Divider Operand A
output[31:0] div_b_o, // Divider Operand B
output div_signed_o, // Division is Signed
input div_ack_i, // Divider Ack
input[31:0] div_quotient_i, // Divider Quotient
input[31:0] div_remainder_i, // Divider Remainder
 
// Instruction Memory
output imem_read_o, // I$ Read
output[31:0] imem_addr_o, // I$ Address
input imem_done_i, // I$ Done
input[31:0] imem_data_i, // I$ Data
 
// Data Memory
output dmem_read_o, // D$ Read
output dmem_write_o, // D$ Write
output[3:0] dmem_sel_o, // D$ Byte selector
output[31:0] dmem_addr_o, // D$ Address
output[31:0] dmem_data_o, // D$ Write Data
input dmem_done_i, // D$ Done
input[31:0] dmem_data_i // D$ Read Data
 
);
 
/*
* Registers
*/
 
// Register file
reg[31:0] GPR[31:0]; // General Purpose Registers
reg[31:0] PC; // Program Counter
reg[31:0] HI, LO; // HI and LO registers (for multiplication/division)
reg[31:0] SysCon[0:31]; // System Control registers
/*
* Pipeline latches
*/
 
// Latch 1: IF/ID
reg[31:0] if_id_opcode; // Instruction Register
reg[31:0] if_id_addr, if_id_addrnext; // Addresses of the fetched opcode and of the next one
 
// Latch 2: ID/EX
reg[31:0] id_ex_opcode;
reg[31:0] id_ex_addr, id_ex_addrnext;
reg[31:0] id_ex_addrbranch, id_ex_addrjump, id_ex_addrjr; // Evaluated jump addresses
reg[31:0] id_ex_alu_a, id_ex_alu_b; // ALU operands
reg[4:0] id_ex_alu_func; // ALU operation code
reg id_ex_alu_signed; // ALU operation is signed
reg id_ex_branch, id_ex_jump, id_ex_jr, id_ex_linked; // Instruction is a jump
reg id_ex_mult, id_ex_div; // Instruction is a multiplication/division
reg id_ex_load, id_ex_store; // Instruction is a load/store
reg[2:0] id_ex_size; // Load/store size (see defs.h)
reg[31:0] id_ex_store_value; // Store value
reg[4:0] id_ex_destreg; // Destination register (GPR number)
reg id_ex_desthi, id_ex_destlo; // Destination register (HI/LO)
reg[4:0] id_ex_destsyscon; // Destination register (System Control)
 
// Latch 3: EX/MEM
reg[31:0] ex_mem_opcode;
reg[31:0] ex_mem_addr, ex_mem_addrnext;
reg[31:0] ex_mem_addrbranch, ex_mem_addrjump, ex_mem_addrjr;
reg[63:0] ex_mem_aluout; // ALU result
reg ex_mem_carry; // ALU carry
reg ex_mem_branch, ex_mem_jump, ex_mem_jr, ex_mem_linked;
reg ex_mem_mult, ex_mem_div;
reg ex_mem_load, ex_mem_store;
reg[2:0] ex_mem_size;
reg[31:0] ex_mem_store_value;
reg[3:0] ex_mem_store_sel; // Byte Selector on Stores
reg[31:0] ex_mem_destold; // Old value for partial rewrite
reg[4:0] ex_mem_destreg;
reg ex_mem_desthi, ex_mem_destlo;
reg[4:0] ex_mem_destsyscon;
// Latch 4: MEM/WB
reg[31:0] mem_wb_opcode;
reg[31:0] mem_wb_addr, mem_wb_addrnext;
reg[63:0] mem_wb_value; // Write-back value
reg[4:0] mem_wb_destreg;
reg mem_wb_desthi, mem_wb_destlo;
reg [4:0] mem_wb_destsyscon;
 
/*
* Combinational logic
*/
 
// ALU
assign alu_a_o = id_ex_alu_a;
assign alu_b_o = id_ex_alu_b;
assign alu_func_o = id_ex_alu_func;
assign alu_signed_o = id_ex_alu_signed;
 
// Multiplier
assign mul_a_o = id_ex_alu_a;
assign mul_b_o = id_ex_alu_b;
assign mul_signed_o = id_ex_alu_signed;
wire mul_ready = (mul_req_o==mul_ack_i); // Convert ABP ack to true/false format
wire mul_busy = !mul_ready;
 
// Divider
assign div_a_o = id_ex_alu_a;
assign div_b_o = id_ex_alu_b;
assign div_signed_o = id_ex_alu_signed;
wire div_ready = (div_req_o==div_ack_i); // Convert ABP ack to true/false format
wire div_busy = !div_ready;
 
// Incremented Program Counter
wire[31:0] PCnext = PC + 4;
 
// Instruction Memory
assign imem_read_o = 1;
assign imem_addr_o = PC;
 
// Data Memory
assign dmem_addr_o = ex_mem_aluout;
assign dmem_read_o = ex_mem_load;
assign dmem_write_o = ex_mem_store;
assign dmem_data_o = ex_mem_store_value;
assign dmem_sel_o = ex_mem_store_sel;
 
// Decode fields from the Instruction Register
wire[5:0] if_id_op = if_id_opcode[31:26]; // Operation code
wire[4:0] if_id_rs = if_id_opcode[25:21]; // Source register
wire[4:0] if_id_rt = if_id_opcode[20:16]; // Target register
wire[4:0] if_id_rd = if_id_opcode[15:11]; // Destination register
wire[31:0] if_id_imm_signext = {{16{if_id_opcode[15]}}, if_id_opcode[15:0]}; // Immediate field with sign-extension
wire[31:0] if_id_imm_zeroext = {16'b0, if_id_opcode[15:0]}; // Immediate field with zero-extension
wire[25:0] if_id_index = if_id_opcode[25:0]; // Index field
wire[4:0] if_id_shamt = if_id_opcode[10:6]; // Shift amount
wire[5:0] if_id_func = if_id_opcode[5:0]; // Function
 
// True for still undecoded operations that read GPR[rs]
wire if_id_reads_rs = (
if_id_op==`OPCODE_BEQ || if_id_op==`OPCODE_BNE || if_id_op==`OPCODE_BLEZ || if_id_op==`OPCODE_BGTZ ||
if_id_op==`OPCODE_ADDI || if_id_op==`OPCODE_ADDIU || if_id_op==`OPCODE_SLTI || if_id_op==`OPCODE_SLTIU ||
if_id_op==`OPCODE_ANDI || if_id_op==`OPCODE_ORI || if_id_op==`OPCODE_XORI || if_id_op==`OPCODE_LB ||
if_id_op==`OPCODE_LH || if_id_op==`OPCODE_LWL || if_id_op==`OPCODE_LW || if_id_op==`OPCODE_LBU ||
if_id_op==`OPCODE_LHU || if_id_op==`OPCODE_LWR || if_id_op==`OPCODE_SB || if_id_op==`OPCODE_SH ||
if_id_op==`OPCODE_SWL || if_id_op==`OPCODE_SW || if_id_op==`OPCODE_SWR || (
if_id_op==`OPCODE_SPECIAL && (
if_id_func==`FUNCTION_SLLV || if_id_func==`FUNCTION_SRLV || if_id_func==`FUNCTION_SRAV ||
if_id_func==`FUNCTION_JR || if_id_func==`FUNCTION_JALR || if_id_func==`FUNCTION_MTHI ||
if_id_func==`FUNCTION_MTLO || if_id_func==`FUNCTION_MULT || if_id_func==`FUNCTION_MULTU ||
if_id_func==`FUNCTION_DIV || if_id_func==`FUNCTION_DIVU || if_id_func==`FUNCTION_ADD ||
if_id_func==`FUNCTION_ADDU || if_id_func==`FUNCTION_SUB || if_id_func==`FUNCTION_SUBU ||
if_id_func==`FUNCTION_AND || if_id_func==`FUNCTION_OR || if_id_func==`FUNCTION_XOR ||
if_id_func==`FUNCTION_NOR || if_id_func==`FUNCTION_SLT || if_id_func==`FUNCTION_SLTU
)
) || (
if_id_op==`OPCODE_BCOND && (
if_id_rt==`BCOND_BLTZ || if_id_rt==`BCOND_BGEZ || if_id_rt==`BCOND_BLTZAL || if_id_rt==`BCOND_BGEZAL
)
)
);
 
// True for still undecoded operations that read GPR[rt]
wire if_id_reads_rt = (
if_id_op==`OPCODE_BEQ || if_id_op==`OPCODE_BNE || if_id_op==`OPCODE_SB || if_id_op==`OPCODE_SH ||
if_id_op==`OPCODE_SWL || if_id_op==`OPCODE_SW || if_id_op==`OPCODE_SWR || (
if_id_op==`OPCODE_SPECIAL && (
if_id_func==`FUNCTION_SLL || if_id_func==`FUNCTION_SRL || if_id_func==`FUNCTION_SRA ||
if_id_func==`FUNCTION_SLLV || if_id_func==`FUNCTION_SRLV || if_id_func==`FUNCTION_SRAV ||
if_id_func==`FUNCTION_MULT || if_id_func==`FUNCTION_MULTU || if_id_func==`FUNCTION_DIV ||
if_id_func==`FUNCTION_DIVU || if_id_func==`FUNCTION_ADD || if_id_func==`FUNCTION_ADDU ||
if_id_func==`FUNCTION_SUB || if_id_func==`FUNCTION_SUBU || if_id_func==`FUNCTION_AND ||
if_id_func==`FUNCTION_OR || if_id_func==`FUNCTION_XOR || if_id_func==`FUNCTION_NOR ||
if_id_func==`FUNCTION_SLT || if_id_func==`FUNCTION_SLTU
)
)
);
 
// True for still undecoded operations that read the HI register
wire if_id_reads_hi = (if_id_op==`OPCODE_SPECIAL && if_id_func==`FUNCTION_MFHI);
 
// True for still undecoded operations that read the LO register
wire if_id_reads_lo = (if_id_op==`OPCODE_SPECIAL && if_id_func==`FUNCTION_MFLO);
 
// Finally detect a RAW hazard
wire raw_detected = (
(if_id_reads_rs && if_id_rs!=0 &&
(if_id_rs==id_ex_destreg || if_id_rs==ex_mem_destreg || if_id_rs==mem_wb_destreg)) ||
(if_id_reads_rt && if_id_rt!=0 &&
(if_id_rt==id_ex_destreg || if_id_rt==ex_mem_destreg || if_id_rt==mem_wb_destreg)) ||
(if_id_reads_hi && (id_ex_desthi || ex_mem_desthi || mem_wb_desthi)) ||
(if_id_reads_lo && (id_ex_destlo || ex_mem_destlo || mem_wb_destlo))
);
 
// Stall signals for all the stages
wire if_stall, id_stall, ex_stall, mem_stall, wb_stall;
assign if_stall = id_stall || !imem_done_i;
assign id_stall = ex_stall || raw_detected;
assign ex_stall = mem_stall || mul_busy || div_busy;
assign mem_stall = wb_stall || ( (dmem_read_o||dmem_write_o) && !dmem_done_i);
assign wb_stall = 0;
 
// Name the System Configuration registers
wire[31:0] BadVAddr = SysCon[`SYSCON_BADVADDR];
wire[31:0] Status = SysCon[`SYSCON_STATUS];
wire[31:0] Cause = SysCon[`SYSCON_CAUSE];
wire[31:0] EPC = SysCon[`SYSCON_EPC];
wire[31:0] PrID = SysCon[`SYSCON_PRID];
// Index for GPR initialization
integer i;
 
/*
* Sequential logic
*/
 
always @ (posedge sys_clock_i) begin
 
// Initialize all the registers
if (sys_reset_i==1) begin
 
// GPRs initialization
for(i=0; i<=31; i=i+1) GPR[i] <= 32'h00000000;
 
// System registers
PC <= `BOOT_ADDRESS;
HI <= 0;
LO <= 0;
 
// Initialize system configuration registers
for(i=0; i<=31; i=i+1) SysCon[i] <= 32'h00000000;
// Initialize ABP requests to instantiated modules
mul_req_o <= 0;
div_req_o <= 0;
 
// Latch 1: IF/ID
if_id_opcode <= `NOP;
if_id_addr <= `BOOT_ADDRESS;
if_id_addrnext <= 0;
 
// Latch 2: ID/EX
id_ex_opcode <= 0;
id_ex_addr <= 0;
id_ex_addrnext <= 0;
id_ex_addrjump <= 0;
id_ex_addrbranch <= 0;
id_ex_alu_a <= 0;
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <=0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
 
ex_mem_opcode <= 0;
ex_mem_addr <= 0;
ex_mem_addrnext <= 0;
ex_mem_addrjump <= 0;
ex_mem_addrbranch <= 0;
ex_mem_aluout <= 0;
ex_mem_carry <= 0;
ex_mem_branch <= 0;
ex_mem_jump <= 0;
ex_mem_jr <= 0;
ex_mem_linked <= 0;
ex_mem_mult <= 0;
ex_mem_div <= 0;
ex_mem_load <= 0;
ex_mem_store <= 0;
ex_mem_store_value <= 0;
ex_mem_store_sel <= 0;
ex_mem_destreg <= 0;
ex_mem_desthi <= 0;
ex_mem_destlo <= 0;
 
// Latch 4: MEM/WB
mem_wb_opcode <= 0;
mem_wb_addr <= 0;
mem_wb_addrnext <= 0;
mem_wb_value <= 0;
mem_wb_destreg <= 0;
mem_wb_desthi <= 0;
mem_wb_destlo <= 0;
 
end else begin
 
$display("================> Time %t <================", $time);
 
/*
* Pipeline Stage 1: Instruction Fetch (IF)
*
* READ/WRITE:
* - read memory
* - write the IF/ID latch
* - write the PC register
*
* DESCRIPTION:
* This stage usually reads the next instruction from the PC address in memory and
* then updates the PC value by incrementing it by 4.
* When a hazard is detected this stage is idle.
*/
 
// A RAW hazard will stall the CPU
if(if_stall) begin
 
if(id_stall) begin
$display("INFO: CPU(%m)-IF: Fetching stalled and latch kept for following stalled pipeline stage");
end else begin
$display("INFO: CPU(%m)-IF: Fetching stalled and bubble inserted for following running pipeline stage");
if_id_opcode <= `BUBBLE;
end
 
end else begin
 
// If branch taken update the Program Counter
if(ex_mem_branch==1 && ex_mem_aluout==32'h00000001) begin
 
$display("INFO: CPU(%m)-IF: Bubble inserted due branch taken in EX/MEM instruction @ADDR=%X w/OPCODE=%X having ALUout=%X", ex_mem_addr, ex_mem_opcode, ex_mem_aluout);
if_id_opcode <= `BUBBLE;
PC <= ex_mem_addrbranch;
 
// Jump to the required immediate address
end else if(id_ex_jump==1) begin
 
$display("INFO: CPU(%m)-IF: Bubble inserted due to jump in ID/EX instruction @ADDR=%X w/OPCODE=%X", id_ex_addr, id_ex_opcode);
if_id_opcode <= `BUBBLE;
PC <= id_ex_addrjump;
// Jump to the required address stored in GPR
end else if(id_ex_jr==1) begin
 
$display("INFO: CPU(%m)-IF: Bubble inserted due to jump register in ID/EX instruction @ADDR=%X w/OPCODE=%X", id_ex_addr, id_ex_opcode);
if_id_opcode <= `BUBBLE;
PC <= id_ex_addrjr;
// Normal execution
end else begin
 
$display("INFO: CPU(%m)-IF: Fetched from Program Counter @ADDR=%h getting OPCODE=%X", PC, imem_data_i);
if_id_opcode <= imem_data_i;
if_id_addr <= PC;
if_id_addrnext <= PCnext;
PC <= PCnext;
 
end
end
 
/*
* Pipeline Stage 2: Instruction Decode (ID)
*
* READ/WRITE:
* - read the IF/ID latch
* - read the register file
* - write the ID/EX latch
*
* DESCRIPTION:
* This stage decodes the instruction and puts the values for the ALU inputs
*/
 
if(id_stall) begin
if(ex_stall) begin
$display("INFO: CPU(%m)-ID: Decoding stalled and latch kept for following stalled pipeline stage");
end else begin
$display("INFO: CPU(%m)-ID: Decoding stalled and bubble inserted for following running pipeline stage");
id_ex_opcode <=`BUBBLE;
id_ex_alu_a <= 0;
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_addr <= if_id_addr;
id_ex_addrnext <= 0;
id_ex_addrjump <= 0;
id_ex_addrbranch <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
end else begin
id_ex_opcode <= if_id_opcode;
id_ex_addr <= if_id_addr;
id_ex_addrnext <= if_id_addrnext;
id_ex_addrbranch <= if_id_addrnext + {if_id_imm_signext[29:0], 2'b00};
id_ex_addrjump <= {if_id_addr[31:28], if_id_index, 2'b00};
id_ex_addrjr <= GPR[if_id_rs];
 
if(if_id_opcode==`BUBBLE) begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BUBBLE", if_id_addr, if_id_opcode);
id_ex_alu_a <= 0;
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end else case(if_id_op)
`OPCODE_J:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as J %h", if_id_addr, if_id_opcode, if_id_index);
id_ex_alu_a <= 0;
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 1;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_JAL:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as JAL %h", if_id_addr, if_id_opcode, if_id_index);
id_ex_alu_a <= if_id_addrnext;
id_ex_alu_b <= 4;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 1;
id_ex_jr <= 0;
id_ex_linked <= 1;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 31;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_BEQ:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BEQ r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_rt, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_SEQ;
id_ex_alu_signed <= 0;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_BNE:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BNE r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_rt, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_SNE;
id_ex_alu_signed <= 0;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_BLEZ:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BLEZ r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_SLE;
id_ex_alu_signed <= 0;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_BGTZ:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BGTZ r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_SGT;
id_ex_alu_signed <= 0;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_ADDI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as ADDI r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_ADDIU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as ADDIU r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_SLTI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SLTI r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_SLT;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_SLTIU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SLTIU r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_SLT;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_ANDI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as ANDI r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_rs, if_id_imm_zeroext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_zeroext;
id_ex_alu_func <= `ALU_OP_AND;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_ORI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as ORI r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_rs, if_id_imm_zeroext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_zeroext;
id_ex_alu_func <= `ALU_OP_OR;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_XORI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as XORI r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_rs, if_id_imm_zeroext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_zeroext;
id_ex_alu_func <= `ALU_OP_XOR;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LUI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LUI r%d, %h", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_zeroext);
id_ex_alu_a <= if_id_imm_zeroext;
id_ex_alu_b <= 16;
id_ex_alu_func <= `ALU_OP_SLL;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_COP0:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as COP0", if_id_addr, if_id_opcode);
end
`OPCODE_COP1:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as COP1", if_id_addr, if_id_opcode);
end
`OPCODE_COP2:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as COP2", if_id_addr, if_id_opcode);
end
`OPCODE_COP3:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as COP3", if_id_addr, if_id_opcode);
end
`OPCODE_LB:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LB r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 1;
id_ex_store <= 0;
id_ex_size <= `SIZE_BYTE;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LH:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LH r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 1;
id_ex_store <= 0;
id_ex_size <= `SIZE_HALF;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LWL:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LWL r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 1;
id_ex_store <= 0;
id_ex_size <= `SIZE_LEFT;
id_ex_store_value <= GPR[if_id_rt];
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LW:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LW r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 1;
id_ex_store <= 0;
id_ex_size <= `SIZE_WORD;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LBU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LBU r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 1;
id_ex_store <= 0;
id_ex_size <= `SIZE_BYTE;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LHU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LHU r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 1;
id_ex_store <= 0;
id_ex_size <= `SIZE_HALF;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LWR:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LWR r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 1;
id_ex_store <= 0;
id_ex_size <= `SIZE_RIGHT;
id_ex_store_value <= GPR[if_id_rt];
id_ex_destreg <= if_id_rt;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_SB:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SB r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 1;
id_ex_size <= `SIZE_BYTE;
id_ex_store_value <= GPR[if_id_rt];
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_SH:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SH r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 1;
id_ex_size <= `SIZE_HALF;
id_ex_store_value <= GPR[if_id_rt];
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_SWL:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SWL r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 1;
id_ex_size <= `SIZE_LEFT;
id_ex_store_value <= GPR[if_id_rt];
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_SW:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SW r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 1;
id_ex_size <= `SIZE_WORD;
id_ex_store_value <= GPR[if_id_rt];
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_SWR:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SWR r%d, %d(r%d)", if_id_addr, if_id_opcode, if_id_rt, if_id_imm_signext, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= if_id_imm_signext;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 1;
id_ex_size <= `SIZE_RIGHT;
id_ex_store_value <= GPR[if_id_rt];
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`OPCODE_LWC1:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LWC1", if_id_addr, if_id_opcode);
end
`OPCODE_LWC2:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LWC2", if_id_addr, if_id_opcode);
end
`OPCODE_LWC3:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as LWC3", if_id_addr, if_id_opcode);
end
`OPCODE_SWC1:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SWC1", if_id_addr, if_id_opcode);
end
`OPCODE_SWC2:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SWC2", if_id_addr, if_id_opcode);
end
`OPCODE_SWC3:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SWC3", if_id_addr, if_id_opcode);
end
`OPCODE_SPECIAL:
case(if_id_func)
`FUNCTION_SLL:
begin
if(if_id_opcode==`NOP) $display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as NOP", if_id_addr, if_id_opcode);
else $display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SLL r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rd, if_id_rt, if_id_shamt);
id_ex_alu_a <= GPR[if_id_rt];
id_ex_alu_b <= if_id_shamt;
id_ex_alu_func <= `ALU_OP_SLL;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SRL:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SRL r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rd, if_id_rt, if_id_shamt);
id_ex_alu_a <= GPR[if_id_rt];
id_ex_alu_b <= if_id_shamt;
id_ex_alu_func <= `ALU_OP_SRL;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SRA:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SRA r%d, r%d, %h", if_id_addr, if_id_opcode, if_id_rd, if_id_rt, if_id_shamt);
id_ex_alu_a <= GPR[if_id_rt];
id_ex_alu_b <= if_id_shamt;
id_ex_alu_func <= `ALU_OP_SRA;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SLLV:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SLLV r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rt, if_id_rs);
id_ex_alu_a <= GPR[if_id_rt];
id_ex_alu_b <= GPR[if_id_rs];
id_ex_alu_func <= `ALU_OP_SLL;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SRLV:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SRLV r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rt, if_id_rs);
id_ex_alu_a <= GPR[if_id_rt];
id_ex_alu_b <= GPR[if_id_rs];
id_ex_alu_func <= `ALU_OP_SRL;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SRAV:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SRAV r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rt, if_id_rs);
id_ex_alu_a <= GPR[if_id_rt];
id_ex_alu_b <= GPR[if_id_rs];
id_ex_alu_func <= `ALU_OP_SRA;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_JR:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as JR r%d", if_id_addr, if_id_opcode, if_id_rs);
id_ex_alu_a <= 0;
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 1;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_JALR:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as JALR [r%d,] r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs);
id_ex_alu_a <= if_id_addrnext;
id_ex_alu_b <= 4;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 1;
id_ex_linked <= 1;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SYSCALL:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SYSCALL", if_id_addr, if_id_opcode);
// id_ex_alu_a <= 0;
// id_ex_alu_b <= 0;
// id_ex_alu_func <= `ALU_OP_ADD;
// id_ex_alu_signed <= 0;
// id_ex_branch <= 0;
// id_ex_jump <= 0;
// id_ex_jr <= 0;
// id_ex_linked <= 0;
// id_ex_mult <= 0;
// id_ex_div <= 0;
// id_ex_load <= 0;
// id_ex_store <= 0;
// id_ex_size <= 0;
// id_ex_store_value <= 0;
// id_ex_destreg <= 0;
// id_ex_desthi <= 0;
// id_ex_destlo <= 0;
end
`FUNCTION_BREAK:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BREAK", if_id_addr, if_id_opcode);
// id_ex_alu_a <= 0;
// id_ex_alu_b <= 0;
// id_ex_alu_func <= `ALU_OP_ADD;
// id_ex_alu_signed <= 0;
// id_ex_branch <= 0;
// id_ex_jump <= 0;
// id_ex_jr <= 0;
// id_ex_linked <= 0;
// id_ex_mult <= 0;
// id_ex_div <= 0;
// id_ex_load <= 0;
// id_ex_store <= 0;
// id_ex_size <= 0;
// id_ex_store_value <= 0;
// id_ex_destreg <= 0;
// id_ex_desthi <= 0;
// id_ex_destlo <= 0;
end
`FUNCTION_MFHI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as MFHI r%d", if_id_addr, if_id_opcode, if_id_rd);
id_ex_alu_a <= HI;
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_MTHI:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as MTHI r%d", if_id_addr, if_id_opcode, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 1;
id_ex_destlo <= 0;
end
`FUNCTION_MFLO:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as MFLO r%d", if_id_addr, if_id_opcode, if_id_rd);
id_ex_alu_a <= LO;
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_MTLO:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as MTLO r%d", if_id_addr, if_id_opcode, if_id_rs);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 0;
id_ex_destlo <= 1;
end
`FUNCTION_MULT:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as MULT r%d, r%d", if_id_addr, if_id_opcode, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_MULT;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 1;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 1;
id_ex_destlo <= 1;
mul_req_o <= !mul_req_o; // Toggle the ABP request
end
`FUNCTION_MULTU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as MULTU r%d, r%d", if_id_addr, if_id_opcode, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_MULT;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 1;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 1;
id_ex_destlo <= 1;
mul_req_o <= !mul_req_o; // Toggle the ABP request
end
`FUNCTION_DIV:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as DIV r%d, r%d", if_id_addr, if_id_opcode, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_DIV;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 1;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 1;
id_ex_destlo <= 1;
div_req_o <= !div_req_o; // Toggle the ABP request
end
`FUNCTION_DIVU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as DIVU r%d, r%d", if_id_addr, if_id_opcode, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_DIV;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 1;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 0;
id_ex_desthi <= 1;
id_ex_destlo <= 1;
div_req_o <= !div_req_o; // Toggle the ABP request
end
`FUNCTION_ADD:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as ADD r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_ADDU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as ADDU r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_ADD;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SUB:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SUB r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_SUB;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SUBU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SUBU r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_SUB;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_AND:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as AND r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_AND;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_OR:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as OR r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_OR;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_XOR:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as XOR r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_XOR;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_NOR:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as NOR r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_NOR;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SLT:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SLT r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_SLT;
id_ex_alu_signed <= 1;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`FUNCTION_SLTU:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as SLTU r%d, r%d, r%d", if_id_addr, if_id_opcode, if_id_rd, if_id_rs, if_id_rt);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= GPR[if_id_rt];
id_ex_alu_func <= `ALU_OP_SLT;
id_ex_alu_signed <= 0;
id_ex_branch <= 0;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
endcase
`OPCODE_BCOND:
case(if_id_rt)
`BCOND_BLTZ:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BLTZ r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_SLT;
id_ex_alu_signed <= 1;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`BCOND_BGEZ:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BGEZ r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_SGE;
id_ex_alu_signed <= 1;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 0;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= if_id_rd;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`BCOND_BLTZAL:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BLTZAL r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <= `ALU_OP_SLT;
id_ex_alu_signed <= 1;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 1;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 31;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
`BCOND_BGEZAL:
begin
$display("INFO: CPU(%m)-ID: Decoded instruction @ADDR=%X w/OPCODE=%X as BGEZAL r%d, %h", if_id_addr, if_id_opcode, if_id_rs, if_id_imm_signext);
id_ex_alu_a <= GPR[if_id_rs];
id_ex_alu_b <= 0;
id_ex_alu_func <=`ALU_OP_SGE;
id_ex_alu_signed <= 1;
id_ex_branch <= 1;
id_ex_jump <= 0;
id_ex_jr <= 0;
id_ex_linked <= 1;
id_ex_mult <= 0;
id_ex_div <= 0;
id_ex_load <= 0;
id_ex_store <= 0;
id_ex_size <= 0;
id_ex_store_value <= 0;
id_ex_destreg <= 31;
id_ex_desthi <= 0;
id_ex_destlo <= 0;
end
endcase
 
endcase
 
end
 
/*
* Pipeline Stage 3: Execute (EX)
*
* READ/WRITE:
* - read the ID/EX latch
* - write the EX/MEM latch
*
* DESCRIPTION:
* This stage takes the result from the ALU and put it in the proper latch.
* Please note that assignments to ALU inputs are done outside since they're wires.
*/
 
if(ex_stall) begin
if(mem_stall) begin
$display("INFO: CPU(%m)-EX: Execution stalled and latch kept for following stalled pipeline stage");
end else begin
$display("INFO: CPU(%m)-EX: Execution stalled and bubble inserted for following running pipeline stage");
ex_mem_opcode <= `BUBBLE;
ex_mem_addr <= id_ex_addr;
ex_mem_addrnext <= 0;
ex_mem_destreg <= 0;
ex_mem_desthi <= 0;
ex_mem_destlo <= 0;
end
 
end else begin
// If not stalled propagate values to next latches
ex_mem_opcode <= id_ex_opcode;
ex_mem_addr <= id_ex_addr;
ex_mem_addrnext <= id_ex_addrnext;
ex_mem_addrjump <= id_ex_addrjump;
ex_mem_addrbranch <= id_ex_addrbranch;
ex_mem_branch <= id_ex_branch;
ex_mem_jump <= id_ex_jump;
ex_mem_jr <= id_ex_jr;
ex_mem_linked <= id_ex_linked;
ex_mem_mult <= id_ex_mult;
ex_mem_div <= id_ex_div;
ex_mem_load <= id_ex_load;
ex_mem_store <= id_ex_store;
ex_mem_size <= id_ex_size;
ex_mem_destold <= id_ex_store_value;
ex_mem_destreg <= id_ex_destreg;
ex_mem_desthi <= id_ex_desthi;
ex_mem_destlo <= id_ex_destlo;
 
// Choose the output from ALU, Multiplier or Divider
if(id_ex_mult) begin
ex_mem_aluout <= mul_product_i;
ex_mem_carry <= 1'b0;
end else if(id_ex_div) begin
ex_mem_aluout <= { div_remainder_i, div_quotient_i };
ex_mem_carry <= 1'b0;
end else begin
ex_mem_aluout <= {32'b0, alu_result_i[31:0]};
ex_mem_carry <= alu_result_i[32];
end
 
// Handle all supported store sizes
if(id_ex_store) begin
$display("INFO: CPU(%m)-EX: Execution of Store instruction @ADDR=%X w/OPCODE=%X started to STORE_ADDR=%X w/STORE_DATA=%X", id_ex_addr, id_ex_opcode, alu_result_i, id_ex_store_value);
case(id_ex_size)
`SIZE_WORD: begin
ex_mem_store_value <= id_ex_store_value;
ex_mem_store_sel <= 4'b1111;
end
`SIZE_HALF: begin
if(alu_result_i[1]==0) begin
ex_mem_store_value <= {{16'b0}, id_ex_store_value[15:0]};
ex_mem_store_sel <= 4'b0011;
end else begin
ex_mem_store_value <= {id_ex_store_value[15:0], {16'b0}};
ex_mem_store_sel <= 4'b1100;
end
end
`SIZE_BYTE: begin
case(alu_result_i[1:0])
2'b00: begin
ex_mem_store_value <= {{24'b0}, id_ex_store_value[7:0]};
ex_mem_store_sel <= 4'b0001;
end
2'b01: begin
ex_mem_store_value <= {{16'b0}, id_ex_store_value[7:0],{8'b0}};
ex_mem_store_sel <= 4'b0010;
end
2'b10: begin
ex_mem_store_value <= {{8'b0}, id_ex_store_value[7:0],{16'b0}};
ex_mem_store_sel <= 4'b0100;
end
2'b11: begin
ex_mem_store_value <= {id_ex_store_value[7:0], {24'b0}};
ex_mem_store_sel <= 4'b1000;
end
endcase
end
`SIZE_LEFT: begin
case(alu_result_i[1:0])
2'b00: begin
ex_mem_store_value <= {24'b0, id_ex_store_value[31:24]};
ex_mem_store_sel <= 4'b0001;
end
2'b01: begin
ex_mem_store_value <= {16'b0, id_ex_store_value[31:16]};
ex_mem_store_sel <= 4'b0011;
end
2'b10: begin
ex_mem_store_value <= {8'b0, id_ex_store_value[31:8]};
ex_mem_store_sel <= 4'b0111;
end
2'b11: begin
ex_mem_store_value <= id_ex_store_value;
ex_mem_store_sel <= 4'b1111;
end
endcase
end
`SIZE_RIGHT: begin
case(alu_result_i[1:0])
2'b00: begin
ex_mem_store_value <= id_ex_store_value;
ex_mem_store_sel <= 4'b1111;
end
2'b01: begin
ex_mem_store_value <= {id_ex_store_value[23:0], 8'b0};
ex_mem_store_sel <= 4'b1110;
end
2'b10: begin
ex_mem_store_value <= {id_ex_store_value[15:0], 16'b0};
ex_mem_store_sel <= 4'b1100;
end
2'b11: begin
ex_mem_store_value <= {id_ex_store_value[7:0], 24'b0};
ex_mem_store_sel <= 4'b1000;
end
endcase
end
endcase
 
// Not a store
end else begin
$display("INFO: CPU(%m)-EX: Execution of instruction @ADDR=%X w/OPCODE=%X gave ALU result %X", id_ex_addr, id_ex_opcode, alu_result_i);
end
 
end
 
/*
* Pipeline Stage 4: Memory access (MEM)
*
* READ/WRITE:
* - read the EX/MEM latch
* - read or write memory
* - write the MEM/WB latch
*
* DESCRIPTION:
* This stage perform accesses to memory to read/write the data during
* the load/store operations.
*/
 
if(mem_stall) begin
 
$display("INFO: CPU(%m)-MEM: Memory stalled");
 
end else begin
 
mem_wb_opcode <= ex_mem_opcode;
mem_wb_addr <= ex_mem_addr;
mem_wb_addrnext <= ex_mem_addrnext;
mem_wb_destreg <= ex_mem_destreg;
mem_wb_desthi <= ex_mem_desthi;
mem_wb_destlo <= ex_mem_destlo;
 
// Handle all supported load sizes
if(ex_mem_load) begin
 
$display("INFO: CPU(%m)-MEM: Loading value %X", dmem_data_i);
mem_wb_value[63:32] <= 32'b0;
case(ex_mem_size)
`SIZE_WORD: begin
mem_wb_value[31:0] <= dmem_data_i;
end
`SIZE_HALF: begin
if(ex_mem_aluout[1]==0) mem_wb_value[31:0] <= {{16{dmem_data_i[15]}}, dmem_data_i[15:0]};
else mem_wb_value[31:0] <= {{16{dmem_data_i[31]}}, dmem_data_i[31:16]};
end
`SIZE_BYTE: begin
case(ex_mem_aluout[1:0])
2'b00: mem_wb_value[31:0] <= {{24{dmem_data_i[7]}}, dmem_data_i[7:0]};
2'b01: mem_wb_value[31:0] <= {{24{dmem_data_i[15]}}, dmem_data_i[15:8]};
2'b10: mem_wb_value[31:0] <= {{24{dmem_data_i[23]}}, dmem_data_i[23:16]};
2'b11: mem_wb_value[31:0] <= {{24{dmem_data_i[31]}}, dmem_data_i[31:24]};
endcase
end
`SIZE_LEFT: begin
case(ex_mem_aluout[1:0])
2'b00: mem_wb_value[31:0] <= {dmem_data_i[7:0], ex_mem_destold[23:0]};
2'b01: mem_wb_value[31:0] <= {dmem_data_i[15:0], ex_mem_destold[15:0]};
2'b10: mem_wb_value[31:0] <= {dmem_data_i[23:0], ex_mem_destold[7:0]};
2'b11: mem_wb_value[31:0] <= dmem_data_i;
endcase
end
`SIZE_RIGHT: begin
case(ex_mem_aluout[1:0])
2'b00: mem_wb_value[31:0] <= dmem_data_i;
2'b01: mem_wb_value[31:0] <= {ex_mem_destold[31:24], dmem_data_i[31:8]};
2'b10: mem_wb_value[31:0] <= {ex_mem_destold[31:16], dmem_data_i[31:16]};
2'b11: mem_wb_value[31:0] <= {ex_mem_destold[31:8], dmem_data_i[31:24]};
endcase
end
endcase
 
// For multiplications and divisions the result is 64-bit wide
end else if (ex_mem_desthi && ex_mem_destlo) begin
 
$display("INFO: CPU(%m)-MEM: Propagating value %X", ex_mem_aluout);
mem_wb_value[63:32] <= ex_mem_aluout[63:32];
mem_wb_value[31:0] <= ex_mem_aluout[31:0];
 
// For MTHI instruction we must move the value to the correct side of the bus
end else if (ex_mem_desthi) begin
 
$display("INFO: CPU(%m)-MEM: Propagating value %X", ex_mem_aluout);
mem_wb_value[63:32] <= ex_mem_aluout[31:0];
mem_wb_value[31:0] <= 32'b0;
 
// The default is working with 32-bit values
end else begin
 
$display("INFO: CPU(%m)-MEM: Propagating value %X", ex_mem_aluout);
mem_wb_value[63:32] <= 32'b0;
mem_wb_value[31:0] <= ex_mem_aluout[31:0];
 
end
 
end
 
/*
* Pipeline Stage 5: Write Back (WB)
*
* READ/WRITE:
* - read the MEM/WB latch
* - write the register file
*
* DESCRIPTION:
* This stage writes back the result into the proper register (GPR, HI, LO).
*/
 
if(wb_stall) begin
 
$display("INFO: CPU(%m)-WB: Write-Back stalled");
 
end else begin
 
// GPRs
if(mem_wb_destreg!=0) begin
$display("INFO: CPU(%m)-WB: Writing Back GPR[%d]=%X", mem_wb_destreg, mem_wb_value[31:0]);
GPR[mem_wb_destreg] <= mem_wb_value[31:0];
end
 
// HI
if(mem_wb_desthi) begin
$display("INFO: CPU(%m)-WB: Writing Back HI=%X", mem_wb_value[63:32]);
HI <= mem_wb_value[63:32];
end
 
// LO
if(mem_wb_destlo) begin
$display("INFO: CPU(%m)-WB: Writing Back LO=%X", mem_wb_value[31:0]);
LO <= mem_wb_value[31:0];
end
 
// SysCon
if(mem_wb_destsyscon!=0) begin
$display("INFO: CPU(%m)-WB: Writing Back SysCon[%d]=%X", mem_wb_destsyscon, mem_wb_value[31:0]);
SysCon[mem_wb_destsyscon] <= mem_wb_value[31:0];
end
// Idle
if(mem_wb_destreg==0 & mem_wb_desthi==0 & mem_wb_destlo==0)
$display("INFO: CPU(%m)-WB: Write-Back has nothing to do");
 
end
 
// Display register file at each raising edge
$display("INFO: CPU(%m)-Regs: R00=%X R01=%X R02=%X R03=%X R04=%X R05=%X R06=%X R07=%X",
GPR[0], GPR[1], GPR[2], GPR[3], GPR[4], GPR[5], GPR[6], GPR[7]);
$display("INFO: CPU(%m)-Regs: R08=%X R09=%X R10=%X R11=%X R12=%X R13=%X R14=%X R15=%X",
GPR[8], GPR[9], GPR[10], GPR[11], GPR[12], GPR[13], GPR[14], GPR[15]);
$display("INFO: CPU(%m)-Regs: R16=%X R17=%X R18=%X R19=%X R20=%X R21=%X R22=%X R23=%X",
GPR[16], GPR[17], GPR[18], GPR[19], GPR[20], GPR[21], GPR[22], GPR[23]);
$display("INFO: CPU(%m)-Regs: R24=%X R25=%X R26=%X R27=%X R28=%X R29=%X R30=%X R31=%X",
GPR[24], GPR[25], GPR[26], GPR[27], GPR[28], GPR[29], GPR[30], GPR[31]);
$display("INFO: CPU(%m)-Regs: PC=%X HI=%X LO=%X",
PC, HI, LO);
 
end
end
 
endmodule
 
/m1_core/m1_alu.v
0,0 → 1,56
/*
* Simply RISC M1 Arithmetic-Logic Unit
*
* Simple RTL-level ALU with Alternating Bit Protocol (ABP) interface.
*/
 
`include "m1_defs.vh"
 
// Combinational ALU with 32-bit operands
module m1_alu(
input[31:0] a_i, // Operand A
input[31:0] b_i, // Operand B
input[4:0] func_i, // Function to be performed
input signed_i, // Operation is signed
output reg[32:0] result_o // 33-bit result (uppermost bit is the carry)
);
 
// ALU Logic
always @(a_i or b_i or func_i or signed_i) begin
case(func_i)
 
// Shift instructions
`ALU_OP_SLL: result_o = {1'b0, a_i << b_i[4:0]};
`ALU_OP_SRL: result_o = {1'b0, a_i >> b_i[4:0]};
`ALU_OP_SRA: result_o = {1'b0, {{32{a_i[31]}}, a_i } >> b_i[4:0]};
 
// Arithmetical instructions
`ALU_OP_ADD: if(signed_i) result_o = a_i + b_i; // Result may include a carry bit
else result_o = {1'b0, a_i + b_i};
`ALU_OP_SUB: if(signed_i) result_o = a_i - b_i; // Result may include a carry bit
else result_o = {1'b0, a_i - b_i};
 
// Logical instructions
`ALU_OP_AND: result_o = {1'b0, a_i & b_i};
`ALU_OP_OR: result_o = {1'b0, a_i | b_i};
`ALU_OP_XOR: result_o = {1'b0, a_i ^ b_i};
`ALU_OP_NOR: result_o = {1'b0, ~(a_i | b_i)};
 
// Conditional instructions
`ALU_OP_SEQ: result_o = (a_i == b_i) ? 33'b1 : 33'b0;
`ALU_OP_SNE: result_o = (a_i != b_i) ? 33'b1 : 33'b0;
`ALU_OP_SLT: if(signed_i) result_o = ({~a_i[31],a_i[30:0]} < {~b_i[31],b_i[30:0]}) ? 33'b1 : 33'b0;
else result_o = (a_i < b_i) ? 33'b1 : 33'b0;
`ALU_OP_SLE: if(signed_i) result_o = ({~a_i[31],a_i[30:0]} <= {~b_i[31],b_i[30:0]}) ? 33'b1 : 33'b0;
else result_o = (a_i <= b_i) ? 33'b1 : 33'b0;
`ALU_OP_SGT: if(signed_i) result_o = ({~a_i[31],a_i[30:0]} > {~b_i[31],b_i[30:0]}) ? 33'b1 : 33'b0;
else result_o = (a_i > b_i) ? 33'b1 : 33'b0;
`ALU_OP_SGE: if(signed_i) result_o = ({~a_i[31],a_i[30:0]} >= {~b_i[31],b_i[30:0]}) ? 33'b1 : 33'b0;
else result_o = (a_i >= b_i) ? 33'b1 : 33'b0;
default: result_o = 33'b0;
endcase
end
 
endmodule
 
/m1_core/m1_core.v
0,0 → 1,193
/*
* Simply RISC M1 Core Top-Level
*
* Schematic with instances of CPU, ALU, Mul, Div and MMU
*/
 
module m1_core (
 
// System
input sys_clock_i, // System clock
input sys_reset_i, // System reset
input sys_irq_i, // Interrupt Request
 
// Wishbone master interface
output wb_cyc_o, // WB Cycle
output wb_stb_o, // WB Strobe
output wb_we_o, // WB Write Enable
output[31:0] wb_adr_o, // WB Address
output[31:0] wb_dat_o, // WB Data Out
output[3:0] wb_sel_o, // WB Byte Select
input wb_ack_i, // WB Ack
input[31:0] wb_dat_i // WB Data In
 
);
/*
* Wires
*/
 
// ALU
wire[31:0] alu_a;
wire[31:0] alu_b;
wire[4:0] alu_func;
wire alu_signed;
wire[32:0] alu_result;
 
// Multiplier
wire mul_req;
wire[31:0] mul_a;
wire[31:0] mul_b;
wire mul_signed;
wire mul_ack;
wire[63:0] mul_product;
 
// Divider
wire div_req;
wire[31:0] div_a;
wire[31:0] div_b;
wire div_signed;
wire div_ack;
wire[31:0] div_quotient;
wire[31:0] div_remainder;
 
// Instruction Memory
wire imem_read;
wire[31:0] imem_addr;
wire imem_done;
wire[31:0] imem_data;
 
// Data Memory
wire dmem_read;
wire dmem_write;
wire[31:0] dmem_addr;
wire[31:0] dmem_data_w;
wire[3:0] dmem_sel;
wire dmem_done;
wire[31:0] dmem_data_r;
 
/*
* Module instances
*/
 
// CPU
m1_cpu m1_cpu_0 (
 
// System
.sys_clock_i(sys_clock_i),
.sys_reset_i(sys_reset_i),
.sys_irq_i(sys_irq_i),
 
// ALU
.alu_a_o(alu_a),
.alu_b_o(alu_b),
.alu_func_o(alu_func),
.alu_signed_o(alu_signed),
.alu_result_i(alu_result),
 
// Multiplier
.mul_req_o(mul_req),
.mul_a_o(mul_a),
.mul_b_o(mul_b),
.mul_signed_o(mul_signed),
.mul_ack_i(mul_ack),
.mul_product_i(mul_product),
 
// Divider
.div_req_o(div_req),
.div_a_o(div_a),
.div_b_o(div_b),
.div_signed_o(div_signed),
.div_ack_i(div_ack),
.div_quotient_i(div_quotient),
.div_remainder_i(div_remainder),
 
// Instruction Memory
.imem_read_o(imem_read),
.imem_addr_o(imem_addr),
.imem_data_i(imem_data),
.imem_done_i(imem_done),
 
// Data Memory
.dmem_read_o(dmem_read),
.dmem_write_o(dmem_write),
.dmem_sel_o(dmem_sel),
.dmem_addr_o(dmem_addr),
.dmem_data_o(dmem_data_w),
.dmem_data_i(dmem_data_r),
.dmem_done_i(dmem_done)
 
);
 
// ALU
m1_alu m1_alu_0 (
.a_i(alu_a),
.b_i(alu_b),
.func_i(alu_func),
.signed_i(alu_signed),
.result_o(alu_result)
);
 
// Multiplier
m1_mul m1_mul_0 (
.sys_reset_i(sys_reset_i),
.sys_clock_i(sys_clock_i),
 
.abp_req_i(mul_req),
.a_i(mul_a),
.b_i(mul_b),
.signed_i(mul_signed),
.abp_ack_o(mul_ack),
.product_o(mul_product)
);
 
// Divider
m1_div m1_div_0 (
.sys_reset_i(sys_reset_i),
.sys_clock_i(sys_clock_i),
 
.abp_req_i(div_req),
.a_i(div_a),
.b_i(div_b),
.signed_i(div_signed),
.abp_ack_o(div_ack),
.quotient_o(div_quotient),
.remainder_o(div_remainder)
);
 
// MMU
m1_mmu m1_mmu_0 (
 
// System
.sys_clock_i(sys_clock_i),
.sys_reset_i(sys_reset_i),
 
// Instruction Memory
.imem_read_i(imem_read),
.imem_addr_i(imem_addr),
.imem_data_o(imem_data),
.imem_done_o(imem_done),
 
// Data Memory
.dmem_read_i(dmem_read),
.dmem_write_i(dmem_write),
.dmem_sel_i(dmem_sel),
.dmem_addr_i(dmem_addr),
.dmem_data_i(dmem_data_w),
.dmem_data_o(dmem_data_r),
.dmem_done_o(dmem_done),
 
// Wishbone master interface
.wb_cyc_o(wb_cyc_o),
.wb_stb_o(wb_stb_o),
.wb_we_o(wb_we_o),
.wb_adr_o(wb_adr_o),
.wb_dat_o(wb_dat_o),
.wb_sel_o(wb_sel_o),
.wb_ack_i(wb_ack_i),
.wb_dat_i(wb_dat_i)
 
);
 
endmodule
 
/m1_core/m1_defs.vh
0,0 → 1,126
/*
* Simply RISC M1 Defines
*/
 
// Useful constants
`define NOP 32'h00000000
`define BUBBLE 32'hFFFFFFFF
`define BOOT_ADDRESS 32'h00000000 /* could be 32'hBFC00000 */
`define STACK_TOP 32'h00000FF0 /* for 4 KBytes Internal SRAM */
 
// Load/Store size
`define SIZE_BYTE 3'b000
`define SIZE_HALF 3'b001
`define SIZE_WORD 3'b011
`define SIZE_LEFT 3'b100
`define SIZE_RIGHT 3'b101
 
// System Configuration Coprocessor (CP0) registers for TLB-less systems
`define SYSCON_BADVADDR 8
`define SYSCON_STATUS 12
`define SYSCON_CAUSE 13
`define SYSCON_EPC 14
`define SYSCON_PRID 15
 
// Opcodes (ordered by binary value)
`define OPCODE_SPECIAL 6'b000000 // SPECIAL instruction class
`define OPCODE_BCOND 6'b000001 // BCOND instruction class
`define OPCODE_J 6'b000010 // Jump
`define OPCODE_JAL 6'b000011 // Jump and link
`define OPCODE_BEQ 6'b000100 // Branch on equal
`define OPCODE_BNE 6'b000101 // Branch on not equal
`define OPCODE_BLEZ 6'b000110 // Branch on less than or equal to zero
`define OPCODE_BGTZ 6'b000111 // Branch on greater than zero
`define OPCODE_ADDI 6'b001000 // Add immediate
`define OPCODE_ADDIU 6'b001001 // Add immediate unsigned
`define OPCODE_SLTI 6'b001010 // Set on less than immediate
`define OPCODE_SLTIU 6'b001011 // Set on less than immediate unsigned
`define OPCODE_ANDI 6'b001100 // Bitwise AND immediate
`define OPCODE_ORI 6'b001101 // Bitwise OR immediate
`define OPCODE_XORI 6'b001110 // Bitwise XOR immediate
`define OPCODE_LUI 6'b001111 // Load upper immediate
`define OPCODE_COP0 6'b010000 // Coprocessor 0 Operation TODO
`define OPCODE_COP1 6'b010001 // Coprocessor 1 Operation (optional)
`define OPCODE_COP2 6'b010010 // Coprocessor 2 Operation (optional)
`define OPCODE_COP3 6'b010011 // Coprocessor 3 Operation (optional)
`define OPCODE_LB 6'b100000 // Load byte
`define OPCODE_LH 6'b100001 // Load halfword
`define OPCODE_LWL 6'b100010 // Load word left TODO
`define OPCODE_LW 6'b100011 // Load word
`define OPCODE_LBU 6'b100100 // Load byte unsigned
`define OPCODE_LHU 6'b100101 // Load halfword unsigned
`define OPCODE_LWR 6'b100110 // Load word right TODO
`define OPCODE_SB 6'b101000 // Store byte
`define OPCODE_SH 6'b101001 // Store halfword
`define OPCODE_SWL 6'b101010 // Store word left TODO
`define OPCODE_SW 6'b101011 // Store word
`define OPCODE_SWR 6'b101110 // Store word right TODO
`define OPCODE_LWC1 6'b110001 // Load word to Coprocessor 1 (optional)
`define OPCODE_LWC2 6'b110010 // Load word to Coprocessor 2 (optional)
`define OPCODE_LWC3 6'b110011 // Load word to Coprocessor 3 (optional)
`define OPCODE_SWC1 6'b111001 // Store word from Coprocessor 1 (optional)
`define OPCODE_SWC2 6'b111010 // Store word from Coprocessor 2 (optional)
`define OPCODE_SWC3 6'b111011 // Store word from Coprocessor 3 (optional)
 
// SPECIAL instruction class functions (ordered by binary value)
`define FUNCTION_SLL 6'b000000 // Shift left logical
`define FUNCTION_SRL 6'b000010 // Shift right logical
`define FUNCTION_SRA 6'b000011 // Shift right arithmetic
`define FUNCTION_SLLV 6'b000100 // Shift left logical variable
`define FUNCTION_SRLV 6'b000110 // Shift right logical variable
`define FUNCTION_SRAV 6'b000111 // Shift right arithmetic variable
`define FUNCTION_JR 6'b001000 // Jump register
`define FUNCTION_JALR 6'b001001 // Jump and link register
`define FUNCTION_SYSCALL 6'b001100 // System call TODO
`define FUNCTION_BREAK 6'b001101 // Breakpoint TODO
`define FUNCTION_MFHI 6'b010000 // Move from HI register TODO
`define FUNCTION_MTHI 6'b010001 // Move to HI register TODO
`define FUNCTION_MFLO 6'b010010 // Move from LO register TODO
`define FUNCTION_MTLO 6'b010011 // Move to LO register TODO
`define FUNCTION_MULT 6'b011000 // Multiply TODO
`define FUNCTION_MULTU 6'b011001 // Multiply unsigned TODO
`define FUNCTION_DIV 6'b011010 // Divide TODO
`define FUNCTION_DIVU 6'b011011 // Divide unsigned TODO
`define FUNCTION_ADD 6'b100000 // Add
`define FUNCTION_ADDU 6'b100001 // Add unsigned
`define FUNCTION_SUB 6'b100010 // Subtract
`define FUNCTION_SUBU 6'b100011 // Subtract unsigned
`define FUNCTION_AND 6'b100100 // Bitwise AND
`define FUNCTION_OR 6'b100101 // Bitwise OR
`define FUNCTION_XOR 6'b100110 // Bitwise XOR
`define FUNCTION_NOR 6'b100111 // Bitwise NOR
`define FUNCTION_SLT 6'b101010 // Set on less than
`define FUNCTION_SLTU 6'b101011 // Set on less than unsigned
 
// BCOND instruction class rt fields (ordered by binary value)
`define BCOND_BLTZ 5'b00000 // Branch on less than zero
`define BCOND_BGEZ 5'b00001 // Branch on greater than or equal to zero
`define BCOND_BLTZAL 5'b10000 // Branch on less than zero and link
`define BCOND_BGEZAL 5'b10001 // Branch on greater than or equal to zero and link
 
// Coprocessors instruction class rs fields (ordered by binary value)
`define COP_MFCz 5'b00000 // Move from Coprocessor z
`define COP_CFCz 5'b00010 // Copy from Coprocessor z
`define COP_MTCz 5'b00100 // Move to Coprocessor z
`define COP_CTCz 5'b00110 // Copy to Coprocessor z
`define COP_BCOND 5'b01000 // Branch condition for Coprocessor z
 
// ALU operation codes used internally (please note that signed/unsigned is another input)
`define ALU_OP_SLL 5'b00001
`define ALU_OP_SRL 5'b00010
`define ALU_OP_SRA 5'b00011
`define ALU_OP_ADD 5'b00100
`define ALU_OP_SUB 5'b00101
`define ALU_OP_AND 5'b00110
`define ALU_OP_OR 5'b00111
`define ALU_OP_XOR 5'b01000
`define ALU_OP_NOR 5'b01001
`define ALU_OP_SEQ 5'b01010
`define ALU_OP_SNE 5'b01011
`define ALU_OP_SLT 5'b01100
`define ALU_OP_SLE 5'b01101
`define ALU_OP_SGT 5'b01110
`define ALU_OP_SGE 5'b01111
`define ALU_OP_MULT 5'b10000
`define ALU_OP_DIV 5'b10001
 
/m1_core/m1_mmu.v
0,0 → 1,82
/*
* Simply RISC M1 Memory Management Unit
*
* This block converts Harvard architecture requests to access the
* small internal prefetch buffer, and just in case the external
* Wishbone bus.
* Memory size is 256 word * 4 byte = 1024 byte,
* so 10 address bits are required => [9:0]
* and being the lower 2 bits unused the offset in memory is [9:2].
*/
 
module m1_mmu (
 
// System
input sys_clock_i, // System Clock
input sys_reset_i, // System Reset
 
// Instruction Memory
input imem_read_i, // I$ Read
input[31:0] imem_addr_i, // I$ Address
output imem_done_o, // I$ Done
output[31:0] imem_data_o, // I$ Data
 
// Data Memory
input dmem_read_i, // D$ Read
input dmem_write_i, // D$ Write
input[31:0] dmem_addr_i, // D$ Address
input[31:0] dmem_data_i, // D$ Write Data
input[3:0] dmem_sel_i, // D$ Byte selector
output dmem_done_o, // D$ Done
output[31:0] dmem_data_o, // D$ Read Data
 
// Wishbone Master interface
output wb_cyc_o, // Cycle Start
output wb_stb_o, // Strobe Request
output wb_we_o, // Write Enable
output[31:0] wb_adr_o, // Address Bus
output[31:0] wb_dat_o, // Data Out
output[3:0] wb_sel_o, // Byte Select
input wb_ack_i, // Ack
input[31:0] wb_dat_i // Data In
 
);
 
/*
* Registers
*/
 
// Prefetch buffer
reg[31:0] MEM[255:0];
 
// Initialize memory content
initial begin
`include "m1_mmu_initial.vh"
end
 
/*
* Wires
*/
 
// See if there are pending requests
wire access_pending_imem = imem_read_i;
wire access_pending_dmem = 0;
wire access_pending_ext = (dmem_read_i || dmem_write_i);
 
// Default grant for memories
assign imem_done_o = access_pending_imem;
assign dmem_done_o = access_pending_dmem || (access_pending_ext && wb_ack_i);
 
// Set Wishbone outputs
assign wb_cyc_o = access_pending_ext;
assign wb_stb_o = access_pending_ext;
assign wb_we_o = access_pending_ext && dmem_write_i;
assign wb_sel_o = dmem_sel_i;
assign wb_adr_o = dmem_addr_i;
assign wb_dat_o = dmem_data_i;
 
// Return read data
assign imem_data_o = MEM[imem_addr_i[9:2]];
assign dmem_data_o = wb_dat_i;
 
endmodule
/m1_core/m1_mmu_initial.vh
0,0 → 1,257
/* THIS FILE IS GENERATED AUTOMATICALLY BY THE compile_test SCRIPT */
MEM[0] <= 32'h201d1000;
MEM[1] <= 32'h3c1fdead;
MEM[2] <= 32'h37ffbeef;
MEM[3] <= 32'h00000000;
MEM[4] <= 32'h27bdffe8;
MEM[5] <= 32'hafbe0010;
MEM[6] <= 32'h03a0f021;
MEM[7] <= 32'h3c02faba;
MEM[8] <= 32'h34421210;
MEM[9] <= 32'hafc20008;
MEM[10] <= 32'h8fc30008;
MEM[11] <= 32'h24020048;
MEM[12] <= 32'hac620000;
MEM[13] <= 32'h8fc30008;
MEM[14] <= 32'h24020065;
MEM[15] <= 32'hac620000;
MEM[16] <= 32'h8fc30008;
MEM[17] <= 32'h2402006c;
MEM[18] <= 32'hac620000;
MEM[19] <= 32'h8fc30008;
MEM[20] <= 32'h2402006c;
MEM[21] <= 32'hac620000;
MEM[22] <= 32'h8fc30008;
MEM[23] <= 32'h2402006f;
MEM[24] <= 32'hac620000;
MEM[25] <= 32'h8fc30008;
MEM[26] <= 32'h24020021;
MEM[27] <= 32'hac620000;
MEM[28] <= 32'h8fc30008;
MEM[29] <= 32'h2402000a;
MEM[30] <= 32'hac620000;
MEM[31] <= 32'h00001021;
MEM[32] <= 32'h03c0e821;
MEM[33] <= 32'h8fbe0010;
MEM[34] <= 32'h27bd0018;
MEM[35] <= 32'h03e00008;
MEM[36] <= 32'h00000000;
MEM[37] <= 32'h00000000;
MEM[38] <= 32'h00000000;
MEM[39] <= 32'h00000000;
MEM[40] <= 32'h00000000;
MEM[41] <= 32'h00000000;
MEM[42] <= 32'h00000000;
MEM[43] <= 32'h00000000;
MEM[44] <= 32'h00000000;
MEM[45] <= 32'h00000000;
MEM[46] <= 32'h00000000;
MEM[47] <= 32'h00000000;
MEM[48] <= 32'h00000000;
MEM[49] <= 32'h00000000;
MEM[50] <= 32'h00000000;
MEM[51] <= 32'h00000000;
MEM[52] <= 32'h00000000;
MEM[53] <= 32'h00000000;
MEM[54] <= 32'h00000000;
MEM[55] <= 32'h00000000;
MEM[56] <= 32'h00000000;
MEM[57] <= 32'h00000000;
MEM[58] <= 32'h00000000;
MEM[59] <= 32'h00000000;
MEM[60] <= 32'h00000000;
MEM[61] <= 32'h00000000;
MEM[62] <= 32'h00000000;
MEM[63] <= 32'h00000000;
MEM[64] <= 32'h00000000;
MEM[65] <= 32'h00000000;
MEM[66] <= 32'h00000000;
MEM[67] <= 32'h00000000;
MEM[68] <= 32'h00000000;
MEM[69] <= 32'h00000000;
MEM[70] <= 32'h00000000;
MEM[71] <= 32'h00000000;
MEM[72] <= 32'h00000000;
MEM[73] <= 32'h00000000;
MEM[74] <= 32'h00000000;
MEM[75] <= 32'h00000000;
MEM[76] <= 32'h00000000;
MEM[77] <= 32'h00000000;
MEM[78] <= 32'h00000000;
MEM[79] <= 32'h00000000;
MEM[80] <= 32'h00000000;
MEM[81] <= 32'h00000000;
MEM[82] <= 32'h00000000;
MEM[83] <= 32'h00000000;
MEM[84] <= 32'h00000000;
MEM[85] <= 32'h00000000;
MEM[86] <= 32'h00000000;
MEM[87] <= 32'h00000000;
MEM[88] <= 32'h00000000;
MEM[89] <= 32'h00000000;
MEM[90] <= 32'h00000000;
MEM[91] <= 32'h00000000;
MEM[92] <= 32'h00000000;
MEM[93] <= 32'h00000000;
MEM[94] <= 32'h00000000;
MEM[95] <= 32'h00000000;
MEM[96] <= 32'h00000000;
MEM[97] <= 32'h00000000;
MEM[98] <= 32'h00000000;
MEM[99] <= 32'h00000000;
MEM[100] <= 32'h00000000;
MEM[101] <= 32'h00000000;
MEM[102] <= 32'h00000000;
MEM[103] <= 32'h00000000;
MEM[104] <= 32'h00000000;
MEM[105] <= 32'h00000000;
MEM[106] <= 32'h00000000;
MEM[107] <= 32'h00000000;
MEM[108] <= 32'h00000000;
MEM[109] <= 32'h00000000;
MEM[110] <= 32'h00000000;
MEM[111] <= 32'h00000000;
MEM[112] <= 32'h00000000;
MEM[113] <= 32'h00000000;
MEM[114] <= 32'h00000000;
MEM[115] <= 32'h00000000;
MEM[116] <= 32'h00000000;
MEM[117] <= 32'h00000000;
MEM[118] <= 32'h00000000;
MEM[119] <= 32'h00000000;
MEM[120] <= 32'h00000000;
MEM[121] <= 32'h00000000;
MEM[122] <= 32'h00000000;
MEM[123] <= 32'h00000000;
MEM[124] <= 32'h00000000;
MEM[125] <= 32'h00000000;
MEM[126] <= 32'h00000000;
MEM[127] <= 32'h00000000;
MEM[128] <= 32'h00000000;
MEM[129] <= 32'h00000000;
MEM[130] <= 32'h00000000;
MEM[131] <= 32'h00000000;
MEM[132] <= 32'h00000000;
MEM[133] <= 32'h00000000;
MEM[134] <= 32'h00000000;
MEM[135] <= 32'h00000000;
MEM[136] <= 32'h00000000;
MEM[137] <= 32'h00000000;
MEM[138] <= 32'h00000000;
MEM[139] <= 32'h00000000;
MEM[140] <= 32'h00000000;
MEM[141] <= 32'h00000000;
MEM[142] <= 32'h00000000;
MEM[143] <= 32'h00000000;
MEM[144] <= 32'h00000000;
MEM[145] <= 32'h00000000;
MEM[146] <= 32'h00000000;
MEM[147] <= 32'h00000000;
MEM[148] <= 32'h00000000;
MEM[149] <= 32'h00000000;
MEM[150] <= 32'h00000000;
MEM[151] <= 32'h00000000;
MEM[152] <= 32'h00000000;
MEM[153] <= 32'h00000000;
MEM[154] <= 32'h00000000;
MEM[155] <= 32'h00000000;
MEM[156] <= 32'h00000000;
MEM[157] <= 32'h00000000;
MEM[158] <= 32'h00000000;
MEM[159] <= 32'h00000000;
MEM[160] <= 32'h00000000;
MEM[161] <= 32'h00000000;
MEM[162] <= 32'h00000000;
MEM[163] <= 32'h00000000;
MEM[164] <= 32'h00000000;
MEM[165] <= 32'h00000000;
MEM[166] <= 32'h00000000;
MEM[167] <= 32'h00000000;
MEM[168] <= 32'h00000000;
MEM[169] <= 32'h00000000;
MEM[170] <= 32'h00000000;
MEM[171] <= 32'h00000000;
MEM[172] <= 32'h00000000;
MEM[173] <= 32'h00000000;
MEM[174] <= 32'h00000000;
MEM[175] <= 32'h00000000;
MEM[176] <= 32'h00000000;
MEM[177] <= 32'h00000000;
MEM[178] <= 32'h00000000;
MEM[179] <= 32'h00000000;
MEM[180] <= 32'h00000000;
MEM[181] <= 32'h00000000;
MEM[182] <= 32'h00000000;
MEM[183] <= 32'h00000000;
MEM[184] <= 32'h00000000;
MEM[185] <= 32'h00000000;
MEM[186] <= 32'h00000000;
MEM[187] <= 32'h00000000;
MEM[188] <= 32'h00000000;
MEM[189] <= 32'h00000000;
MEM[190] <= 32'h00000000;
MEM[191] <= 32'h00000000;
MEM[192] <= 32'h00000000;
MEM[193] <= 32'h00000000;
MEM[194] <= 32'h00000000;
MEM[195] <= 32'h00000000;
MEM[196] <= 32'h00000000;
MEM[197] <= 32'h00000000;
MEM[198] <= 32'h00000000;
MEM[199] <= 32'h00000000;
MEM[200] <= 32'h00000000;
MEM[201] <= 32'h00000000;
MEM[202] <= 32'h00000000;
MEM[203] <= 32'h00000000;
MEM[204] <= 32'h00000000;
MEM[205] <= 32'h00000000;
MEM[206] <= 32'h00000000;
MEM[207] <= 32'h00000000;
MEM[208] <= 32'h00000000;
MEM[209] <= 32'h00000000;
MEM[210] <= 32'h00000000;
MEM[211] <= 32'h00000000;
MEM[212] <= 32'h00000000;
MEM[213] <= 32'h00000000;
MEM[214] <= 32'h00000000;
MEM[215] <= 32'h00000000;
MEM[216] <= 32'h00000000;
MEM[217] <= 32'h00000000;
MEM[218] <= 32'h00000000;
MEM[219] <= 32'h00000000;
MEM[220] <= 32'h00000000;
MEM[221] <= 32'h00000000;
MEM[222] <= 32'h00000000;
MEM[223] <= 32'h00000000;
MEM[224] <= 32'h00000000;
MEM[225] <= 32'h00000000;
MEM[226] <= 32'h00000000;
MEM[227] <= 32'h00000000;
MEM[228] <= 32'h00000000;
MEM[229] <= 32'h00000000;
MEM[230] <= 32'h00000000;
MEM[231] <= 32'h00000000;
MEM[232] <= 32'h00000000;
MEM[233] <= 32'h00000000;
MEM[234] <= 32'h00000000;
MEM[235] <= 32'h00000000;
MEM[236] <= 32'h00000000;
MEM[237] <= 32'h00000000;
MEM[238] <= 32'h00000000;
MEM[239] <= 32'h00000000;
MEM[240] <= 32'h00000000;
MEM[241] <= 32'h00000000;
MEM[242] <= 32'h00000000;
MEM[243] <= 32'h00000000;
MEM[244] <= 32'h00000000;
MEM[245] <= 32'h00000000;
MEM[246] <= 32'h00000000;
MEM[247] <= 32'h00000000;
MEM[248] <= 32'h00000000;
MEM[249] <= 32'h00000000;
MEM[250] <= 32'h00000000;
MEM[251] <= 32'h00000000;
MEM[252] <= 32'h00000000;
MEM[253] <= 32'h00000000;
MEM[254] <= 32'h00000000;
MEM[255] <= 32'h00000000;
/m1_core/m1_div.v
0,0 → 1,82
/*
* Simply RISC M1 Divider
*
* Simple RTL-level divider with Alternating Bit Protocol (ABP) interface.
*/
 
// 32-bit / 32-bit Integer Divider (this version is not optimized and always takes 32 cycles)
module m1_div(
input sys_reset_i, // System Reset
input sys_clock_i, // System Clock
input[31:0] a_i, // Operand A
input[31:0] b_i, // Operand B
input signed_i, // If division is signed
output reg[31:0] quotient_o, // Quotient of division
output reg[31:0] remainder_o, // Remainder of division
input abp_req_i, // ABP Request
output reg abp_ack_o // ABP Acknowledgement
);
 
// Registers
reg[63:0] a_latched; // Latched 'a' input
reg[63:0] b_latched; // Latched 'b' input
reg[31:0] quotient_tmp; // Temporary result
reg[31:0] remainder_tmp; // Temporary result
reg negative_output; // If output is negative
reg[5:0] count; // Downward counter (32->0)
reg abp_last; // Level of last ABP request
reg[63:0] diff; // Difference
 
// Sequential logic
always @(posedge sys_clock_i) begin
 
// Initialization
if(sys_reset_i) begin
 
quotient_o = 0;
remainder_o = 0;
abp_ack_o = 0;
negative_output = 0;
count = 6'd0;
abp_last = 0;
 
// New request
end else if(abp_req_i!=abp_last) begin
 
abp_last = abp_req_i; // Latch level of ABP request
count = 6'd32; // Start counter
quotient_tmp = 0; // Initialize result
remainder_tmp = 0; // Initialize result
a_latched = (!signed_i || !a_i[31]) ? { 32'd0, a_i } : { 32'd0, (~a_i + 1'b1) };
b_latched = (!signed_i || !b_i[31]) ? { 1'b0, b_i, 31'd0 } : { 1'b0, ~b_i + 1'b1, 31'd0 };
negative_output = signed_i && (a_i[31] ^ b_i[31]);
quotient_o = (!negative_output) ? quotient_tmp : (~quotient_tmp+1); // Debugging only
remainder_o = (!negative_output) ? a_latched[31:0] : (~a_latched[31:0]+1); // Debugging only
// Calculating
end else if(count>0) begin
 
count = count-1;
diff = a_latched-b_latched;
quotient_tmp = quotient_tmp << 1;
if(!diff[63]) begin
a_latched = diff;
quotient_tmp[0] = 1;
end
b_latched = b_latched >> 1;
quotient_o = (!negative_output) ? quotient_tmp : (~quotient_tmp+1); // Debugging only
remainder_o = (!negative_output) ? a_latched[31:0] : (~a_latched[31:0]+1); // Debugging only
 
// Return the result
end else if(count==0) begin
 
abp_ack_o = abp_req_i; // Return the result
quotient_o = (!negative_output) ? quotient_tmp : (~quotient_tmp+1);
remainder_o = (!negative_output) ? a_latched[31:0] : (~a_latched[31:0]+1);
 
end
 
end
 
endmodule
 
/m1_core/m1_mul.v
0,0 → 1,71
/*
* Simply RISC M1 Multiplier
*
* Simple RTL-level Multiplier with Alternating Bit Protocol (ABP) interface.
*/
 
// 32-bit * 32-bit Integer Multiplier (this version is not optimized and always takes 32 cycles)
module m1_mul(
input sys_reset_i, // System Reset
input sys_clock_i, // System Clock
input[31:0] a_i, // Operand A
input[31:0] b_i, // Operand B
input signed_i, // If multiplication is signed
output reg[63:0] product_o, // Product of multiplication
input abp_req_i, // ABP Request
output reg abp_ack_o // ABP Acknowledgement
);
 
 
// Registers
reg[63:0] a_latched; // Latched 'a' input
reg[31:0] b_latched; // Latched 'b' input
reg[63:0] product_tmp; // Temporary result
reg negative_output; // If output is negative
reg[5:0] count; // Downward counter (32->0)
reg abp_last; // Level of last ABP request
 
// Sequential logic
always @(posedge sys_clock_i) begin
 
// Initialization
if(sys_reset_i) begin
 
product_o = 0;
abp_ack_o = 0;
negative_output = 0;
count = 6'd0;
abp_last = 0;
 
// New request
end else if(abp_req_i!=abp_last) begin
 
abp_last = abp_req_i; // Latch level of ABP request
count = 6'd32; // Start counter
product_tmp = 0; // Initialize result
a_latched = (!signed_i || !a_i[31]) ? { 32'd0, a_i } : { 32'd0, (~a_i+1'b1) };
b_latched = (!signed_i || !b_i[31]) ? b_i : (~b_i + 1'b1);
negative_output = signed_i && (a_i[31] ^ b_i[31]);
product_o = (!negative_output) ? product_tmp : (~product_tmp+1); // Degugging only
// Calculating
end else if(count>0) begin
 
count = count-1;
if(b_latched[0]==1) product_tmp = product_tmp + a_latched;
a_latched = a_latched << 1;
b_latched = b_latched >> 1;
product_o = (!negative_output) ? product_tmp : (~product_tmp + 1); // Debugging only
 
// Return the result
end else if(count==0) begin
 
abp_ack_o = abp_req_i; // Return the result
product_o = (!negative_output) ? product_tmp : (~product_tmp + 1);
 
end
 
end
 
endmodule
 
/spartan3esk_top/spartan3esk_top.v
0,0 → 1,262
/*
* Simply RISC M1 Core System for Xilinx Spartan-3E 500 Starter Kit
*/
 
`include "ddr_include.v"
 
module spartan3esk_top (
 
// System
input sys_clock_i,
input sys_reset_i,
 
// VGA Port
output vga_rgb_r_o,
output vga_rgb_g_o,
output vga_rgb_b_o,
output vga_hsync_o,
output vga_vsync_o,
 
// PS/2 Keyboard interface
inout ps2_keyboard_clock_io,
inout ps2_keyboard_data_io,
 
// DDR Port
output ddr_clk,
output ddr_clk_n,
input ddr_clk_fb,
output ddr_ras_n,
output ddr_cas_n,
output ddr_we_n,
output ddr_cke,
output ddr_cs_n,
output[`A_RNG] ddr_a,
output[`BA_RNG] ddr_ba,
inout[`DQ_RNG] ddr_dq,
inout[`DQS_RNG] ddr_dqs,
output[`DM_RNG] ddr_dm
 
);
 
/*
* Wires
*/
 
// Interrupts
wire sys_irq;
wire[31:0] sys_irqs;
assign sys_irqs[31:1] = 31'h00000000;
 
// Rotary interface
wire[2:0] rot = 3'b000;
 
// PS/2 Keyboard interface
wire ps2_keyboard_clock_i;
wire ps2_keyboard_data_i;
wire ps2_keyboard_clock_o;
wire ps2_keyboard_data_o;
wire ps2_keyboard_clock_padoe_o;
wire ps2_keyboard_data_padoe_o;
assign ps2_keyboard_clock_io = (ps2_keyboard_clock_padoe_o ? ps2_keyboard_clock_o : 1'bZ);
assign ps2_keyboard_data_io = (ps2_keyboard_data_padoe_o ? ps2_keyboard_data_o : 1'bZ);
 
// Wishbone interface
wire wb_cyc_core, wb_cyc_intc, wb_cyc_text, wb_cyc_ps2, wb_cyc_ddr;
wire wb_stb_core, wb_stb_intc, wb_stb_text, wb_stb_ps2, wb_stb_ddr;
wire wb_we_core, wb_we_intc, wb_we_text, wb_we_ps2, wb_we_ddr;
wire[31:0] wb_adr_core, wb_adr_intc, wb_adr_text, wb_adr_ps2, wb_adr_ddr;
wire[31:0] wb_wdat_core, wb_wdat_intc, wb_wdat_text, wb_wdat_ps2, wb_wdat_ddr;
wire[3:0] wb_sel_core, wb_sel_intc, wb_sel_text, wb_sel_ps2, wb_sel_ddr;
wire wb_ack_core, wb_ack_intc, wb_ack_text, wb_ack_ps2, wb_ack_ddr;
wire[31:0] wb_rdat_core, wb_rdat_intc, wb_rdat_text, wb_rdat_ps2, wb_rdat_ddr;
 
// The most significant byte of the address is used to select the destination
wire request_to_ddr = (wb_stb_core && wb_cyc_core && wb_adr_core[31:24]==8'h00);
wire request_to_intc = (wb_stb_core && wb_cyc_core && wb_adr_core[31:24]==8'hF8);
wire request_to_text = (wb_stb_core && wb_cyc_core && wb_adr_core[31:24]==8'hFA);
wire request_to_ps2 = (wb_stb_core && wb_cyc_core && wb_adr_core[31:24]==8'hFB);
 
// Select outputs connected to M1 Core inputs
assign wb_ack_core = (request_to_ddr ? wb_ack_ddr :
(request_to_intc ? wb_ack_intc :
(request_to_text ? wb_ack_text : wb_ack_ps2) ) );
assign wb_rdat_core = (request_to_ddr ? wb_rdat_ddr :
(request_to_intc ? wb_rdat_intc :
(request_to_text ? wb_rdat_text : wb_rdat_ps2) ) );
 
// Select outputs connected to Interrupt Controller inputs
assign wb_cyc_intc = (request_to_intc ? wb_cyc_core : 1'b0);
assign wb_stb_intc = (request_to_intc ? wb_stb_core : 1'b0);
assign wb_adr_intc = (request_to_intc ? wb_adr_core : 32'h00000000);
assign wb_we_intc = (request_to_intc ? wb_we_core : 1'b0);
assign wb_sel_intc = (request_to_intc ? wb_sel_core : 4'b0000);
assign wb_wdat_intc = (request_to_intc ? wb_wdat_core : 32'h00000000);
 
// Select outputs connected to Text-only VGA Controller inputs
assign wb_cyc_text = (request_to_text ? wb_cyc_core : 1'b0);
assign wb_stb_text = (request_to_text ? wb_stb_core : 1'b0);
assign wb_adr_text = (request_to_text ? wb_adr_core : 32'h00000000);
assign wb_we_text = (request_to_text ? wb_we_core : 1'b0);
assign wb_sel_text = (request_to_text ? wb_sel_core : 4'b0000);
assign wb_wdat_text = (request_to_text ? wb_wdat_core : 32'h00000000);
 
// Select outputs connected to PS/2 Keyboard Interface inputs
assign wb_cyc_ps2 = (request_to_ps2 ? wb_cyc_core : 1'b0);
assign wb_stb_ps2 = (request_to_ps2 ? wb_stb_core : 1'b0);
assign wb_adr_ps2 = (request_to_ps2 ? wb_adr_core : 32'h00000000);
assign wb_we_ps2 = (request_to_ps2 ? wb_we_core : 1'b0);
assign wb_sel_ps2 = (request_to_ps2 ? wb_sel_core : 4'b0000);
assign wb_wdat_ps2 = (request_to_ps2 ? wb_wdat_core : 32'h00000000);
 
// Select outputs connected to DDR Controller inputs
assign wb_cyc_ddr = (request_to_ddr ? wb_cyc_core : 1'b0);
assign wb_stb_ddr = (request_to_ddr ? wb_stb_core : 1'b0);
assign wb_adr_ddr = (request_to_ddr ? wb_adr_core : 32'h00000000);
assign wb_we_ddr = (request_to_ddr ? wb_we_core : 1'b0);
assign wb_sel_ddr = (request_to_ddr ? wb_sel_core : 4'b0000);
assign wb_wdat_ddr = (request_to_ddr ? wb_wdat_core : 32'h00000000);
 
/*
* Module instances
*/
 
// M1 Core
m1_core m1_core_0 (
 
// System
.sys_clock_i(sys_clock_i),
.sys_reset_i(sys_reset_i),
.sys_irq_i(sys_irq),
 
// Wishbone master interface
.wb_cyc_o(wb_cyc_core),
.wb_stb_o(wb_stb_core),
.wb_we_o(wb_we_core),
.wb_sel_o(wb_sel_core),
.wb_adr_o(wb_adr_core),
.wb_dat_o(wb_wdat_core),
.wb_ack_i(wb_ack_core),
.wb_dat_i(wb_rdat_core)
 
);
 
// Interrupt Controller
wb_int_ctrl wb_int_ctrl_0 (
 
// System
.sys_clock_i(sys_clock_i),
.sys_reset_i(sys_reset_i),
 
// Interrupts
.sys_irqs_i(sys_irqs),
.sys_irq_o(sys_irq),
 
// Wishbone slave interface
.wb_cyc_i(wb_cyc_intc),
.wb_stb_i(wb_stb_intc),
.wb_adr_i(wb_adr_intc),
.wb_we_i(wb_we_intc),
.wb_sel_i(wb_sel_intc),
.wb_dat_i(wb_wdat_intc),
.wb_ack_o(wb_ack_intc),
.wb_dat_o(wb_rdat_intc)
 
);
 
// Text-only VGA Controller
wb_text_vga wb_text_vga_0 (
 
// System
.sys_clock_i(sys_clock_i),
.sys_reset_i(sys_reset_i),
 
// Wishbone slave interface
.wb_cyc_i(wb_cyc_text),
.wb_stb_i(wb_stb_text),
.wb_adr_i(wb_adr_text),
.wb_we_i(wb_we_text),
.wb_sel_i(wb_sel_text),
.wb_dat_i(wb_wdat_text),
.wb_ack_o(wb_ack_text),
.wb_dat_o(wb_rdat_text),
 
// VGA Port
.vga_rgb_r_o(vga_rgb_r_o),
.vga_rgb_g_o(vga_rgb_g_o),
.vga_rgb_b_o(vga_rgb_b_o),
.vga_hsync_o(vga_hsync_o),
.vga_vsync_o(vga_vsync_o)
 
);
 
// PS/2 Keyboard Interface
ps2_top wb_ps2_keyboard_0
(
 
// System
.wb_clk_i(sys_clock_i),
.wb_rst_i(sys_reset_i),
// Wishbone slave interface
.wb_cyc_i(wb_cyc_ps2),
.wb_stb_i(wb_stb_ps2),
.wb_we_i(wb_we_ps2),
.wb_sel_i(wb_sel_ps2),
.wb_adr_i(wb_adr_ps2[3:0]),
.wb_dat_i(wb_wdat_ps2),
.wb_dat_o(wb_rdat_ps2),
.wb_ack_o(wb_ack_ps2),
 
// Interrupt
.wb_int_o(sys_irqs[0]),
 
// PS/2 Keyboard Port
.ps2_kbd_clk_pad_i(ps2_keyboard_clock_i),
.ps2_kbd_data_pad_i(ps2_keyboard_data_i),
.ps2_kbd_clk_pad_o(ps2_keyboard_clock_o),
.ps2_kbd_data_pad_o(ps2_keyboard_data_o),
.ps2_kbd_clk_pad_oe_o(ps2_keyboard_clock_padoe_o),
.ps2_kbd_data_pad_oe_o(ps2_keyboard_data_padoe_o)
 
);
// DDR Controller
wb_ddr wb_ddr_0 (
 
// System
.clk(sys_clock_i),
.reset(sys_reset_i),
 
// DDR Port
.ddr_clk(ddr_clk),
.ddr_clk_n(ddr_clk_n),
.ddr_clk_fb(ddr_clk_fb),
.ddr_ras_n(ddr_ras_n),
.ddr_cas_n(ddr_cas_n),
.ddr_we_n(ddr_we_n),
.ddr_cke(ddr_cke),
.ddr_cs_n(ddr_cs_n),
.ddr_a(ddr_a),
.ddr_ba(ddr_ba),
.ddr_dq(ddr_dq),
.ddr_dqs(ddr_dqs),
.ddr_dm(ddr_dm),
 
// Wishbone master interface
.wb_cyc_i(wb_cyc_ddr),
.wb_stb_i(wb_stb_ddr),
.wb_we_i(wb_we_ddr),
.wb_adr_i(wb_adr_ddr),
.wb_dat_o(wb_rdat_ddr),
.wb_dat_i(wb_wdat_ddr),
.wb_sel_i(wb_sel_ddr),
.wb_ack_o(wb_ack_ddr),
 
// phase shifting
.rot(rot)
 
);
 
 
endmodule
 
/spartan3esk_top/spartan3esk_top.ucf
0,0 → 1,64
### Clock ###
# Main clock running @ 50 MHz
NET "sys_clock_i" LOC = "C9" | IOSTANDARD = LVCMOS33 ;
NET "sys_clock_i" PERIOD = 20.0ns HIGH 40%;
 
### Rotary ###
# Pressing the center of the rotary switch will reset the chip
NET "sys_reset_i" LOC = "V16" | IOSTANDARD = LVTTL | PULLDOWN ;
 
### VGA Port ###
NET "vga_rgb_r_o" LOC = "H14" | IOSTANDARD = LVTTL | DRIVE = 8 | SLEW = FAST ;
NET "vga_rgb_g_o" LOC = "H15" | IOSTANDARD = LVTTL | DRIVE = 8 | SLEW = FAST ;
NET "vga_rgb_b_o" LOC = "G15" | IOSTANDARD = LVTTL | DRIVE = 8 | SLEW = FAST ;
NET "vga_hsync_o" LOC = "F15" | IOSTANDARD = LVTTL | DRIVE = 8 | SLEW = FAST ;
NET "vga_vsync_o" LOC = "F14" | IOSTANDARD = LVTTL | DRIVE = 8 | SLEW = FAST ;
 
### PS/2 Keyboard interface ###
NET "ps2_keyboard_clock_io" LOC = "G14" | IOSTANDARD = LVCMOS33 | DRIVE = 8 | SLEW = SLOW ;
NET "ps2_keyboard_data_io" LOC = "G13" | IOSTANDARD = LVCMOS33 | DRIVE = 8 | SLEW = SLOW ;
 
### DDR SDRAM ###
NET "ddr_clk" LOC = "J5" | IOSTANDARD = SSTL2_I ;
NET "ddr_clk_n" LOC = "J4" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<0>" LOC = "T1" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<1>" LOC = "R3" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<2>" LOC = "R2" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<3>" LOC = "P1" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<4>" LOC = "F4" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<5>" LOC = "H4" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<6>" LOC = "H3" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<7>" LOC = "H1" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<8>" LOC = "H2" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<9>" LOC = "N4" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<10>" LOC = "T2" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<11>" LOC = "N5" | IOSTANDARD = SSTL2_I ;
NET "ddr_a<12>" LOC = "P2" | IOSTANDARD = SSTL2_I ;
NET "ddr_ba<0>" LOC = "K5" | IOSTANDARD = SSTL2_I ;
NET "ddr_ba<1>" LOC = "K6" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<0>" LOC = "L2" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<1>" LOC = "L1" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<2>" LOC = "L3" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<3>" LOC = "L4" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<4>" LOC = "M3" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<5>" LOC = "M4" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<6>" LOC = "M5" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<7>" LOC = "M6" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<8>" LOC = "E2" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<9>" LOC = "E1" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<10>" LOC = "F1" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<11>" LOC = "F2" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<12>" LOC = "G6" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<13>" LOC = "G5" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<14>" LOC = "H6" | IOSTANDARD = SSTL2_I ;
NET "ddr_dq<15>" LOC = "H5" | IOSTANDARD = SSTL2_I ;
NET "ddr_dm<0>" LOC = "J2" | IOSTANDARD = SSTL2_I ;
NET "ddr_dm<1>" LOC = "J1" | IOSTANDARD = SSTL2_I ;
NET "ddr_dqs<0>" LOC = "L6" | IOSTANDARD = SSTL2_I ;
NET "ddr_dqs<1>" LOC = "G3" | IOSTANDARD = SSTL2_I ;
NET "ddr_cs_n" LOC = "K4" | IOSTANDARD = SSTL2_I ;
NET "ddr_cke" LOC = "K3" | IOSTANDARD = SSTL2_I ;
NET "ddr_ras_n" LOC = "C1" | IOSTANDARD = SSTL2_I ;
NET "ddr_cas_n" LOC = "C2" | IOSTANDARD = SSTL2_I ;
NET "ddr_we_n" LOC = "D1" | IOSTANDARD = SSTL2_I ;
 
/wb_ddr_ctrl/ddr_clkgen.v
0,0 → 1,200
//---------------------------------------------------------------------------
// Wishbone DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//---------------------------------------------------------------------------
 
`timescale 1ns / 1ps
`include "ddr_include.v"
 
module ddr_clkgen
#(
parameter phase_shift = 0,
parameter clk_multiply = 13,
parameter clk_divide = 5
) (
input clk,
input reset,
output locked,
//
output write_clk,
output write_clk90,
//
input ddr_clk_fb,
output read_clk,
input [2:0] rot
);
 
 
//----------------------------------------------------------------------------
// rotary decoder
//----------------------------------------------------------------------------
rotary rotdec0 (
.clk( clk ),
.reset( reset ),
.rot( rot ),
// output
.rot_btn( rot_btn ),
.rot_event( rot_event ),
.rot_left( rot_left )
);
 
reg [1:0] mux_sel;
 
always @(posedge clk)
begin
if (reset)
mux_sel <= 0;
else
if (rot_btn)
mux_sel <= mux_sel + 1;
end
 
//----------------------------------------------------------------------------
// ~133 MHz DDR Clock generator
//----------------------------------------------------------------------------
wire read_clk_u, read_clk180_u;
wire dcm_fx_locked;
 
DCM_SP #(
.CLKDV_DIVIDE(2.0), // Divide by: 1.5,2.0,2.5,3.0,3.5,4.0,4.5,5.0,5.5,6.0,6.5
// 7.0,7.5,8.0,9.0,10.0,11.0,12.0,13.0,14.0,15.0 or 16.0
.CLKFX_DIVIDE(clk_divide), // Can be any integer from 1 to 32
.CLKFX_MULTIPLY(clk_multiply), // Can be any integer from 2 to 32
.CLKIN_DIVIDE_BY_2("FALSE"), // TRUE/FALSE to enable CLKIN divide by two feature
.CLKIN_PERIOD(), // Specify period of input clock
.CLKOUT_PHASE_SHIFT("NONE"), // Specify phase shift of NONE, FIXED or VARIABLE
.CLK_FEEDBACK("NONE"), // Specify clock feedback of NONE, 1X or 2X
.DESKEW_ADJUST("SOURCE_SYNCHRONOUS"), // SOURCE_SYNCHRONOUS, SYSTEM_SYNCHRONOUS or
// an integer from 0 to 15
.DFS_FREQUENCY_MODE("LOW"), // HIGH or LOW frequency mode for frequency synthesis
.DLL_FREQUENCY_MODE("LOW"), // HIGH or LOW frequency mode for DLL
.DUTY_CYCLE_CORRECTION("TRUE"), // Duty cycle correction, TRUE or FALSE
.FACTORY_JF(16'hC080), // FACTORY JF values
.PHASE_SHIFT(0), // Amount of fixed phase shift from -255 to 255
.STARTUP_WAIT("FALSE") // Delay configuration DONE until DCM LOCK, TRUE/FALSE
) dcm_fx (
.DSSEN(),
.CLK0(), // 0 degree DCM CLK output
.CLK180(), // 180 degree DCM CLK output
.CLK270(), // 270 degree DCM CLK output
.CLK2X(), // 2X DCM CLK output
.CLK2X180(), // 2X, 180 degree DCM CLK out
.CLK90(), // 90 degree DCM CLK output
.CLKDV(), // Divided DCM CLK out (CLKDV_DIVIDE)
.CLKFX( read_clk_u ), // DCM CLK synthesis out (M/D)
.CLKFX180( read_clk180_u), // 180 degree CLK synthesis out
.LOCKED( dcm_fx_locked), // DCM LOCK status output
.PSDONE(), // Dynamic phase adjust done output
.STATUS(), // 8-bit DCM status bits output
.CLKFB(), // DCM clock feedback
.CLKIN( clk ), // Clock input (from IBUFG, BUFG or DCM)
.PSCLK( gnd ), // Dynamic phase adjust clock input
.PSEN( gnd ), // Dynamic phase adjust enable input
.PSINCDEC( gnd ), // Dynamic phase adjust increment/decrement
.RST(reset) // DCM asynchronous reset input
);
 
//----------------------------------------------------------------------------
// BUFG read clock
//----------------------------------------------------------------------------
BUFG bufg_fx_clk (
.O(read_clk), // Clock buffer output
.I(read_clk_u) // Clock buffer input
);
 
//----------------------------------------------------------------------------
// ~133 MHz DDR Clock generator
//----------------------------------------------------------------------------
wire phase_dcm_reset;
wire phase_dcm_locked;
wire write_clk_u, write_clk90_u, write_clk180_u, write_clk270_u;
wire write_clk_fb;
 
DCM_SP #(
.CLKDV_DIVIDE(2.0), // Divide by: 1.5,2.0,2.5,3.0,3.5,4.0,4.5,5.0,5.5,6.0,6.5
// 7.0,7.5,8.0,9.0,10.0,11.0,12.0,13.0,14.0,15.0 or 16.0
.CLKFX_DIVIDE(2), // Can be any integer from 1 to 32
.CLKFX_MULTIPLY(2), // Can be any integer from 2 to 32
.CLKIN_DIVIDE_BY_2("FALSE"), // TRUE/FALSE to enable CLKIN divide by two feature
.CLKIN_PERIOD(), // Specify period of input clock
.CLK_FEEDBACK("1X"), // Specify clock feedback of NONE, 1X or 2X
.DESKEW_ADJUST("SYSTEM_SYNCHRONOUS"), // SOURCE_SYNCHRONOUS, SYSTEM_SYNCHRONOUS or
// an integer from 0 to 15
.DFS_FREQUENCY_MODE("LOW"), // HIGH or LOW frequency mode for frequency synthesis
.DLL_FREQUENCY_MODE("LOW"), // HIGH or LOW frequency mode for DLL
.DUTY_CYCLE_CORRECTION("TRUE"), // Duty cycle correction, TRUE or FALSE
.FACTORY_JF(16'hC080), // FACTORY JF values
.CLKOUT_PHASE_SHIFT("VARIABLE"), // Specify phase shift of NONE, FIXED or VARIABLE
.PHASE_SHIFT( phase_shift ), // Amount of fixed phase shift from -255 to 255
.STARTUP_WAIT("FALSE") // Delay configuration DONE until DCM LOCK, TRUE/FALSE
) dcm_phase (
.DSSEN(),
.CLK0( write_clk_u ), // 0 degree DCM CLK output
.CLK90( write_clk90_u ), // 90 degree DCM CLK output
.CLK180( write_clk180_u ), // 180 degree DCM CLK output
.CLK270( write_clk270_u ), // 270 degree DCM CLK output
.CLK2X(), // 2X DCM CLK output
.CLK2X180(), // 2X, 180 degree DCM CLK out
.CLKDV(), // Divided DCM CLK out (CLKDV_DIVIDE)
.CLKFX(), // DCM CLK synthesis out (M/D)
.CLKFX180(), // 180 degree CLK synthesis out
.LOCKED( phase_dcm_locked ), // DCM LOCK status output
.PSDONE(), // Dynamic phase adjust done output
.STATUS(), // 8-bit DCM status bits output
.CLKFB( write_clk_fb ), // DCM clock feedback
.CLKIN( read_clk ), // Clock input (from IBUFG, BUFG or DCM)
.PSCLK( clk ), // Dynamic phase adjust clock input
.PSEN( rot_event ), // Dynamic phase adjust enable input
.PSINCDEC( rot_left ), // Dynamic phase adjust increment/decrement
.RST( phase_dcm_reset ) // DCM asynchronous reset input
);
 
 
assign write_clk_fb = (mux_sel == 'b00) ? write_clk_u :
(mux_sel == 'b01) ? write_clk90_u :
(mux_sel == 'b10) ? write_clk180_u :
write_clk270_u;
 
reg [3:0] reset_counter;
assign phase_dcm_reset = reset | (reset_counter != 0);
 
always @(posedge clk)
begin
if (reset)
reset_counter <= 1;
else begin
if (dcm_fx_locked & (reset_counter != 0))
reset_counter <= reset_counter + 1;
end
end
 
 
//----------------------------------------------------------------------------
// BUFG write clock
//----------------------------------------------------------------------------
 
BUFG bufg_write_clk (
.O(write_clk ), // Clock buffer output
.I(write_clk_u) // Clock buffer input
);
 
BUFG bufg_write_clk90 (
.O(write_clk90 ), // Clock buffer output
.I(write_clk90_u) // Clock buffer input
);
 
//----------------------------------------------------------------------------
// LOCKED logic
//----------------------------------------------------------------------------
reg phase_dcm_locked_delayed;
 
always @(posedge write_clk)
begin
phase_dcm_locked_delayed <= phase_dcm_locked;
end
 
assign locked = ~reset & phase_dcm_locked_delayed;
 
 
endmodule
/wb_ddr_ctrl/ddr_include.v
0,0 → 1,122
//---------------------------------------------------------------------------
// Wishbone DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//---------------------------------------------------------------------------
 
`ifdef WBDDR_INCLUDE_V
`else
`define WBDDR_INCLUDE_V
 
`timescale 1ns/10ps
 
//---------------------------------------------------------------------------
// Frequency and timeouts
//---------------------------------------------------------------------------
`define SYS_CLK_FREQUENCY 50000 // in kHz
`define DDR_CLK_MULTIPLY 5
`define DDR_CLK_DIVIDE 2
 
//---------------------------------------------------------------------------
// Width
//---------------------------------------------------------------------------
`define CMD_WIDTH 3
`define A_WIDTH 13
`define BA_WIDTH 2
`define DQ_WIDTH 16
`define DQS_WIDTH 2
`define DM_WIDTH 2
 
`define RFIFO_WIDTH (2 * `DQ_WIDTH )
`define WFIFO_WIDTH (2 * (`DQ_WIDTH + `DM_WIDTH))
`define CBA_WIDTH (`CMD_WIDTH+`BA_WIDTH+`A_WIDTH)
 
// Ranges
`define CMD_RNG (`CMD_WIDTH-1):0
`define A_RNG (`A_WIDTH-1):0
`define BA_RNG (`BA_WIDTH-1):0
`define DQ_RNG (`DQ_WIDTH-1):0
`define DQS_RNG (`DQS_WIDTH-1):0
`define DM_RNG (`DM_WIDTH-1):0
 
`define RFIFO_RNG (`RFIFO_WIDTH-1):0
`define WFIFO_RNG (`WFIFO_WIDTH-1):0
`define WFIFO_D0_RNG (1*`DQ_WIDTH-1):0
`define WFIFO_D1_RNG (2*`DQ_WIDTH-1):(`DQ_WIDTH)
`define WFIFO_M0_RNG (2*`DQ_WIDTH+1*`DM_WIDTH-1):(2*`DQ_WIDTH+0*`DM_WIDTH)
`define WFIFO_M1_RNG (2*`DQ_WIDTH+2*`DM_WIDTH-1):(2*`DQ_WIDTH+1*`DM_WIDTH)
`define CBA_RNG (`CBA_WIDTH-1):0
`define CBA_CMD_RNG (`CBA_WIDTH-1):(`CBA_WIDTH-3)
`define CBA_BA_RNG (`CBA_WIDTH-4):(`CBA_WIDTH-5)
`define CBA_A_RNG (`CBA_WIDTH-6):0
 
`define ROW_RNG 12:0
 
//----------------------------------------------------------------------------
// Configuration registers
//----------------------------------------------------------------------------
`define DDR_INIT_EMRS `A_WIDTH'b0000000000000 // DLL enable
`define DDR_INIT_MRS1 `A_WIDTH'b0000101100011 // BURST=8, CL=2.5, DLL RESET
`define DDR_INIT_MRS2 `A_WIDTH'b0000001100011 // BURST=8, CL=2.5
 
//----------------------------------------------------------------------------
// FML constants
//----------------------------------------------------------------------------
`define FML_ADR_RNG 25:4
`define FML_ADR_BA_RNG 25:24
`define FML_ADR_ROW_RNG 23:11
`define FML_ADR_COL_RNG 10:4
`define FML_DAT_RNG 31:0
`define FML_BE_RNG 3:0
 
//----------------------------------------------------------------------------
// DDR constants
//----------------------------------------------------------------------------
`define DDR_CMD_NOP 3'b111
`define DDR_CMD_ACT 3'b011
`define DDR_CMD_READ 3'b101
`define DDR_CMD_WRITE 3'b100
`define DDR_CMD_TERM 3'b110
`define DDR_CMD_PRE 3'b010
`define DDR_CMD_AR 3'b001
`define DDR_CMD_MRS 3'b000
 
`define ADR_BA_RNG 25:24
`define ADR_ROW_RNG 23:11
`define ADR_COL_RNG 10:4
 
`define T_MRD 2 // Mode register set
`define T_RP 2 // Precharge Command Period
`define T_RFC 8 // Precharge Command Period
 
//----------------------------------------------------------------------------
// Buffer Cache
//----------------------------------------------------------------------------
`define WAY_WIDTH (`WB_DAT_WIDTH + `WB_SEL_WIDTH)
`define WAY_LINE_RNG (`WAY_WIDTH-1):0
`define WAY_DAT_RNG 31:0
`define WAY_VALID_RNG 35:32
 
`define TAG_LINE_RNG 32:0
`define TAG_LINE_TAG0_RNG 14:0
`define TAG_LINE_TAG1_RNG 29:15
`define TAG_LINE_DIRTY0_RNG 30
`define TAG_LINE_DIRTY1_RNG 31
`define TAG_LINE_LRU_RNG 32
 
//----------------------------------------------------------------------------
// Whishbone constants
//----------------------------------------------------------------------------
`define WB_ADR_WIDTH 32
`define WB_DAT_WIDTH 32
`define WB_SEL_WIDTH 4
 
`define WB_ADR_RNG (`WB_ADR_WIDTH-1):0
`define WB_DAT_RNG (`WB_DAT_WIDTH-1):0
`define WB_SEL_RNG (`WB_SEL_WIDTH-1):0
 
`define WB_WORD_RNG 3:2
`define WB_SET_RNG 10:4
`define WB_TAG_RNG 25:11
 
`endif
/wb_ddr_ctrl/ddr_init.v
0,0 → 1,191
//----------------------------------------------------------------------------
// Wishbone DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//----------------------------------------------------------------------------
`include "ddr_include.v"
 
module ddr_init
#(
parameter wait200_init = 26
) (
input clk,
input reset,
input pulse78,
output wait200,
output init_done,
//
output mngt_req,
input mngt_ack,
output [`CBA_RNG] mngt_cba // CMD, BA and ADDRESS
);
 
reg cmd_req_reg;
reg [`CMD_RNG] cmd_cmd_reg;
reg [ `BA_RNG] cmd_ba_reg;
reg [ `A_RNG] cmd_a_reg;
reg [7:0] cmd_idle_reg;
 
//---------------------------------------------------------------------------
// Initial 200us delay
//---------------------------------------------------------------------------
 
// `define WAIT200_INIT 26
// `define WAIT200_INIT 1
 
reg [4:0] wait200_counter;
reg wait200_reg;
 
always @(posedge clk)
begin
if (reset) begin
wait200_reg <= 1;
wait200_counter <= wait200_init;
end else begin
if (wait200_counter == 0)
wait200_reg <= 0;
 
if (wait200_reg & pulse78)
wait200_counter <= wait200_counter - 1;
end
end
 
assign wait200 = wait200_reg;
 
//---------------------------------------------------------------------------
// Auto refresh counter
//---------------------------------------------------------------------------
 
reg [2:0] ar_counter;
wire ar_cmd_acked;
wire ar_needed;
wire ar_badly_needed;
 
assign ar_cmd_acked = (cmd_cmd_reg == `DDR_CMD_AR) & mngt_ack;
assign ar_needed = (ar_counter != 0) & ~ar_cmd_acked;
assign ar_badly_needed = ar_counter[2] == 1'b1; // >= 4
 
always @(posedge clk)
begin
if (reset) begin
ar_counter <= 0;
end else begin
if (~init_done)
ar_counter <= 0;
else if (pulse78 & ~ar_cmd_acked)
ar_counter <= ar_counter + 1;
else if (ar_cmd_acked & ~pulse78)
ar_counter <= ar_counter - 1;
end
end
 
//----------------------------------------------------------------------------
// DDR Initialization State Machine
//----------------------------------------------------------------------------
 
parameter s_wait200 = 0;
parameter s_init1 = 1;
parameter s_init2 = 2;
parameter s_init3 = 3;
parameter s_init4 = 4;
parameter s_init5 = 5;
parameter s_init6 = 6;
parameter s_waitack = 7;
parameter s_idle = 8;
 
reg [3:0] state;
reg init_done_reg;
 
assign mngt_cba = {cmd_cmd_reg, cmd_ba_reg, cmd_a_reg};
assign mngt_req = cmd_req_reg;
assign mngt_pri_req = ~init_done_reg;
assign init_done = init_done_reg;
 
always @(posedge clk or posedge reset)
begin
if (reset) begin
init_done_reg <= 0;
state <= s_wait200;
cmd_idle_reg <= 0;
cmd_req_reg <= 0;
cmd_cmd_reg <= 'b0;
cmd_ba_reg <= 'b0;
cmd_a_reg <= 'b0;
end else begin
case (state)
s_wait200: begin
if (~wait200_reg) begin
state <= s_init1;
cmd_req_reg <= 1;
cmd_cmd_reg <= `DDR_CMD_PRE; // PRE ALL
cmd_a_reg[10] <= 1'b1;
end
end
s_init1: begin
if (mngt_ack) begin
state <= s_init2;
cmd_req_reg <= 1;
cmd_cmd_reg <= `DDR_CMD_MRS; // EMRS
cmd_ba_reg <= 2'b01;
cmd_a_reg <= `DDR_INIT_EMRS;
end
end
s_init2: begin
if (mngt_ack) begin
state <= s_init3;
cmd_req_reg <= 1;
cmd_cmd_reg <= `DDR_CMD_MRS; // MRS
cmd_ba_reg <= 2'b00;
cmd_a_reg <= `DDR_INIT_MRS1;
end
end
s_init3: begin
if (mngt_ack) begin
state <= s_init4;
cmd_req_reg <= 1;
cmd_cmd_reg <= `DDR_CMD_PRE; // PRE ALL
cmd_a_reg[10] <= 1'b1;
end
end
s_init4: begin
if (mngt_ack) begin
state <= s_init5;
cmd_req_reg <= 1;
cmd_cmd_reg <= `DDR_CMD_AR; // AR
end
end
s_init5: begin
if (mngt_ack) begin
state <= s_init6;
cmd_req_reg <= 1;
cmd_cmd_reg <= `DDR_CMD_AR; // AR
end
end
s_init6: begin
if (mngt_ack) begin
init_done_reg <= 1;
state <= s_waitack;
cmd_req_reg <= 1;
cmd_cmd_reg <= `DDR_CMD_MRS; // MRS
cmd_ba_reg <= 2'b00;
cmd_a_reg <= `DDR_INIT_MRS2;
end
end
s_waitack: begin
if (mngt_ack) begin
state <= s_idle;
cmd_req_reg <= 0;
cmd_cmd_reg <= 'b0;
cmd_ba_reg <= 'b0;
cmd_a_reg <= 'b0;
end
end
s_idle: begin
end
endcase ///////////////////////////////////////// INIT STATE MACHINE ///
end
end
 
 
endmodule
 
/wb_ddr_ctrl/ddr_wpath.v
0,0 → 1,286
//----------------------------------------------------------------------------
//
// Wishbone DDR Controller -- fast write data-path
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//
//----------------------------------------------------------------------------
 
`include "ddr_include.v"
 
module ddr_wpath (
input clk,
input clk90,
input reset,
// CBA async fifo
input cba_clk,
input [`CBA_RNG] cba_din,
input cba_wr,
output cba_full,
// WDATA async fifo
input wdata_clk,
input [`WFIFO_RNG] wdata_din,
input wdata_wr,
output wdata_full,
// sample to rdata
output sample,
// DDR
output ddr_clk,
output ddr_clk_n,
output ddr_ras_n,
output ddr_cas_n,
output ddr_we_n,
output [ `A_RNG] ddr_a,
output [ `BA_RNG] ddr_ba,
output [ `DM_RNG] ddr_dm,
output [ `DQ_RNG] ddr_dq,
output [`DQS_RNG] ddr_dqs,
output ddr_dqs_oe
);
 
wire gnd = 1'b0;
wire vcc = 1'b1;
 
//----------------------------------------------------------------------------
// CBA async. fifo
//----------------------------------------------------------------------------
wire [`CBA_RNG] cba_data;
wire cba_empty;
wire cba_ack;
 
wire cba_avail = ~cba_empty;
 
async_fifo #(
.DATA_WIDTH( `CBA_WIDTH ),
.ADDRESS_WIDTH( 3 )
) cba_fifo (
.Data_out( cba_data ),
.Empty_out( cba_empty ),
.ReadEn_in( cba_ack ),
.RClk( clk ),
//
.Data_in( cba_din ),
.WriteEn_in( cba_wr ),
.Full_out( cba_full ),
.WClk( cba_clk ),
.Clear_in( reset )
);
 
//----------------------------------------------------------------------------
// WDATA async. fifo
//----------------------------------------------------------------------------
wire [`WFIFO_RNG] wdata_data;
wire wdata_empty;
wire wdata_ack;
 
wire wdata_avail = ~wdata_empty;
 
async_fifo #(
.DATA_WIDTH( `WFIFO_WIDTH ),
.ADDRESS_WIDTH( 3 )
) wdata_fifo (
.Data_out( wdata_data ),
.Empty_out( wdata_empty ),
.ReadEn_in( wdata_ack ),
.RClk( ~clk90 ),
//
.Data_in( wdata_din ),
.WriteEn_in( wdata_wr ),
.Full_out( wdata_full ),
.WClk( wdata_clk ),
.Clear_in( reset )
);
 
 
//----------------------------------------------------------------------------
// Handle CBA
//----------------------------------------------------------------------------
reg [3:0] delay_count;
 
reg [`CBA_RNG] ddr_cba;
wire [`CBA_RNG] CBA_NOP = { `DDR_CMD_NOP, 15'b0 };
 
assign cba_ack = cba_avail & (delay_count == 0);
 
wire [`CMD_RNG] cba_cmd = cba_data[(`CBA_WIDTH-1):(`CBA_WIDTH-3)];
 
always @(posedge clk)
begin
if (reset) begin
delay_count <= 0;
ddr_cba <= CBA_NOP;
end else begin
if (delay_count != 0) begin
delay_count <= delay_count - 1;
ddr_cba <= CBA_NOP;
end
 
if (!cba_ack) begin
ddr_cba <= CBA_NOP;
end else begin
ddr_cba <= cba_data;
 
case (cba_cmd)
`DDR_CMD_MRS : delay_count <= 2;
`DDR_CMD_AR : delay_count <= 14;
`DDR_CMD_ACT : delay_count <= 4;
`DDR_CMD_PRE : delay_count <= 2;
`DDR_CMD_READ : delay_count <= 6; // XXX
`DDR_CMD_WRITE : delay_count <= 8; // XXX
endcase
end
end
end
 
//----------------------------------------------------------------------------
// READ-SHIFT-REGISTER
//----------------------------------------------------------------------------
reg [0:7] read_shr;
wire read_cmd = (cba_cmd == `DDR_CMD_READ) & cba_ack;
assign sample = read_shr[1];
 
always @(posedge clk)
begin
if (reset)
read_shr <= 'b0;
else begin
if (read_cmd)
read_shr <= { 8'b00011111 };
else
read_shr <= { read_shr[1:7], 1'b0 };
end
end
 
//----------------------------------------------------------------------------
// WRITE-SHIFT-REGISTER
//----------------------------------------------------------------------------
 
reg [0:4] write_shr;
wire write_cmd = (cba_cmd == `DDR_CMD_WRITE) & cba_ack;
 
always @(posedge clk)
begin
if (reset)
write_shr <= 'b0;
else begin
if (write_cmd)
write_shr <= { 5'b11111 };
else
write_shr <= { write_shr[1:4], 1'b0 };
end
end
 
//----------------------------------------------------------------------------
// DDR_DQS, DDR_DQS_OE
//----------------------------------------------------------------------------
genvar i;
 
reg ddr_dqs_oe_reg;
assign ddr_dqs_oe = ddr_dqs_oe_reg;
 
always @(negedge clk)
begin
ddr_dqs_oe_reg <= write_shr[0];
end
 
FDDRRSE ddr_clk_reg (
.Q( ddr_clk ),
.C0( clk90 ),
.C1( ~clk90 ),
.CE( vcc ),
.D0( vcc ),
.D1( gnd ),
.R( gnd ),
.S( gnd )
);
 
FDDRRSE ddr_clk_n_reg (
.Q( ddr_clk_n ),
.C0( clk90 ),
.C1( ~clk90 ),
.CE( vcc ),
.D0( gnd ),
.D1( vcc ),
.R( gnd ),
.S( gnd )
);
 
 
generate
for (i=0; i<`DQS_WIDTH; i=i+1) begin : DQS
FDDRRSE ddr_dqs_reg (
.Q( ddr_dqs[i] ),
.C0( clk ),
.C1( ~clk ),
.CE( vcc ),
.D0( write_shr[1] ),
.D1( gnd ),
.R( gnd ),
.S( gnd )
);
end
endgenerate
 
 
//----------------------------------------------------------------------------
// DQ data output
//----------------------------------------------------------------------------
wire [`DQ_RNG] buf_d0;
wire [`DM_RNG] buf_m0;
reg [`DQ_RNG] buf_d1; // pipleine high word data
reg [`DM_RNG] buf_m1; // pipleine high word mask
 
assign buf_d0 = wdata_data[`WFIFO_D0_RNG];
assign buf_m0 = wdata_data[`WFIFO_M0_RNG];
 
always @(negedge clk90)
begin
buf_d1 <= wdata_data[`WFIFO_D1_RNG];
buf_m1 <= wdata_data[`WFIFO_M1_RNG];
end
 
assign wdata_ack = write_shr[1];
 
// generate DDR_DQ register
generate
for (i=0; i<`DQ_WIDTH; i=i+1) begin : DQ_REG
FDDRRSE ddr_dq_reg (
.Q( ddr_dq[i] ),
.C0( ~clk90 ),
.C1( clk90 ),
.CE( vcc ),
.D0( buf_d0[i] ),
.D1( buf_d1[i] ),
.R( gnd ),
.S( gnd )
);
end
endgenerate
 
// generate DDR_DM register
generate
for (i=0; i<`DM_WIDTH; i=i+1) begin : DM_REG
FDDRRSE ddr_dm_reg (
.Q( ddr_dm[i] ),
.C0( ~clk90 ),
.C1( clk90 ),
.CE( vcc ),
.D0( buf_m0[i] ),
.D1( buf_m1[i] ),
.R( gnd ),
.S( gnd )
);
end
endgenerate
 
//----------------------------------------------------------------------------
// Connect ddr_cba to actual DDR pins
//----------------------------------------------------------------------------
assign ddr_a = ddr_cba[(`A_WIDTH-1):0];
assign ddr_ba = ddr_cba[(`A_WIDTH+`BA_WIDTH-1):(`A_WIDTH)];
assign ddr_ras_n = ddr_cba[(`CBA_WIDTH-1)];
assign ddr_cas_n = ddr_cba[(`CBA_WIDTH-2)];
assign ddr_we_n = ddr_cba[(`CBA_WIDTH-3)];
 
endmodule
/wb_ddr_ctrl/ddr_ctrl.v
0,0 → 1,339
//----------------------------------------------------------------------------
// Pipelined, asyncronous DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//----------------------------------------------------------------------------
`include "ddr_include.v"
 
module ddr_ctrl
#(
parameter phase_shift = 0,
parameter clk_multiply = 12,
parameter clk_divide = 5,
parameter wait200_init = 26
) (
input clk,
input reset,
// Temporary DCM control input
input [2:0] rot, // XXX
// DDR ports
output ddr_clk,
output ddr_clk_n,
input ddr_clk_fb,
output ddr_ras_n,
output ddr_cas_n,
output ddr_we_n,
output ddr_cke,
output ddr_cs_n,
output [ `A_RNG] ddr_a,
output [ `BA_RNG] ddr_ba,
inout [ `DQ_RNG] ddr_dq,
inout [`DQS_RNG] ddr_dqs,
output [ `DM_RNG] ddr_dm,
// FML (FastMemoryLink)
output reg fml_done,
input [`FML_ADR_RNG] fml_adr,
input fml_rd,
input fml_wr,
input [`FML_DAT_RNG] fml_wdat,
input [`FML_BE_RNG] fml_wbe,
input fml_wnext,
output fml_rempty,
input fml_rnext,
output [`FML_DAT_RNG] fml_rdat
);
 
wire [ `DQ_RNG] ddr_dq_i, ddr_dq_o;
wire [`DQS_RNG] ddr_dqs_i, ddr_dqs_o;
wire ddr_dqs_oe;
 
//----------------------------------------------------------------------------
// clock generator
//----------------------------------------------------------------------------
wire clk_locked;
wire write_clk, write_clk90;
wire read_clk;
 
wire reset_int = reset | ~clk_locked;
 
ddr_clkgen #(
.phase_shift( phase_shift ),
.clk_multiply( clk_multiply ),
.clk_divide( clk_divide )
) clkgen (
.clk( clk ),
.reset( reset ),
.locked( clk_locked ),
// ddr-clk
.write_clk( write_clk ),
.write_clk90( write_clk90 ),
// ddr-read-clk
.ddr_clk_fb( ddr_clk_fb ),
.read_clk( read_clk ),
// phase shift control
.rot( rot ) // XXX
);
 
//----------------------------------------------------------------------------
// async_fifos (cmd, wdata, rdata)
//----------------------------------------------------------------------------
wire cba_fifo_full;
reg [`CBA_RNG] cba_fifo_din;
reg cba_fifo_we;
 
wire wfifo_full;
wire [`WFIFO_RNG] wfifo_din;
wire wfifo_we;
 
wire [`RFIFO_RNG] rfifo_dout;
wire rfifo_empty;
wire rfifo_next;
 
assign wfifo_din = { ~fml_wbe, fml_wdat };
assign wfifo_we = fml_wnext;
 
assign fml_rdat = rfifo_dout;
assign fml_rempty = rfifo_empty;
assign rfifo_next = fml_rnext;
 
//----------------------------------------------------------------------------
// High-speed cmd, write and read datapath
//----------------------------------------------------------------------------
ddr_wpath wpath0 (
.clk( write_clk ),
.clk90( write_clk90 ),
.reset( reset_int ),
// CBA async fifo
.cba_clk( clk ),
.cba_din( cba_fifo_din ),
.cba_wr( cba_fifo_we ),
.cba_full( cba_fifo_full ),
// WDATA async fifo
.wdata_clk( clk ),
.wdata_din( wfifo_din ),
.wdata_wr( wfifo_we ),
.wdata_full( wfifo_full ),
//
.sample( sample ),
// DDR
.ddr_clk( ddr_clk ),
.ddr_clk_n( ddr_clk_n ),
.ddr_ras_n( ddr_ras_n ),
.ddr_cas_n( ddr_cas_n ),
.ddr_we_n( ddr_we_n ),
.ddr_a( ddr_a ),
.ddr_ba( ddr_ba ),
.ddr_dm( ddr_dm ),
.ddr_dq( ddr_dq_o ),
.ddr_dqs( ddr_dqs_o ),
.ddr_dqs_oe( ddr_dqs_oe )
);
 
ddr_rpath rpath0 (
.clk( read_clk ),
.reset( reset_int ),
//
.sample( sample ),
//
.rfifo_clk( clk ),
.rfifo_empty( rfifo_empty),
.rfifo_dout( rfifo_dout ),
.rfifo_next( rfifo_next ),
// DDR
.ddr_dq( ddr_dq_i ),
.ddr_dqs( ddr_dqs_i )
);
 
//----------------------------------------------------------------------------
// 7.8 us pulse generator
//----------------------------------------------------------------------------
wire pulse78;
reg ar_req;
reg ar_done;
 
ddr_pulse78 pulse79_gen (
.clk( clk ),
.reset( reset_int ),
.pulse78( pulse78 )
);
 
//----------------------------------------------------------------------------
// Auto Refresh request generator
//----------------------------------------------------------------------------
always @(posedge clk)
if (reset_int)
ar_req <= 0;
else
ar_req <= pulse78 | (ar_req & ~ar_done);
 
// operations we might want to submit
wire [`CBA_RNG] ar_pre_cba;
wire [`CBA_RNG] ar_ar_cba;
 
assign ar_pre_cba = { `DDR_CMD_PRE, 2'b00, 13'b1111111111111 };
assign ar_ar_cba = { `DDR_CMD_AR, 2'b00, 13'b0000000000000 };
 
//----------------------------------------------------------------------------
// Init & management
//----------------------------------------------------------------------------
wire init_req;
reg init_ack;
wire [`CBA_RNG] init_cba;
wire init_done;
wire wait200;
 
ddr_init #(
.wait200_init( wait200_init )
) init (
.clk( clk ),
.reset( reset_int ),
.pulse78( pulse78 ),
.wait200( wait200 ),
.init_done( init_done ),
//
.mngt_req( init_req ),
.mngt_ack( init_ack ),
.mngt_cba( init_cba )
);
 
//----------------------------------------------------------------------------
// Active Bank Information
//----------------------------------------------------------------------------
reg [`ROW_RNG] ba_row [3:0];
reg [3:0] ba_active;
 
//----------------------------------------------------------------------------
// FML decoding
//----------------------------------------------------------------------------
wire [`FML_ADR_BA_RNG] fml_ba = fml_adr[`FML_ADR_BA_RNG];
wire [`FML_ADR_ROW_RNG] fml_row = fml_adr[`FML_ADR_ROW_RNG];
wire [`FML_ADR_COL_RNG] fml_col = fml_adr[`FML_ADR_COL_RNG];
 
wire [`FML_ADR_ROW_RNG] fml_cur_row; // current active row in sel. bank
assign fml_cur_row = ba_row[fml_ba];
 
wire fml_row_active; // is row in selected ba really active?
assign fml_row_active = ba_active[fml_ba];
 
 
/*
wire fml_row_active = (fml_ba == 0) ? ba0_active : // is row in selected
(fml_ba == 1) ? ba1_active : // bank really active?
(fml_ba == 2) ? ba2_active :
ba3_active ;
*/
 
// request operation iff correct bank is active
wire fml_req = fml_rd | fml_wr;
wire fml_row_match = (fml_row == fml_cur_row) & fml_row_active;
wire fml_pre_req = fml_req & ~fml_row_match & fml_row_active;
wire fml_act_req = fml_req & ~fml_row_active;
wire fml_read_req = fml_rd & fml_row_match & ~fml_done;
wire fml_write_req = fml_wr & fml_row_match & ~fml_done;
 
// actual operations we might want to submit
wire [`CBA_RNG] fml_pre_cba;
wire [`CBA_RNG] fml_act_cba;
wire [`CBA_RNG] fml_read_cba;
wire [`CBA_RNG] fml_write_cba;
 
assign fml_pre_cba = { `DDR_CMD_PRE, fml_ba, 13'b0 };
assign fml_act_cba = { `DDR_CMD_ACT, fml_ba, fml_row };
assign fml_read_cba = { `DDR_CMD_READ, fml_ba, {3'b000}, fml_col, {3'b000} };
assign fml_write_cba = { `DDR_CMD_WRITE, fml_ba, {3'b000}, fml_col, {3'b000} };
 
//----------------------------------------------------------------------------
// Schedule and issue commands
//----------------------------------------------------------------------------
 
parameter s_init = 0;
parameter s_idle = 1;
parameter s_ar = 2;
parameter s_reading = 3;
 
reg [1:0] state;
 
always @(posedge clk)
begin
if (reset_int) begin
state <= s_init;
ba_active <= 0;
ba_row[0] <= 0;
ba_row[1] <= 0;
ba_row[2] <= 0;
ba_row[3] <= 0;
 
fml_done <= 0;
init_ack <= 0;
cba_fifo_we <= 0;
ar_done <= 0;
end else begin
fml_done <= 0;
init_ack <= 0;
cba_fifo_we <= 0;
ar_done <= 0;
 
case (state)
s_init: begin
if (init_done)
state <= s_idle;
 
if (init_req & ~cba_fifo_full) begin
cba_fifo_we <= 1;
cba_fifo_din <= init_cba;
init_ack <= 1;
end
end
s_idle: begin
if (fml_read_req & ~cba_fifo_full) begin
cba_fifo_we <= 1;
cba_fifo_din <= fml_read_cba;
fml_done <= 1;
end else if (fml_write_req & ~cba_fifo_full) begin
cba_fifo_we <= 1;
cba_fifo_din <= fml_write_cba;
fml_done <= 1;
end else if (ar_req & ~cba_fifo_full) begin
cba_fifo_we <= 1;
cba_fifo_din <= ar_pre_cba;
ar_done <= 1;
ba_active <= 'b0;
state <= s_ar;
end else if (fml_pre_req & ~cba_fifo_full) begin
cba_fifo_we <= 1;
cba_fifo_din <= fml_pre_cba;
ba_active[fml_ba] <= 0;
end else if (fml_act_req & ~cba_fifo_full) begin
cba_fifo_we <= 1;
cba_fifo_din <= fml_act_cba;
ba_active[fml_ba] <= 1;
ba_row[fml_ba] <= fml_row;
end
end
s_ar: begin
if (~cba_fifo_full) begin
cba_fifo_we <= 1;
cba_fifo_din <= ar_ar_cba;
state <= s_idle;
end
end
endcase
end
end
 
//----------------------------------------------------------------------------
// Demux dqs and dq
//----------------------------------------------------------------------------
assign ddr_cke = ~wait200; // bring up CKE as soon 200us wait is finished
 
assign ddr_dqs = ddr_dqs_oe!=1'b0 ? ddr_dqs_o : 'bz;
assign ddr_dq = ddr_dqs_oe!=1'b0 ? ddr_dq_o : 'bz;
 
assign ddr_dqs_i = ddr_dqs;
assign ddr_dq_i = ddr_dq;
 
assign ddr_cs_n = 0;
 
endmodule
 
// vim: set ts=4
/wb_ddr_ctrl/async_fifo.v
0,0 → 1,116
//==========================================
// Function : Asynchronous FIFO (w/ 2 asynchronous clocks).
// Coder : Alex Claros F.
// Date : 15/May/2005.
// Notes : This implementation is based on the article
// 'Asynchronous FIFO in Virtex-II FPGAs'
// writen by Peter Alfke. This TechXclusive
// article can be downloaded from the
// Xilinx website. It has some minor modifications.
//=========================================
 
`timescale 1ns / 1ps
 
module async_fifo
#(parameter DATA_WIDTH = 8,
ADDRESS_WIDTH = 4,
FIFO_DEPTH = (1 << ADDRESS_WIDTH))
//Reading port
(output wire [DATA_WIDTH-1:0] Data_out,
output reg Empty_out,
input wire ReadEn_in,
input wire RClk,
//Writing port.
input wire [DATA_WIDTH-1:0] Data_in,
output reg Full_out,
input wire WriteEn_in,
input wire WClk,
input wire Clear_in);
 
/////Internal connections & variables//////
reg [DATA_WIDTH-1:0] Mem [FIFO_DEPTH-1:0];
wire [ADDRESS_WIDTH-1:0] pNextWordToWrite, pNextWordToRead;
wire EqualAddresses;
wire NextWriteAddressEn, NextReadAddressEn;
wire Set_Status, Rst_Status;
reg Status;
wire PresetFull, PresetEmpty;
//////////////Code///////////////
//Data ports logic:
//(Uses a dual-port RAM).
//'Data_out' logic:
assign Data_out = Mem[pNextWordToRead];
// always @ (posedge RClk)
// if (!PresetEmpty)
// Data_out <= Mem[pNextWordToRead];
// if (ReadEn_in & !Empty_out)
//'Data_in' logic:
always @ (posedge WClk)
if (WriteEn_in & !Full_out)
Mem[pNextWordToWrite] <= Data_in;
 
//Fifo addresses support logic:
//'Next Addresses' enable logic:
assign NextWriteAddressEn = WriteEn_in & ~Full_out;
assign NextReadAddressEn = ReadEn_in & ~Empty_out;
//Addreses (Gray counters) logic:
GrayCounter #(
.COUNTER_WIDTH( ADDRESS_WIDTH )
) GrayCounter_pWr (
.GrayCount_out(pNextWordToWrite),
.Enable_in(NextWriteAddressEn),
.Clear_in(Clear_in),
.Clk(WClk)
);
GrayCounter #(
.COUNTER_WIDTH( ADDRESS_WIDTH )
) GrayCounter_pRd (
.GrayCount_out(pNextWordToRead),
.Enable_in(NextReadAddressEn),
.Clear_in(Clear_in),
.Clk(RClk)
);
 
//'EqualAddresses' logic:
assign EqualAddresses = (pNextWordToWrite == pNextWordToRead);
 
//'Quadrant selectors' logic:
assign Set_Status = (pNextWordToWrite[ADDRESS_WIDTH-2] ~^ pNextWordToRead[ADDRESS_WIDTH-1]) &
(pNextWordToWrite[ADDRESS_WIDTH-1] ^ pNextWordToRead[ADDRESS_WIDTH-2]);
assign Rst_Status = (pNextWordToWrite[ADDRESS_WIDTH-2] ^ pNextWordToRead[ADDRESS_WIDTH-1]) &
(pNextWordToWrite[ADDRESS_WIDTH-1] ~^ pNextWordToRead[ADDRESS_WIDTH-2]);
//'Status' latch logic:
always @ (Set_Status, Rst_Status, Clear_in) //D Latch w/ Asynchronous Clear & Preset.
if (Rst_Status | Clear_in)
Status = 0; //Going 'Empty'.
else if (Set_Status)
Status = 1; //Going 'Full'.
//'Full_out' logic for the writing port:
assign PresetFull = Status & EqualAddresses; //'Full' Fifo.
always @ (posedge WClk, posedge PresetFull) //D Flip-Flop w/ Asynchronous Preset.
if (PresetFull)
Full_out <= 1;
else
Full_out <= 0;
//'Empty_out' logic for the reading port:
assign PresetEmpty = ~Status & EqualAddresses; //'Empty' Fifo.
always @ (posedge RClk, posedge PresetEmpty) //D Flip-Flop w/ Asynchronous Preset.
if (PresetEmpty)
Empty_out <= 1;
else
Empty_out <= 0;
endmodule
/wb_ddr_ctrl/ddr_pulse78.v
0,0 → 1,44
///////////////////////////////////////////////////////////////////
//
// Wishbone DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//
 
`include "ddr_include.v"
 
module ddr_pulse78 (
input clk,
input reset,
//
output pulse78
);
 
`define PULSE78_RNG 8:0
`define PULSE78_INIT 389
 
reg [`PULSE78_RNG] counter;
reg pulse78_reg;
 
assign pulse78 = pulse78_reg;
 
always @(posedge clk)
begin
if (reset) begin
counter <= `PULSE78_INIT;
pulse78_reg <= 0;
end else begin
if (counter == 0) begin
counter <= `PULSE78_INIT;
pulse78_reg <= 1'b1;
end else begin
counter <= counter - 1;
pulse78_reg <= 0;
end
end
end
 
 
endmodule
 
// vim: set ts=4
/wb_ddr_ctrl/rotary.v
0,0 → 1,70
//----------------------------------------------------------------------------
// Decode rotary encoder to clk-syncronous signals
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//----------------------------------------------------------------------------
 
module rotary (
input clk,
input reset,
input [2:0] rot,
//
output reg rot_btn,
output reg rot_event,
output reg rot_left
);
 
//----------------------------------------------------------------------------
// decode rotary encoder
//----------------------------------------------------------------------------
reg [1:0] rot_q;
 
always @(posedge clk)
begin
case (rot[1:0])
2'b00: rot_q <= { rot_q[1], 1'b0 };
2'b01: rot_q <= { 1'b0, rot_q[0] };
2'b10: rot_q <= { 1'b1, rot_q[0] };
2'b11: rot_q <= { rot_q[1], 1'b1 };
endcase
end
 
reg [1:0] rot_q_delayed;
 
always @(posedge clk)
begin
rot_q_delayed <= rot_q;
 
if (rot_q[0] && ~rot_q_delayed[0]) begin
rot_event <= 1;
rot_left <= rot_q[1];
end else
rot_event <= 0;
end
 
//----------------------------------------------------------------------------
// debounce push button (rot[2])
//----------------------------------------------------------------------------
reg [2:0] rot_d;
reg [15:0] dead_count;
 
always @(posedge clk)
begin
if (reset) begin
rot_btn <= 0;
dead_count <= 0;
end else begin
rot_btn <= 1'b0;
rot_d <= { rot_d[1:0], rot[2] };
 
if (dead_count == 0) begin
if ( rot_d[2:1] == 2'b01 ) begin
rot_btn <= 1'b1;
dead_count <= dead_count - 1;
end
end else
dead_count <= dead_count - 1;
end
end
 
endmodule
/wb_ddr_ctrl/gray_counter.v
0,0 → 1,35
//==========================================
// Function : Code Gray counter.
// Coder : Alex Claros F.
// Date : 15/May/2005.
//=======================================
 
`timescale 1ns/1ps
 
module GrayCounter
#(parameter COUNTER_WIDTH = 2)
(output reg [COUNTER_WIDTH-1:0] GrayCount_out, //'Gray' code count output.
input wire Enable_in, //Count enable.
input wire Clear_in, //Count reset.
input wire Clk);
 
/////////Internal connections & variables///////
reg [COUNTER_WIDTH-1:0] BinaryCount;
 
/////////Code///////////////////////
always @ (posedge Clk)
if (Clear_in) begin
BinaryCount <= {COUNTER_WIDTH{1'b 0}} + 1; //Gray count begins @ '1' with
GrayCount_out <= {COUNTER_WIDTH{1'b 0}}; // first 'Enable_in'.
end
else if (Enable_in) begin
BinaryCount <= BinaryCount + 1;
GrayCount_out <= {BinaryCount[COUNTER_WIDTH-1],
BinaryCount[COUNTER_WIDTH-2:0] ^ BinaryCount[COUNTER_WIDTH-1:1]};
end
endmodule
/wb_ddr_ctrl/wb_ddr.v
0,0 → 1,612
//----------------------------------------------------------------------------
// Wishbone DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//----------------------------------------------------------------------------
 
`include "ddr_include.v"
 
module wb_ddr
#(
parameter phase_shift = 0,
parameter clk_multiply = 12,
parameter clk_divide = 5,
parameter wait200_init = 26
) (
input clk,
input reset,
// XXX -- DCM phase control -- XXX
input [2:0] rot,
// DDR ports
output ddr_clk,
output ddr_clk_n,
input ddr_clk_fb,
output ddr_ras_n,
output ddr_cas_n,
output ddr_we_n,
output ddr_cke,
output ddr_cs_n,
output [ `A_RNG] ddr_a,
output [ `BA_RNG] ddr_ba,
inout [ `DQ_RNG] ddr_dq,
inout [`DQS_RNG] ddr_dqs,
output [ `DM_RNG] ddr_dm,
// Wishbone Slave Interface
input [`WB_ADR_RNG] wb_adr_i,
input [`WB_DAT_RNG] wb_dat_i,
output reg [`WB_DAT_RNG] wb_dat_o,
input [`WB_SEL_RNG] wb_sel_i,
input wb_cyc_i,
input wb_stb_i,
input wb_we_i,
output reg wb_ack_o
);
 
//----------------------------------------------------------------------------
// Wishbone handling
//----------------------------------------------------------------------------
wire wb_rd = wb_stb_i & wb_cyc_i & ~wb_we_i;
wire wb_wr = wb_stb_i & wb_cyc_i & wb_we_i;
 
wire [`WB_WORD_RNG] wb_adr_word = wb_adr_i[`WB_WORD_RNG]; // word in bufferline
wire [`WB_SET_RNG] wb_adr_set = wb_adr_i[`WB_SET_RNG]; // index into wayX_ram
wire [`WB_TAG_RNG] wb_adr_tag = wb_adr_i[`WB_TAG_RNG]; // more significant bits
 
//----------------------------------------------------------------------------
// TAG RAM (2-way set assioziative)
//----------------------------------------------------------------------------
wire [`TAG_LINE_RNG] tag_load;
wire [`TAG_LINE_RNG] tag_store;
wire tag_we;
 
wire [`WB_TAG_RNG] tag_load_set0 = tag_load[`TAG_LINE_TAG0_RNG];
wire [`WB_TAG_RNG] tag_load_set1 = tag_load[`TAG_LINE_TAG1_RNG];
wire tag_load_dirty0 = tag_load[`TAG_LINE_DIRTY0_RNG];
wire tag_load_dirty1 = tag_load[`TAG_LINE_DIRTY1_RNG];
wire tag_load_lru = tag_load[`TAG_LINE_LRU_RNG];
 
reg [`WB_TAG_RNG] tag_store_set0;
reg [`WB_TAG_RNG] tag_store_set1;
reg tag_store_dirty0;
reg tag_store_dirty1;
reg tag_store_lru;
 
assign tag_store[`TAG_LINE_TAG0_RNG] = tag_store_set0;
assign tag_store[`TAG_LINE_TAG1_RNG] = tag_store_set1;
assign tag_store[`TAG_LINE_DIRTY0_RNG] = tag_store_dirty0;
assign tag_store[`TAG_LINE_DIRTY1_RNG] = tag_store_dirty1;
assign tag_store[`TAG_LINE_LRU_RNG] = tag_store_lru;
 
wire [`WB_SET_RNG] ls_tag_adr;
wire [`TAG_LINE_RNG] ls_tag_load;
reg [`TAG_LINE_RNG] ls_tag_store;
reg ls_tag_we;
 
dpram #(
.adr_width( 7 ),
.dat_width( 33 )
) tag_ram (
.clk ( clk ),
//
.adr0( wb_adr_set ),
.dout0( tag_load ),
.din0( tag_store ),
.we0( tag_we ),
//
.adr1( ls_tag_adr ),
.dout1( ls_tag_load ),
.din1( ls_tag_store ),
.we1( ls_tag_we )
);
 
wire tag_load_match0 = (tag_load_set0 == wb_adr_tag);
wire tag_load_match1 = (tag_load_set1 == wb_adr_tag);
wire tag_load_match = tag_load_match0 | tag_load_match1;
 
//----------------------------------------------------------------------------
// Buffer cache ram (2 ways)
//----------------------------------------------------------------------------
wire [8:0] wayX_adr = { wb_adr_set, wb_adr_word };
 
wire [`WAY_LINE_RNG] way0_load, way1_load;
wire [`WAY_LINE_RNG] wayX_store;
 
wire [31:0] way0_load_dat = way0_load[`WAY_DAT_RNG];
wire [31:0] way1_load_dat = way1_load[`WAY_DAT_RNG];
wire [3:0] way0_load_valid = way0_load[`WAY_VALID_RNG];
wire [3:0] way1_load_valid = way1_load[`WAY_VALID_RNG];
 
wire way0_we;
wire way1_we;
reg [31:0] wayX_store_dat;
reg [3:0] wayX_store_valid;
 
assign wayX_store[`WAY_DAT_RNG] = wayX_store_dat;
assign wayX_store[`WAY_VALID_RNG] = wayX_store_valid;
 
wire [8:0] ls_wayX_adr;
wire [`WAY_LINE_RNG] ls_way0_load;
wire [`WAY_LINE_RNG] ls_way1_load;
wire [`WAY_LINE_RNG] ls_wayX_store;
wire ls_way0_we;
wire ls_way1_we;
reg ls_wayX_we;
 
wire way0_sel_valid = ( (~way0_load_valid & wb_sel_i) == 'b0);
wire way1_sel_valid = ( (~way1_load_valid & wb_sel_i) == 'b0);
wire wayX_sel_valid = (tag_load_match0) ? way0_sel_valid : way1_sel_valid;
 
// synthesis attribute ram_style of way0_ram is block
dpram #(
.adr_width( 9 ),
.dat_width( 36 )
) way0_ram (
.clk( clk ),
//
.adr0( wayX_adr ),
.dout0( way0_load ),
.din0( wayX_store ),
.we0( way0_we ),
//
.adr1( ls_wayX_adr ),
.dout1( ls_way0_load ),
.we1( ls_way0_we ),
.din1( ls_wayX_store )
);
 
// synthesis attribute ram_style of way1_ram is block
dpram #(
.adr_width( 9 ),
.dat_width( 36 )
) way1_ram (
.clk( clk ),
//
.adr0( wayX_adr ),
.dout0( way1_load ),
.din0( wayX_store ),
.we0( way1_we ),
//
.adr1( ls_wayX_adr ),
.dout1( ls_way1_load ),
.we1( ls_way1_we ),
.din1( ls_wayX_store )
);
 
//----------------------------------------------------------------------------
// Write/update buffer cache from wishbone side
//----------------------------------------------------------------------------
wire store_to_way0 = tag_load_lru & ~tag_load_dirty0; // store new data into way0? XXX spill_done XXX
wire store_to_way1 = ~tag_load_lru & ~tag_load_dirty1; // store new data into way1? XXX spill_done XXX
wire store_to_way = store_to_way0 | store_to_way1;
 
reg update_lru0; //
reg update_lru1;
 
reg update_way0; //
reg update_way1;
 
assign way0_we = update_way0;
assign way1_we = update_way1;
assign tag_we = way0_we | way1_we | update_lru0 | update_lru1;
 
//----------------------------------------------------------------------------
// MUX wayX_store input
//----------------------------------------------------------------------------
 
integer i;
always @(*)
begin
/*
for(i=0; i<4; i=i+1) begin
if (wb_sel_i[i]) begin
wayX_store_dat[8*i+7:8*i] = wb_dat_i[8*i+7:8*i];
wayX_store_valid[i] = 1;
end else if (update_way0) begin
wayX_store_dat[8*i+7:8*i] = way0_load_dat[8*i+7:8*i];
wayX_store_valid[i] = way0_load_valid[i];
end else begin
wayX_store_dat[8*i+7:8*i] = way1_load_dat[8*i+7:8*i];
wayX_store_valid[i] = way1_load_valid[i];
end
end
*/
 
if (wb_sel_i[0]) begin
wayX_store_dat[8*0+7:8*0] = wb_dat_i[8*0+7:8*0];
wayX_store_valid[0] = 1;
end else if (update_way0) begin
wayX_store_dat[8*0+7:8*0] = way0_load_dat[8*0+7:8*0];
wayX_store_valid[0] = way0_load_valid[0];
end else begin
wayX_store_dat[8*0+7:8*0] = way1_load_dat[8*0+7:8*0];
wayX_store_valid[0] = way1_load_valid[0];
end
 
if (wb_sel_i[1]) begin
wayX_store_dat[8*1+7:8*1] = wb_dat_i[8*1+7:8*1];
wayX_store_valid[1] = 1;
end else if (update_way0) begin
wayX_store_dat[8*1+7:8*1] = way0_load_dat[8*1+7:8*1];
wayX_store_valid[1] = way0_load_valid[1];
end else begin
wayX_store_dat[8*1+7:8*1] = way1_load_dat[8*1+7:8*1];
wayX_store_valid[1] = way1_load_valid[1];
end
 
if (wb_sel_i[2]) begin
wayX_store_dat[8*2+7:8*2] = wb_dat_i[8*2+7:8*2];
wayX_store_valid[2] = 1;
end else if (update_way0) begin
wayX_store_dat[8*2+7:8*2] = way0_load_dat[8*2+7:8*2];
wayX_store_valid[2] = way0_load_valid[2];
end else begin
wayX_store_dat[8*2+7:8*2] = way1_load_dat[8*2+7:8*2];
wayX_store_valid[2] = way1_load_valid[2];
end
 
if (wb_sel_i[3]) begin
wayX_store_dat[8*3+7:8*3] = wb_dat_i[8*3+7:8*3];
wayX_store_valid[3] = 1;
end else if (update_way0) begin
wayX_store_dat[8*3+7:8*3] = way0_load_dat[8*3+7:8*3];
wayX_store_valid[3] = way0_load_valid[3];
end else begin
wayX_store_dat[8*3+7:8*3] = way1_load_dat[8*3+7:8*3];
wayX_store_valid[3] = way1_load_valid[3];
end
end
 
always @(*)
begin
if (update_way0) begin
tag_store_set0 = wb_adr_tag;
tag_store_dirty0 = 1;
end else begin
tag_store_set0 = tag_load_set0;
tag_store_dirty0 = tag_load_dirty0;
end
 
if (update_way1) begin
tag_store_set1 = wb_adr_tag;
tag_store_dirty1 = 1;
end else begin
tag_store_set1 = tag_load_set1;
tag_store_dirty1 = tag_load_dirty1;
end
 
if (update_lru0)
tag_store_lru = 0;
else if (update_lru1)
tag_store_lru = 1;
else
tag_store_lru = tag_load_lru;
end
 
//----------------------------------------------------------------------------
// Wishbone FSM
//----------------------------------------------------------------------------
reg ls_fill;
reg ls_spill;
reg ls_way;
wire ls_busy;
 
reg [`WB_TAG_RNG] ls_adr_tag;
reg [`WB_SET_RNG] ls_adr_set;
reg [`WB_WORD_RNG] ls_adr_word;
 
reg [2:0] state;
 
parameter s_idle = 0;
parameter s_read = 1;
parameter s_rspill = 2;
parameter s_rfill = 3;
parameter s_write = 4;
parameter s_wspill = 5;
 
// Syncronous part of FSM
always @(posedge clk)
begin
if (reset) begin
state <= s_idle;
ls_spill <= 0;
ls_fill <= 0;
ls_way <= 0;
end else begin
ls_fill <= 0;
ls_spill <= 0;
 
case (state)
s_idle: begin
if (wb_rd)
state <= s_read;
 
if (wb_wr)
state <= s_write;
end
s_read: begin
if ((tag_load_match0 & way0_sel_valid) | (tag_load_match1 & way1_sel_valid)) begin
state <= s_idle;
end else if (store_to_way & ~ls_busy) begin
state <= s_rfill;
ls_fill <= 1;
ls_way <= ~tag_load_lru;
ls_adr_tag <= wb_adr_tag;
ls_adr_set <= wb_adr_set;
end else if (~ls_busy) begin
state <= s_rspill;
ls_spill <= 1;
ls_way <= ~tag_load_lru;
ls_adr_set <= wb_adr_set;
if (tag_load_lru == 1)
ls_adr_tag <= tag_load_set0;
else
ls_adr_tag <= tag_load_set1;
end
end
s_rspill: begin
if (~ls_busy) begin
state <= s_rfill;
ls_fill <= 1;
ls_way <= ~tag_load_lru;
ls_adr_tag <= wb_adr_tag;
ls_adr_set <= wb_adr_set;
end
end
s_rfill: begin
if (tag_load_match & wayX_sel_valid)
state <= s_idle;
end
s_write: begin
if (tag_load_match | store_to_way) begin
state <= s_idle;
end else if (~ls_busy) begin
state <= s_wspill;
ls_spill <= 1;
ls_way <= ~tag_load_lru;
ls_adr_set <= wb_adr_set;
if (tag_load_lru == 1)
ls_adr_tag <= tag_load_set0;
else
ls_adr_tag <= tag_load_set1;
end
end
s_wspill: begin
if (tag_load_match | store_to_way) begin
state <= s_idle;
end
end
default:
state <= s_idle;
endcase
end
end
 
// Asyncronous part of FSM
always @(*)
begin
update_lru0 <= 0;
update_lru1 <= 0;
update_way0 <= 0;
update_way1 <= 0;
wb_dat_o <= 0;
wb_ack_o <= 0;
 
case (state)
s_idle: begin end
s_read: begin
if (tag_load_match0 & way0_sel_valid) begin
update_lru0 <= 1;
wb_dat_o <= way0_load_dat;
wb_ack_o <= 1;
end else if (tag_load_match1 & way1_sel_valid) begin
update_lru1 <= 1;
wb_dat_o <= way1_load_dat;
wb_ack_o <= 1;
end
end
s_write: begin
if (tag_load_match0 | store_to_way0) begin
update_lru0 <= 1;
update_way0 <= 1;
wb_ack_o <= 1;
end else if (tag_load_match1 | store_to_way1) begin
update_lru1 <= 1;
update_way1 <= 1;
wb_ack_o <= 1;
end
end
endcase
end
 
 
//----------------------------------------------------------------------------
// DDR Controller Engine (including clkgen, [rw]-path)
//----------------------------------------------------------------------------
reg fml_rd;
reg fml_wr;
wire fml_done;
wire [`FML_ADR_RNG] fml_adr;
wire [`FML_DAT_RNG] fml_wdat;
wire [`FML_BE_RNG] fml_wbe;
reg fml_wnext;
reg fml_wnext2;
wire fml_rempty;
reg fml_rnext;
wire [`FML_DAT_RNG] fml_rdat;
 
ddr_ctrl #(
.phase_shift( phase_shift ),
.clk_multiply( clk_multiply ),
.clk_divide( clk_divide ),
.wait200_init( wait200_init )
) ctrl0 (
.clk( clk ),
.reset( reset ),
.rot( rot ),
// DDR Ports
.ddr_clk( ddr_clk ),
.ddr_clk_n( ddr_clk_n ),
.ddr_clk_fb( ddr_clk_fb ),
.ddr_ras_n( ddr_ras_n ),
.ddr_cas_n( ddr_cas_n ),
.ddr_we_n( ddr_we_n ),
.ddr_cke( ddr_cke ),
.ddr_cs_n( ddr_cs_n ),
.ddr_a( ddr_a ),
.ddr_ba( ddr_ba ),
.ddr_dq( ddr_dq ),
.ddr_dqs( ddr_dqs ),
.ddr_dm( ddr_dm ),
// FML (FastMemoryLink)
.fml_rd( fml_rd ),
.fml_wr( fml_wr ),
.fml_done( fml_done ),
.fml_adr( fml_adr ),
.fml_wdat( fml_wdat ),
.fml_wbe( fml_wbe ),
.fml_wnext( fml_wnext2 ),
.fml_rempty( fml_rempty ),
.fml_rdat( fml_rdat ),
.fml_rnext( fml_rnext )
);
 
assign fml_adr = { ls_adr_tag, ls_adr_set };
 
assign fml_wdat = (ls_way) ? ls_way1_load[`WAY_DAT_RNG] :
ls_way0_load[`WAY_DAT_RNG];
 
assign fml_wbe = (ls_way) ? ls_way1_load[`WAY_VALID_RNG] :
ls_way0_load[`WAY_VALID_RNG];
 
assign ls_tag_adr = { ls_adr_set };
assign ls_wayX_adr = { ls_adr_set, ls_adr_word };
assign ls_way0_we = ls_wayX_we & ~ls_way;
assign ls_way1_we = ls_wayX_we & ls_way;
 
assign ls_wayX_store[`WAY_DAT_RNG] = fml_rdat;
assign ls_wayX_store[`WAY_VALID_RNG] = 4'b1111;
 
 
//----------------------------------------------------------------------------
// LS (Load and Store) Engine
//----------------------------------------------------------------------------
parameter l_idle = 0;
parameter l_fill = 1;
parameter l_spill = 2;
parameter l_waitdone = 3;
 
reg [2:0] ls_state;
assign ls_busy = (ls_state != l_idle) || ls_fill || ls_spill;
 
// Syncronous part FSM
always @(posedge clk)
begin
if (reset) begin
ls_state <= l_idle;
ls_adr_word <= 0;
fml_wr <= 0;
fml_rd <= 0;
end else begin
fml_wnext2 <= fml_wnext;
 
case (ls_state)
l_idle: begin
ls_adr_word <= 0;
 
if (ls_spill) begin
ls_state <= l_spill;
ls_adr_word <= ls_adr_word + 1;
end
if (ls_fill) begin
ls_state <= l_fill;
fml_rd <= 1;
end
end
l_spill: begin
ls_adr_word <= ls_adr_word + 1;
 
if (ls_adr_word == 3) begin
ls_state <= l_waitdone;
fml_wr <= 1;
end
end
l_waitdone: begin
ls_adr_word <= 0;
if (fml_done) begin
ls_state <= l_idle;
fml_wr <= 0;
end
end
l_fill: begin
if (fml_done)
fml_rd <= 0;
 
if (~fml_rempty)
ls_adr_word <= ls_adr_word + 1;
 
if (~fml_rempty & (ls_adr_word == 3))
ls_state <= l_idle;
end
endcase
end
end
 
always @(*)
begin
fml_wnext <= 0;
fml_rnext <= 0;
ls_tag_we <= 0;
ls_tag_store <= ls_tag_load;
ls_wayX_we <= 0;
 
case (ls_state)
l_idle: begin
if (ls_spill) begin
fml_wnext <= 1;
end
end
l_spill: begin
fml_wnext <= 1;
end
l_waitdone: begin
if (ls_way == 0)
ls_tag_store[`TAG_LINE_DIRTY0_RNG] <= 0;
else
ls_tag_store[`TAG_LINE_DIRTY1_RNG] <= 0;
 
if (fml_done)
ls_tag_we <= 1;
end
l_fill: begin
if (ls_way == 0) begin
ls_tag_store[`TAG_LINE_DIRTY0_RNG] <= 0;
ls_tag_store[`TAG_LINE_TAG0_RNG] <= ls_adr_tag;
end else begin
ls_tag_store[`TAG_LINE_DIRTY1_RNG] <= 0;
ls_tag_store[`TAG_LINE_TAG1_RNG] <= ls_adr_tag;
end
 
if (~fml_rempty) begin
ls_wayX_we <= 1;
fml_rnext <= 1;
end
 
if (~fml_rempty & (ls_adr_word == 3))
ls_tag_we <= 1;
end
endcase
end
 
always @(posedge clk)
begin
if (ls_fill)
$display ("At time %t WB_DDR fill cacheline: TAG = %h, SET = %h)", $time, ls_adr_tag, ls_adr_set);
 
if (ls_spill)
$display ("At time %t WB_DDR spill cacheline: TAG = %h, SET = %h)", $time, ls_adr_tag, ls_adr_set);
end
 
 
endmodule
/wb_ddr_ctrl/dpram.v
0,0 → 1,63
//----------------------------------------------------------------------------
// Wishbone DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//----------------------------------------------------------------------------
 
module dpram
#(
parameter adr_width = 9,
parameter dat_width = 36
) (
input clk,
// Port 0
input [adr_width-1:0] adr0,
input we0,
input [dat_width-1:0] din0,
output reg [dat_width-1:0] dout0,
// Port 1
input [adr_width-1:0] adr1,
input we1,
input [dat_width-1:0] din1,
output reg [dat_width-1:0] dout1
);
 
parameter depth = (1 << adr_width);
 
// actual ram
reg [dat_width-1:0] ram [0:depth-1];
 
//------------------------------------------------------------------
// Syncronous Dual Port RAM Access
//------------------------------------------------------------------
always @(posedge clk)
begin
// Frst port
if (we0)
ram[adr0] <= din0;
 
dout0 <= ram[adr0];
end
 
 
always @(posedge clk)
begin
// Second port
if (we1)
ram[adr1] <= din1;
 
dout1 <= ram[adr1];
end
 
//------------------------------------------------------------------
// Initialize content to Zero
//------------------------------------------------------------------
integer i;
 
initial
begin
for(i=0; i<depth; i=i+1)
ram[i] <= 'b0;
end
 
endmodule
/wb_ddr_ctrl/ddr_rpath.v
0,0 → 1,112
//----------------------------------------------------------------------------
// Wishbone DDR Controller
//
// (c) Joerg Bornschein (<jb@capsec.org>)
//----------------------------------------------------------------------------
 
`include "ddr_include.v"
 
module ddr_rpath
(
input clk,
input reset,
// sample activate
input sample,
// RDATA async fifo
input rfifo_clk,
output rfifo_empty,
output [`RFIFO_RNG] rfifo_dout,
input rfifo_next,
// DDR
input [ `DQ_RNG] ddr_dq,
input [`DQS_RNG] ddr_dqs
);
 
//----------------------------------------------------------------------------
// RDATA async. fifo
//----------------------------------------------------------------------------
 
wire [`RFIFO_RNG] rfifo_din;
wire rfifo_wr;
wire rfifo_full;
 
async_fifo #(
.DATA_WIDTH( `RFIFO_WIDTH ),
.ADDRESS_WIDTH( 3 )
) rfifo (
.Data_out( rfifo_dout ),
.Empty_out( rfifo_empty ),
.ReadEn_in( rfifo_next ),
.RClk( rfifo_clk ),
//
.Data_in( rfifo_din ),
.WriteEn_in( rfifo_wr ),
.Full_out( rfifo_full ),
.WClk( ~clk ),
.Clear_in( reset )
);
 
 
//----------------------------------------------------------------------------
// Clean up incoming 'sample' signal and generate sample_dq
//----------------------------------------------------------------------------
 
// anti-meta-state
//reg sample180;
//always @(negedge clk) sample180 <= sample;
wire sample180 = sample;
 
 
reg sample_dq; // authoritive sample flag (after cleanup)
reg sample_dq_delayed; // write to rfifo?
reg [3:0] sample_count; // make sure sample_dq is up exactly
// BURSTLENGTH/2 cycles
 
always @(posedge clk or posedge reset)
begin
if (reset) begin
sample_dq <= 0;
sample_dq_delayed <= 0;
sample_count <= 0;
end else begin
sample_dq_delayed <= sample_dq;
if (sample_count == 0) begin
if (sample180) begin
sample_dq <= 1;
sample_count <= 1;
end
end else if (sample_count == 4) begin
sample_dq <= 0;
sample_count <= 0;
end else
sample_count <= sample_count + 1;
end
end
 
//----------------------------------------------------------------------------
// Sampe DQ and fill RFIFO
//----------------------------------------------------------------------------
reg [15:0] ddr_dq_low, ddr_dq_high;
 
always @(negedge clk )
begin
if (reset)
ddr_dq_low <= 'b0;
else
ddr_dq_low <= ddr_dq;
end
 
always @(posedge clk)
begin
if (reset)
ddr_dq_high <= 'b0;
else
ddr_dq_high <= ddr_dq;
end
 
assign rfifo_wr = sample_dq_delayed;
assign rfifo_din = { ddr_dq_high, ddr_dq_low };
 
endmodule
 
/wb_int_ctrl/wb_int_ctrl.v
0,0 → 1,33
/*
* Interrupt Controller with Wishbone Slave Interface
*/
 
module wb_int_ctrl (
 
// System
input sys_clock_i, // System Clock
input sys_reset_i, // System Reset
 
// Interrupts
input[31:0] sys_irqs_i, // Input IRQs
output sys_irq_o, // Output IRQ
 
// Wishbone slave interface
input wb_cyc_i,
input wb_stb_i,
input wb_we_i,
input[3:0] wb_sel_i,
input[31:0] wb_adr_i,
input[31:0] wb_dat_i,
output wb_ack_o,
output[31:0] wb_dat_o
 
);
 
assign sys_irq_o = (|sys_irqs_i); // Unary OR reduction operator
assign wb_ack_o = (wb_cyc_i & wb_stb_i);
assign wb_dat_o = sys_irqs_i;
 
endmodule
 
 
/wb_text_vga/fontmap_rom.v~
0,0 → 1,2587
/*
* Fontmap ROM
*
* This is the ROM containing the map for a monospaced 8x8 font.
* The address input is the concatenation of the required ASCII code [10:3] and the
* number of the line [2:0] contained into the char (starting from the top).
* It should use only one 2KByte Block RAM on a Xilinx FPGA device.
* The font design is (C) 2005 by Brian Cassidy and released under the Perl license.
* All the rest is (C) 2008 by Simply RISC LLP and released under the GPL license.
*/
 
// synthesis attribute rom_style of fontmap_rom is block;
module fontmap_rom (
input sys_clock_i,
input read_i,
input[10:0] address_i,
output reg[7:0] data_o
);
 
always @(posedge sys_clock_i) begin
if(read_i) begin
case(address_i)
 
// ASCII 0
0 : data_o <= 8'h00;
1 : data_o <= 8'h00;
2 : data_o <= 8'h00;
3 : data_o <= 8'h00;
4 : data_o <= 8'h00;
5 : data_o <= 8'h00;
6 : data_o <= 8'h00;
7 : data_o <= 8'h00;
 
// ASCII 1
8 : data_o <= 8'h7e;
9 : data_o <= 8'h81;
10 : data_o <= 8'ha5;
11 : data_o <= 8'h81;
12 : data_o <= 8'hbd;
13 : data_o <= 8'h99;
14 : data_o <= 8'h81;
15 : data_o <= 8'h7e;
 
// ASCII 2
16 : data_o <= 8'h7e;
17 : data_o <= 8'hff;
18 : data_o <= 8'hdb;
19 : data_o <= 8'hff;
20 : data_o <= 8'hc3;
21 : data_o <= 8'he7;
22 : data_o <= 8'hff;
23 : data_o <= 8'h7e;
 
// ASCII 3
24 : data_o <= 8'h6c;
25 : data_o <= 8'hfe;
26 : data_o <= 8'hfe;
27 : data_o <= 8'hfe;
28 : data_o <= 8'h7c;
29 : data_o <= 8'h38;
30 : data_o <= 8'h10;
31 : data_o <= 8'h00;
 
// ASCII 4
32 : data_o <= 8'h10;
33 : data_o <= 8'h38;
34 : data_o <= 8'h7c;
35 : data_o <= 8'hfe;
36 : data_o <= 8'h7c;
37 : data_o <= 8'h38;
38 : data_o <= 8'h10;
39 : data_o <= 8'h00;
 
// ASCII 5
40 : data_o <= 8'h38;
41 : data_o <= 8'h7c;
42 : data_o <= 8'h38;
43 : data_o <= 8'hfe;
44 : data_o <= 8'hfe;
45 : data_o <= 8'hd6;
46 : data_o <= 8'h10;
47 : data_o <= 8'h38;
 
// ASCII 6
48 : data_o <= 8'h10;
49 : data_o <= 8'h38;
50 : data_o <= 8'h7c;
51 : data_o <= 8'hfe;
52 : data_o <= 8'hfe;
53 : data_o <= 8'h7c;
54 : data_o <= 8'h10;
55 : data_o <= 8'h38;
 
// ASCII 7
56 : data_o <= 8'h00;
57 : data_o <= 8'h00;
58 : data_o <= 8'h18;
59 : data_o <= 8'h3c;
60 : data_o <= 8'h3c;
61 : data_o <= 8'h18;
62 : data_o <= 8'h00;
63 : data_o <= 8'h00;
 
// ASCII 8
64 : data_o <= 8'hff;
65 : data_o <= 8'hff;
66 : data_o <= 8'he7;
67 : data_o <= 8'hc3;
68 : data_o <= 8'hc3;
69 : data_o <= 8'he7;
70 : data_o <= 8'hff;
71 : data_o <= 8'hff;
 
// ASCII 9
72 : data_o <= 8'h00;
73 : data_o <= 8'h3c;
74 : data_o <= 8'h66;
75 : data_o <= 8'h42;
76 : data_o <= 8'h42;
77 : data_o <= 8'h66;
78 : data_o <= 8'h3c;
79 : data_o <= 8'h00;
 
// ASCII 10
80 : data_o <= 8'hff;
81 : data_o <= 8'hc3;
82 : data_o <= 8'h99;
83 : data_o <= 8'hbd;
84 : data_o <= 8'hbd;
85 : data_o <= 8'h99;
86 : data_o <= 8'hc3;
87 : data_o <= 8'hff;
 
// ASCII 11
88 : data_o <= 8'h0f;
89 : data_o <= 8'h07;
90 : data_o <= 8'h0f;
91 : data_o <= 8'h7d;
92 : data_o <= 8'hcc;
93 : data_o <= 8'hcc;
94 : data_o <= 8'hcc;
95 : data_o <= 8'h78;
 
// ASCII 12
96 : data_o <= 8'h3c;
97 : data_o <= 8'h66;
98 : data_o <= 8'h66;
99 : data_o <= 8'h66;
100 : data_o <= 8'h3c;
101 : data_o <= 8'h18;
102 : data_o <= 8'h7e;
103 : data_o <= 8'h18;
 
// ASCII 13
104 : data_o <= 8'h3f;
105 : data_o <= 8'h33;
106 : data_o <= 8'h3f;
107 : data_o <= 8'h30;
108 : data_o <= 8'h30;
109 : data_o <= 8'h70;
110 : data_o <= 8'hf0;
111 : data_o <= 8'he0;
 
// ASCII 14
112 : data_o <= 8'h7f;
113 : data_o <= 8'h63;
114 : data_o <= 8'h7f;
115 : data_o <= 8'h63;
116 : data_o <= 8'h63;
117 : data_o <= 8'h67;
118 : data_o <= 8'he6;
119 : data_o <= 8'hc0;
 
// ASCII 15
120 : data_o <= 8'h18;
121 : data_o <= 8'hdb;
122 : data_o <= 8'h3c;
123 : data_o <= 8'he7;
124 : data_o <= 8'he7;
125 : data_o <= 8'h3c;
126 : data_o <= 8'hdb;
127 : data_o <= 8'h18;
 
// ASCII 16
128 : data_o <= 8'h80;
129 : data_o <= 8'he0;
130 : data_o <= 8'hf8;
131 : data_o <= 8'hfe;
132 : data_o <= 8'hf8;
133 : data_o <= 8'he0;
134 : data_o <= 8'h80;
135 : data_o <= 8'h00;
 
// ASCII 17
136 : data_o <= 8'h02;
137 : data_o <= 8'h0e;
138 : data_o <= 8'h3e;
139 : data_o <= 8'hfe;
140 : data_o <= 8'h3e;
141 : data_o <= 8'h0e;
142 : data_o <= 8'h02;
143 : data_o <= 8'h00;
 
// ASCII 18
144 : data_o <= 8'h18;
145 : data_o <= 8'h3c;
146 : data_o <= 8'h7e;
147 : data_o <= 8'h18;
148 : data_o <= 8'h18;
149 : data_o <= 8'h7e;
150 : data_o <= 8'h3c;
151 : data_o <= 8'h18;
 
// ASCII 19
152 : data_o <= 8'h66;
153 : data_o <= 8'h66;
154 : data_o <= 8'h66;
155 : data_o <= 8'h66;
156 : data_o <= 8'h66;
157 : data_o <= 8'h00;
158 : data_o <= 8'h66;
159 : data_o <= 8'h00;
 
// ASCII 20
160 : data_o <= 8'h7f;
161 : data_o <= 8'hdb;
162 : data_o <= 8'hdb;
163 : data_o <= 8'h7b;
164 : data_o <= 8'h1b;
165 : data_o <= 8'h1b;
166 : data_o <= 8'h1b;
167 : data_o <= 8'h00;
 
// ASCII 21
168 : data_o <= 8'h3e;
169 : data_o <= 8'h61;
170 : data_o <= 8'h3c;
171 : data_o <= 8'h66;
172 : data_o <= 8'h66;
173 : data_o <= 8'h3c;
174 : data_o <= 8'h86;
175 : data_o <= 8'h7c;
 
// ASCII 22
176 : data_o <= 8'h00;
177 : data_o <= 8'h00;
178 : data_o <= 8'h00;
179 : data_o <= 8'h00;
180 : data_o <= 8'h7e;
181 : data_o <= 8'h7e;
182 : data_o <= 8'h7e;
183 : data_o <= 8'h00;
 
// ASCII 23
184 : data_o <= 8'h18;
185 : data_o <= 8'h3c;
186 : data_o <= 8'h7e;
187 : data_o <= 8'h18;
188 : data_o <= 8'h7e;
189 : data_o <= 8'h3c;
190 : data_o <= 8'h18;
191 : data_o <= 8'hff;
 
// ASCII 24
192 : data_o <= 8'h18;
193 : data_o <= 8'h3c;
194 : data_o <= 8'h7e;
195 : data_o <= 8'h18;
196 : data_o <= 8'h18;
197 : data_o <= 8'h18;
198 : data_o <= 8'h18;
199 : data_o <= 8'h00;
 
// ASCII 25
200 : data_o <= 8'h18;
201 : data_o <= 8'h18;
202 : data_o <= 8'h18;
203 : data_o <= 8'h18;
204 : data_o <= 8'h7e;
205 : data_o <= 8'h3c;
206 : data_o <= 8'h18;
207 : data_o <= 8'h00;
 
// ASCII 26
208 : data_o <= 8'h00;
209 : data_o <= 8'h18;
210 : data_o <= 8'h0c;
211 : data_o <= 8'hfe;
212 : data_o <= 8'h0c;
213 : data_o <= 8'h18;
214 : data_o <= 8'h00;
215 : data_o <= 8'h00;
 
// ASCII 27
216 : data_o <= 8'h00;
217 : data_o <= 8'h30;
218 : data_o <= 8'h60;
219 : data_o <= 8'hfe;
220 : data_o <= 8'h60;
221 : data_o <= 8'h30;
222 : data_o <= 8'h00;
223 : data_o <= 8'h00;
 
// ASCII 28
224 : data_o <= 8'h00;
225 : data_o <= 8'h00;
226 : data_o <= 8'hc0;
227 : data_o <= 8'hc0;
228 : data_o <= 8'hc0;
229 : data_o <= 8'hfe;
230 : data_o <= 8'h00;
231 : data_o <= 8'h00;
 
// ASCII 29
232 : data_o <= 8'h00;
233 : data_o <= 8'h24;
234 : data_o <= 8'h66;
235 : data_o <= 8'hff;
236 : data_o <= 8'h66;
237 : data_o <= 8'h24;
238 : data_o <= 8'h00;
239 : data_o <= 8'h00;
 
// ASCII 30
240 : data_o <= 8'h00;
241 : data_o <= 8'h18;
242 : data_o <= 8'h3c;
243 : data_o <= 8'h7e;
244 : data_o <= 8'hff;
245 : data_o <= 8'hff;
246 : data_o <= 8'h00;
247 : data_o <= 8'h00;
 
// ASCII 31
248 : data_o <= 8'h00;
249 : data_o <= 8'hff;
250 : data_o <= 8'hff;
251 : data_o <= 8'h7e;
252 : data_o <= 8'h3c;
253 : data_o <= 8'h18;
254 : data_o <= 8'h00;
255 : data_o <= 8'h00;
 
// ASCII 32
256 : data_o <= 8'h00;
257 : data_o <= 8'h00;
258 : data_o <= 8'h00;
259 : data_o <= 8'h00;
260 : data_o <= 8'h00;
261 : data_o <= 8'h00;
262 : data_o <= 8'h00;
263 : data_o <= 8'h00;
 
// ASCII 33
264 : data_o <= 8'h18;
265 : data_o <= 8'h3c;
266 : data_o <= 8'h3c;
267 : data_o <= 8'h18;
268 : data_o <= 8'h18;
269 : data_o <= 8'h00;
270 : data_o <= 8'h18;
271 : data_o <= 8'h00;
 
// ASCII 34
272 : data_o <= 8'h66;
273 : data_o <= 8'h66;
274 : data_o <= 8'h24;
275 : data_o <= 8'h00;
276 : data_o <= 8'h00;
277 : data_o <= 8'h00;
278 : data_o <= 8'h00;
279 : data_o <= 8'h00;
 
// ASCII 35
280 : data_o <= 8'h6c;
281 : data_o <= 8'h6c;
282 : data_o <= 8'hfe;
283 : data_o <= 8'h6c;
284 : data_o <= 8'hfe;
285 : data_o <= 8'h6c;
286 : data_o <= 8'h6c;
287 : data_o <= 8'h00;
 
// ASCII 36
288 : data_o <= 8'h18;
289 : data_o <= 8'h3e;
290 : data_o <= 8'h60;
291 : data_o <= 8'h3c;
292 : data_o <= 8'h06;
293 : data_o <= 8'h7c;
294 : data_o <= 8'h18;
295 : data_o <= 8'h00;
 
// ASCII 37
296 : data_o <= 8'h00;
297 : data_o <= 8'hc6;
298 : data_o <= 8'hcc;
299 : data_o <= 8'h18;
300 : data_o <= 8'h30;
301 : data_o <= 8'h66;
302 : data_o <= 8'hc6;
303 : data_o <= 8'h00;
 
// ASCII 38
304 : data_o <= 8'h38;
305 : data_o <= 8'h6c;
306 : data_o <= 8'h38;
307 : data_o <= 8'h76;
308 : data_o <= 8'hdc;
309 : data_o <= 8'hcc;
310 : data_o <= 8'h76;
311 : data_o <= 8'h00;
 
// ASCII 39
312 : data_o <= 8'h18;
313 : data_o <= 8'h18;
314 : data_o <= 8'h30;
315 : data_o <= 8'h00;
316 : data_o <= 8'h00;
317 : data_o <= 8'h00;
318 : data_o <= 8'h00;
319 : data_o <= 8'h00;
 
// ASCII 40
320 : data_o <= 8'h0c;
321 : data_o <= 8'h18;
322 : data_o <= 8'h30;
323 : data_o <= 8'h30;
324 : data_o <= 8'h30;
325 : data_o <= 8'h18;
326 : data_o <= 8'h0c;
327 : data_o <= 8'h00;
 
// ASCII 41
328 : data_o <= 8'h30;
329 : data_o <= 8'h18;
330 : data_o <= 8'h0c;
331 : data_o <= 8'h0c;
332 : data_o <= 8'h0c;
333 : data_o <= 8'h18;
334 : data_o <= 8'h30;
335 : data_o <= 8'h00;
 
// ASCII 42
336 : data_o <= 8'h00;
337 : data_o <= 8'h66;
338 : data_o <= 8'h3c;
339 : data_o <= 8'hff;
340 : data_o <= 8'h3c;
341 : data_o <= 8'h66;
342 : data_o <= 8'h00;
343 : data_o <= 8'h00;
 
// ASCII 43
344 : data_o <= 8'h00;
345 : data_o <= 8'h18;
346 : data_o <= 8'h18;
347 : data_o <= 8'h7e;
348 : data_o <= 8'h18;
349 : data_o <= 8'h18;
350 : data_o <= 8'h00;
351 : data_o <= 8'h00;
 
// ASCII 44
352 : data_o <= 8'h00;
353 : data_o <= 8'h00;
354 : data_o <= 8'h00;
355 : data_o <= 8'h00;
356 : data_o <= 8'h00;
357 : data_o <= 8'h18;
358 : data_o <= 8'h18;
359 : data_o <= 8'h30;
 
// ASCII 45
360 : data_o <= 8'h00;
361 : data_o <= 8'h00;
362 : data_o <= 8'h00;
363 : data_o <= 8'h7e;
364 : data_o <= 8'h00;
365 : data_o <= 8'h00;
366 : data_o <= 8'h00;
367 : data_o <= 8'h00;
 
// ASCII 46
368 : data_o <= 8'h00;
369 : data_o <= 8'h00;
370 : data_o <= 8'h00;
371 : data_o <= 8'h00;
372 : data_o <= 8'h00;
373 : data_o <= 8'h18;
374 : data_o <= 8'h18;
375 : data_o <= 8'h00;
 
// ASCII 47
376 : data_o <= 8'h06;
377 : data_o <= 8'h0c;
378 : data_o <= 8'h18;
379 : data_o <= 8'h30;
380 : data_o <= 8'h60;
381 : data_o <= 8'hc0;
382 : data_o <= 8'h80;
383 : data_o <= 8'h00;
 
// ASCII 48
384 : data_o <= 8'h38;
385 : data_o <= 8'h6c;
386 : data_o <= 8'hc6;
387 : data_o <= 8'hd6;
388 : data_o <= 8'hc6;
389 : data_o <= 8'h6c;
390 : data_o <= 8'h38;
391 : data_o <= 8'h00;
 
// ASCII 49
392 : data_o <= 8'h18;
393 : data_o <= 8'h38;
394 : data_o <= 8'h18;
395 : data_o <= 8'h18;
396 : data_o <= 8'h18;
397 : data_o <= 8'h18;
398 : data_o <= 8'h7e;
399 : data_o <= 8'h00;
 
// ASCII 50
400 : data_o <= 8'h7c;
401 : data_o <= 8'hc6;
402 : data_o <= 8'h06;
403 : data_o <= 8'h1c;
404 : data_o <= 8'h30;
405 : data_o <= 8'h66;
406 : data_o <= 8'hfe;
407 : data_o <= 8'h00;
 
// ASCII 51
408 : data_o <= 8'h7c;
409 : data_o <= 8'hc6;
410 : data_o <= 8'h06;
411 : data_o <= 8'h3c;
412 : data_o <= 8'h06;
413 : data_o <= 8'hc6;
414 : data_o <= 8'h7c;
415 : data_o <= 8'h00;
 
// ASCII 52
416 : data_o <= 8'h1c;
417 : data_o <= 8'h3c;
418 : data_o <= 8'h6c;
419 : data_o <= 8'hcc;
420 : data_o <= 8'hfe;
421 : data_o <= 8'h0c;
422 : data_o <= 8'h1e;
423 : data_o <= 8'h00;
 
// ASCII 53
424 : data_o <= 8'hfe;
425 : data_o <= 8'hc0;
426 : data_o <= 8'hc0;
427 : data_o <= 8'hfc;
428 : data_o <= 8'h06;
429 : data_o <= 8'hc6;
430 : data_o <= 8'h7c;
431 : data_o <= 8'h00;
 
// ASCII 54
432 : data_o <= 8'h38;
433 : data_o <= 8'h60;
434 : data_o <= 8'hc0;
435 : data_o <= 8'hfc;
436 : data_o <= 8'hc6;
437 : data_o <= 8'hc6;
438 : data_o <= 8'h7c;
439 : data_o <= 8'h00;
 
// ASCII 55
440 : data_o <= 8'hfe;
441 : data_o <= 8'hc6;
442 : data_o <= 8'h0c;
443 : data_o <= 8'h18;
444 : data_o <= 8'h30;
445 : data_o <= 8'h30;
446 : data_o <= 8'h30;
447 : data_o <= 8'h00;
 
// ASCII 56
448 : data_o <= 8'h7c;
449 : data_o <= 8'hc6;
450 : data_o <= 8'hc6;
451 : data_o <= 8'h7c;
452 : data_o <= 8'hc6;
453 : data_o <= 8'hc6;
454 : data_o <= 8'h7c;
455 : data_o <= 8'h00;
 
// ASCII 57
456 : data_o <= 8'h7c;
457 : data_o <= 8'hc6;
458 : data_o <= 8'hc6;
459 : data_o <= 8'h7e;
460 : data_o <= 8'h06;
461 : data_o <= 8'h0c;
462 : data_o <= 8'h78;
463 : data_o <= 8'h00;
 
// ASCII 58
464 : data_o <= 8'h00;
465 : data_o <= 8'h18;
466 : data_o <= 8'h18;
467 : data_o <= 8'h00;
468 : data_o <= 8'h00;
469 : data_o <= 8'h18;
470 : data_o <= 8'h18;
471 : data_o <= 8'h00;
 
// ASCII 59
472 : data_o <= 8'h00;
473 : data_o <= 8'h18;
474 : data_o <= 8'h18;
475 : data_o <= 8'h00;
476 : data_o <= 8'h00;
477 : data_o <= 8'h18;
478 : data_o <= 8'h18;
479 : data_o <= 8'h30;
 
// ASCII 60
480 : data_o <= 8'h06;
481 : data_o <= 8'h0c;
482 : data_o <= 8'h18;
483 : data_o <= 8'h30;
484 : data_o <= 8'h18;
485 : data_o <= 8'h0c;
486 : data_o <= 8'h06;
487 : data_o <= 8'h00;
 
// ASCII 61
488 : data_o <= 8'h00;
489 : data_o <= 8'h00;
490 : data_o <= 8'h7e;
491 : data_o <= 8'h00;
492 : data_o <= 8'h00;
493 : data_o <= 8'h7e;
494 : data_o <= 8'h00;
495 : data_o <= 8'h00;
 
// ASCII 62
496 : data_o <= 8'h60;
497 : data_o <= 8'h30;
498 : data_o <= 8'h18;
499 : data_o <= 8'h0c;
500 : data_o <= 8'h18;
501 : data_o <= 8'h30;
502 : data_o <= 8'h60;
503 : data_o <= 8'h00;
 
// ASCII 63
504 : data_o <= 8'h7c;
505 : data_o <= 8'hc6;
506 : data_o <= 8'h0c;
507 : data_o <= 8'h18;
508 : data_o <= 8'h18;
509 : data_o <= 8'h00;
510 : data_o <= 8'h18;
511 : data_o <= 8'h00;
 
// ASCII 64
512 : data_o <= 8'h7c;
513 : data_o <= 8'hc6;
514 : data_o <= 8'hde;
515 : data_o <= 8'hde;
516 : data_o <= 8'hde;
517 : data_o <= 8'hc0;
518 : data_o <= 8'h78;
519 : data_o <= 8'h00;
 
// ASCII 65
520 : data_o <= 8'h38;
521 : data_o <= 8'h6c;
522 : data_o <= 8'hc6;
523 : data_o <= 8'hfe;
524 : data_o <= 8'hc6;
525 : data_o <= 8'hc6;
526 : data_o <= 8'hc6;
527 : data_o <= 8'h00;
 
// ASCII 66
528 : data_o <= 8'hfc;
529 : data_o <= 8'h66;
530 : data_o <= 8'h66;
531 : data_o <= 8'h7c;
532 : data_o <= 8'h66;
533 : data_o <= 8'h66;
534 : data_o <= 8'hfc;
535 : data_o <= 8'h00;
 
// ASCII 67
536 : data_o <= 8'h3c;
537 : data_o <= 8'h66;
538 : data_o <= 8'hc0;
539 : data_o <= 8'hc0;
540 : data_o <= 8'hc0;
541 : data_o <= 8'h66;
542 : data_o <= 8'h3c;
543 : data_o <= 8'h00;
 
// ASCII 68
544 : data_o <= 8'hf8;
545 : data_o <= 8'h6c;
546 : data_o <= 8'h66;
547 : data_o <= 8'h66;
548 : data_o <= 8'h66;
549 : data_o <= 8'h6c;
550 : data_o <= 8'hf8;
551 : data_o <= 8'h00;
 
// ASCII 69
552 : data_o <= 8'hfe;
553 : data_o <= 8'h62;
554 : data_o <= 8'h68;
555 : data_o <= 8'h78;
556 : data_o <= 8'h68;
557 : data_o <= 8'h62;
558 : data_o <= 8'hfe;
559 : data_o <= 8'h00;
 
// ASCII 70
560 : data_o <= 8'hfe;
561 : data_o <= 8'h62;
562 : data_o <= 8'h68;
563 : data_o <= 8'h78;
564 : data_o <= 8'h68;
565 : data_o <= 8'h60;
566 : data_o <= 8'hf0;
567 : data_o <= 8'h00;
 
// ASCII 71
568 : data_o <= 8'h3c;
569 : data_o <= 8'h66;
570 : data_o <= 8'hc0;
571 : data_o <= 8'hc0;
572 : data_o <= 8'hce;
573 : data_o <= 8'h66;
574 : data_o <= 8'h3a;
575 : data_o <= 8'h00;
 
// ASCII 72
576 : data_o <= 8'hc6;
577 : data_o <= 8'hc6;
578 : data_o <= 8'hc6;
579 : data_o <= 8'hfe;
580 : data_o <= 8'hc6;
581 : data_o <= 8'hc6;
582 : data_o <= 8'hc6;
583 : data_o <= 8'h00;
 
// ASCII 73
584 : data_o <= 8'h3c;
585 : data_o <= 8'h18;
586 : data_o <= 8'h18;
587 : data_o <= 8'h18;
588 : data_o <= 8'h18;
589 : data_o <= 8'h18;
590 : data_o <= 8'h3c;
591 : data_o <= 8'h00;
 
// ASCII 74
592 : data_o <= 8'h1e;
593 : data_o <= 8'h0c;
594 : data_o <= 8'h0c;
595 : data_o <= 8'h0c;
596 : data_o <= 8'hcc;
597 : data_o <= 8'hcc;
598 : data_o <= 8'h78;
599 : data_o <= 8'h00;
 
// ASCII 75
600 : data_o <= 8'he6;
601 : data_o <= 8'h66;
602 : data_o <= 8'h6c;
603 : data_o <= 8'h78;
604 : data_o <= 8'h6c;
605 : data_o <= 8'h66;
606 : data_o <= 8'he6;
607 : data_o <= 8'h00;
 
// ASCII 76
608 : data_o <= 8'hf0;
609 : data_o <= 8'h60;
610 : data_o <= 8'h60;
611 : data_o <= 8'h60;
612 : data_o <= 8'h62;
613 : data_o <= 8'h66;
614 : data_o <= 8'hfe;
615 : data_o <= 8'h00;
 
// ASCII 77
616 : data_o <= 8'hc6;
617 : data_o <= 8'hee;
618 : data_o <= 8'hfe;
619 : data_o <= 8'hfe;
620 : data_o <= 8'hd6;
621 : data_o <= 8'hc6;
622 : data_o <= 8'hc6;
623 : data_o <= 8'h00;
 
// ASCII 78
624 : data_o <= 8'hc6;
625 : data_o <= 8'he6;
626 : data_o <= 8'hf6;
627 : data_o <= 8'hde;
628 : data_o <= 8'hce;
629 : data_o <= 8'hc6;
630 : data_o <= 8'hc6;
631 : data_o <= 8'h00;
 
// ASCII 79
632 : data_o <= 8'h7c;
633 : data_o <= 8'hc6;
634 : data_o <= 8'hc6;
635 : data_o <= 8'hc6;
636 : data_o <= 8'hc6;
637 : data_o <= 8'hc6;
638 : data_o <= 8'h7c;
639 : data_o <= 8'h00;
 
// ASCII 80
640 : data_o <= 8'hfc;
641 : data_o <= 8'h66;
642 : data_o <= 8'h66;
643 : data_o <= 8'h7c;
644 : data_o <= 8'h60;
645 : data_o <= 8'h60;
646 : data_o <= 8'hf0;
647 : data_o <= 8'h00;
 
// ASCII 81
648 : data_o <= 8'h7c;
649 : data_o <= 8'hc6;
650 : data_o <= 8'hc6;
651 : data_o <= 8'hc6;
652 : data_o <= 8'hc6;
653 : data_o <= 8'hce;
654 : data_o <= 8'h7c;
655 : data_o <= 8'h0e;
 
// ASCII 82
656 : data_o <= 8'hfc;
657 : data_o <= 8'h66;
658 : data_o <= 8'h66;
659 : data_o <= 8'h7c;
660 : data_o <= 8'h6c;
661 : data_o <= 8'h66;
662 : data_o <= 8'he6;
663 : data_o <= 8'h00;
 
// ASCII 83
664 : data_o <= 8'h3c;
665 : data_o <= 8'h66;
666 : data_o <= 8'h30;
667 : data_o <= 8'h18;
668 : data_o <= 8'h0c;
669 : data_o <= 8'h66;
670 : data_o <= 8'h3c;
671 : data_o <= 8'h00;
 
// ASCII 84
672 : data_o <= 8'h7e;
673 : data_o <= 8'h7e;
674 : data_o <= 8'h5a;
675 : data_o <= 8'h18;
676 : data_o <= 8'h18;
677 : data_o <= 8'h18;
678 : data_o <= 8'h3c;
679 : data_o <= 8'h00;
 
// ASCII 85
680 : data_o <= 8'hc6;
681 : data_o <= 8'hc6;
682 : data_o <= 8'hc6;
683 : data_o <= 8'hc6;
684 : data_o <= 8'hc6;
685 : data_o <= 8'hc6;
686 : data_o <= 8'h7c;
687 : data_o <= 8'h00;
 
// ASCII 86
688 : data_o <= 8'hc6;
689 : data_o <= 8'hc6;
690 : data_o <= 8'hc6;
691 : data_o <= 8'hc6;
692 : data_o <= 8'hc6;
693 : data_o <= 8'h6c;
694 : data_o <= 8'h38;
695 : data_o <= 8'h00;
 
// ASCII 87
696 : data_o <= 8'hc6;
697 : data_o <= 8'hc6;
698 : data_o <= 8'hc6;
699 : data_o <= 8'hd6;
700 : data_o <= 8'hd6;
701 : data_o <= 8'hfe;
702 : data_o <= 8'h6c;
703 : data_o <= 8'h00;
 
// ASCII 88
704 : data_o <= 8'hc6;
705 : data_o <= 8'hc6;
706 : data_o <= 8'h6c;
707 : data_o <= 8'h38;
708 : data_o <= 8'h6c;
709 : data_o <= 8'hc6;
710 : data_o <= 8'hc6;
711 : data_o <= 8'h00;
 
// ASCII 89
712 : data_o <= 8'h66;
713 : data_o <= 8'h66;
714 : data_o <= 8'h66;
715 : data_o <= 8'h3c;
716 : data_o <= 8'h18;
717 : data_o <= 8'h18;
718 : data_o <= 8'h3c;
719 : data_o <= 8'h00;
 
// ASCII 90
720 : data_o <= 8'hfe;
721 : data_o <= 8'hc6;
722 : data_o <= 8'h8c;
723 : data_o <= 8'h18;
724 : data_o <= 8'h32;
725 : data_o <= 8'h66;
726 : data_o <= 8'hfe;
727 : data_o <= 8'h00;
 
// ASCII 91
728 : data_o <= 8'h3c;
729 : data_o <= 8'h30;
730 : data_o <= 8'h30;
731 : data_o <= 8'h30;
732 : data_o <= 8'h30;
733 : data_o <= 8'h30;
734 : data_o <= 8'h3c;
735 : data_o <= 8'h00;
 
// ASCII 92
736 : data_o <= 8'hc0;
737 : data_o <= 8'h60;
738 : data_o <= 8'h30;
739 : data_o <= 8'h18;
740 : data_o <= 8'h0c;
741 : data_o <= 8'h06;
742 : data_o <= 8'h02;
743 : data_o <= 8'h00;
 
// ASCII 93
744 : data_o <= 8'h3c;
745 : data_o <= 8'h0c;
746 : data_o <= 8'h0c;
747 : data_o <= 8'h0c;
748 : data_o <= 8'h0c;
749 : data_o <= 8'h0c;
750 : data_o <= 8'h3c;
751 : data_o <= 8'h00;
 
// ASCII 94
752 : data_o <= 8'h10;
753 : data_o <= 8'h38;
754 : data_o <= 8'h6c;
755 : data_o <= 8'hc6;
756 : data_o <= 8'h00;
757 : data_o <= 8'h00;
758 : data_o <= 8'h00;
759 : data_o <= 8'h00;
 
// ASCII 95
760 : data_o <= 8'h00;
761 : data_o <= 8'h00;
762 : data_o <= 8'h00;
763 : data_o <= 8'h00;
764 : data_o <= 8'h00;
765 : data_o <= 8'h00;
766 : data_o <= 8'h00;
767 : data_o <= 8'hff;
 
// ASCII 96
768 : data_o <= 8'h30;
769 : data_o <= 8'h18;
770 : data_o <= 8'h0c;
771 : data_o <= 8'h00;
772 : data_o <= 8'h00;
773 : data_o <= 8'h00;
774 : data_o <= 8'h00;
775 : data_o <= 8'h00;
 
// ASCII 97
776 : data_o <= 8'h00;
777 : data_o <= 8'h00;
778 : data_o <= 8'h78;
779 : data_o <= 8'h0c;
780 : data_o <= 8'h7c;
781 : data_o <= 8'hcc;
782 : data_o <= 8'h76;
783 : data_o <= 8'h00;
 
// ASCII 98
784 : data_o <= 8'he0;
785 : data_o <= 8'h60;
786 : data_o <= 8'h7c;
787 : data_o <= 8'h66;
788 : data_o <= 8'h66;
789 : data_o <= 8'h66;
790 : data_o <= 8'hdc;
791 : data_o <= 8'h00;
 
// ASCII 99
792 : data_o <= 8'h00;
793 : data_o <= 8'h00;
794 : data_o <= 8'h7c;
795 : data_o <= 8'hc6;
796 : data_o <= 8'hc0;
797 : data_o <= 8'hc6;
798 : data_o <= 8'h7c;
799 : data_o <= 8'h00;
 
// ASCII 100
800 : data_o <= 8'h1c;
801 : data_o <= 8'h0c;
802 : data_o <= 8'h7c;
803 : data_o <= 8'hcc;
804 : data_o <= 8'hcc;
805 : data_o <= 8'hcc;
806 : data_o <= 8'h76;
807 : data_o <= 8'h00;
 
// ASCII 101
808 : data_o <= 8'h00;
809 : data_o <= 8'h00;
810 : data_o <= 8'h7c;
811 : data_o <= 8'hc6;
812 : data_o <= 8'hfe;
813 : data_o <= 8'hc0;
814 : data_o <= 8'h7c;
815 : data_o <= 8'h00;
 
// ASCII 102
816 : data_o <= 8'h3c;
817 : data_o <= 8'h66;
818 : data_o <= 8'h60;
819 : data_o <= 8'hf8;
820 : data_o <= 8'h60;
821 : data_o <= 8'h60;
822 : data_o <= 8'hf0;
823 : data_o <= 8'h00;
 
// ASCII 103
824 : data_o <= 8'h00;
825 : data_o <= 8'h00;
826 : data_o <= 8'h76;
827 : data_o <= 8'hcc;
828 : data_o <= 8'hcc;
829 : data_o <= 8'h7c;
830 : data_o <= 8'h0c;
831 : data_o <= 8'hf8;
 
// ASCII 104
832 : data_o <= 8'he0;
833 : data_o <= 8'h60;
834 : data_o <= 8'h6c;
835 : data_o <= 8'h76;
836 : data_o <= 8'h66;
837 : data_o <= 8'h66;
838 : data_o <= 8'he6;
839 : data_o <= 8'h00;
 
// ASCII 105
840 : data_o <= 8'h18;
841 : data_o <= 8'h00;
842 : data_o <= 8'h38;
843 : data_o <= 8'h18;
844 : data_o <= 8'h18;
845 : data_o <= 8'h18;
846 : data_o <= 8'h3c;
847 : data_o <= 8'h00;
 
// ASCII 106
848 : data_o <= 8'h06;
849 : data_o <= 8'h00;
850 : data_o <= 8'h06;
851 : data_o <= 8'h06;
852 : data_o <= 8'h06;
853 : data_o <= 8'h66;
854 : data_o <= 8'h66;
855 : data_o <= 8'h3c;
 
// ASCII 107
856 : data_o <= 8'he0;
857 : data_o <= 8'h60;
858 : data_o <= 8'h66;
859 : data_o <= 8'h6c;
860 : data_o <= 8'h78;
861 : data_o <= 8'h6c;
862 : data_o <= 8'he6;
863 : data_o <= 8'h00;
 
// ASCII 108
864 : data_o <= 8'h38;
865 : data_o <= 8'h18;
866 : data_o <= 8'h18;
867 : data_o <= 8'h18;
868 : data_o <= 8'h18;
869 : data_o <= 8'h18;
870 : data_o <= 8'h3c;
871 : data_o <= 8'h00;
 
// ASCII 109
872 : data_o <= 8'h00;
873 : data_o <= 8'h00;
874 : data_o <= 8'hec;
875 : data_o <= 8'hfe;
876 : data_o <= 8'hd6;
877 : data_o <= 8'hd6;
878 : data_o <= 8'hd6;
879 : data_o <= 8'h00;
 
// ASCII 110
880 : data_o <= 8'h00;
881 : data_o <= 8'h00;
882 : data_o <= 8'hdc;
883 : data_o <= 8'h66;
884 : data_o <= 8'h66;
885 : data_o <= 8'h66;
886 : data_o <= 8'h66;
887 : data_o <= 8'h00;
 
// ASCII 111
888 : data_o <= 8'h00;
889 : data_o <= 8'h00;
890 : data_o <= 8'h7c;
891 : data_o <= 8'hc6;
892 : data_o <= 8'hc6;
893 : data_o <= 8'hc6;
894 : data_o <= 8'h7c;
895 : data_o <= 8'h00;
 
// ASCII 112
896 : data_o <= 8'h00;
897 : data_o <= 8'h00;
898 : data_o <= 8'hdc;
899 : data_o <= 8'h66;
900 : data_o <= 8'h66;
901 : data_o <= 8'h7c;
902 : data_o <= 8'h60;
903 : data_o <= 8'hf0;
 
// ASCII 113
904 : data_o <= 8'h00;
905 : data_o <= 8'h00;
906 : data_o <= 8'h76;
907 : data_o <= 8'hcc;
908 : data_o <= 8'hcc;
909 : data_o <= 8'h7c;
910 : data_o <= 8'h0c;
911 : data_o <= 8'h1e;
 
// ASCII 114
912 : data_o <= 8'h00;
913 : data_o <= 8'h00;
914 : data_o <= 8'hdc;
915 : data_o <= 8'h76;
916 : data_o <= 8'h60;
917 : data_o <= 8'h60;
918 : data_o <= 8'hf0;
919 : data_o <= 8'h00;
 
// ASCII 115
920 : data_o <= 8'h00;
921 : data_o <= 8'h00;
922 : data_o <= 8'h7e;
923 : data_o <= 8'hc0;
924 : data_o <= 8'h7c;
925 : data_o <= 8'h06;
926 : data_o <= 8'hfc;
927 : data_o <= 8'h00;
 
// ASCII 116
928 : data_o <= 8'h30;
929 : data_o <= 8'h30;
930 : data_o <= 8'hfc;
931 : data_o <= 8'h30;
932 : data_o <= 8'h30;
933 : data_o <= 8'h36;
934 : data_o <= 8'h1c;
935 : data_o <= 8'h00;
 
// ASCII 117
936 : data_o <= 8'h00;
937 : data_o <= 8'h00;
938 : data_o <= 8'hcc;
939 : data_o <= 8'hcc;
940 : data_o <= 8'hcc;
941 : data_o <= 8'hcc;
942 : data_o <= 8'h76;
943 : data_o <= 8'h00;
 
// ASCII 118
944 : data_o <= 8'h00;
945 : data_o <= 8'h00;
946 : data_o <= 8'hc6;
947 : data_o <= 8'hc6;
948 : data_o <= 8'hc6;
949 : data_o <= 8'h6c;
950 : data_o <= 8'h38;
951 : data_o <= 8'h00;
 
// ASCII 119
952 : data_o <= 8'h00;
953 : data_o <= 8'h00;
954 : data_o <= 8'hc6;
955 : data_o <= 8'hd6;
956 : data_o <= 8'hd6;
957 : data_o <= 8'hfe;
958 : data_o <= 8'h6c;
959 : data_o <= 8'h00;
 
// ASCII 120
960 : data_o <= 8'h00;
961 : data_o <= 8'h00;
962 : data_o <= 8'hc6;
963 : data_o <= 8'h6c;
964 : data_o <= 8'h38;
965 : data_o <= 8'h6c;
966 : data_o <= 8'hc6;
967 : data_o <= 8'h00;
 
// ASCII 121
968 : data_o <= 8'h00;
969 : data_o <= 8'h00;
970 : data_o <= 8'hc6;
971 : data_o <= 8'hc6;
972 : data_o <= 8'hc6;
973 : data_o <= 8'h7e;
974 : data_o <= 8'h06;
975 : data_o <= 8'hfc;
 
// ASCII 122
976 : data_o <= 8'h00;
977 : data_o <= 8'h00;
978 : data_o <= 8'h7e;
979 : data_o <= 8'h4c;
980 : data_o <= 8'h18;
981 : data_o <= 8'h32;
982 : data_o <= 8'h7e;
983 : data_o <= 8'h00;
 
// ASCII 123
984 : data_o <= 8'h0e;
985 : data_o <= 8'h18;
986 : data_o <= 8'h18;
987 : data_o <= 8'h70;
988 : data_o <= 8'h18;
989 : data_o <= 8'h18;
990 : data_o <= 8'h0e;
991 : data_o <= 8'h00;
 
// ASCII 124
992 : data_o <= 8'h18;
993 : data_o <= 8'h18;
994 : data_o <= 8'h18;
995 : data_o <= 8'h18;
996 : data_o <= 8'h18;
997 : data_o <= 8'h18;
998 : data_o <= 8'h18;
999 : data_o <= 8'h00;
 
// ASCII 125
1000 : data_o <= 8'h70;
1001 : data_o <= 8'h18;
1002 : data_o <= 8'h18;
1003 : data_o <= 8'h0e;
1004 : data_o <= 8'h18;
1005 : data_o <= 8'h18;
1006 : data_o <= 8'h70;
1007 : data_o <= 8'h00;
 
// ASCII 126
1008 : data_o <= 8'h76;
1009 : data_o <= 8'hdc;
1010 : data_o <= 8'h00;
1011 : data_o <= 8'h00;
1012 : data_o <= 8'h00;
1013 : data_o <= 8'h00;
1014 : data_o <= 8'h00;
1015 : data_o <= 8'h00;
 
// ASCII 127
1016 : data_o <= 8'h00;
1017 : data_o <= 8'h10;
1018 : data_o <= 8'h38;
1019 : data_o <= 8'h6c;
1020 : data_o <= 8'hc6;
1021 : data_o <= 8'hc6;
1022 : data_o <= 8'hfe;
1023 : data_o <= 8'h00;
 
// ASCII 128
1024 : data_o <= 8'h7c;
1025 : data_o <= 8'hc6;
1026 : data_o <= 8'hc0;
1027 : data_o <= 8'hc0;
1028 : data_o <= 8'hc6;
1029 : data_o <= 8'h7c;
1030 : data_o <= 8'h0c;
1031 : data_o <= 8'h78;
 
// ASCII 129
1032 : data_o <= 8'hcc;
1033 : data_o <= 8'h00;
1034 : data_o <= 8'hcc;
1035 : data_o <= 8'hcc;
1036 : data_o <= 8'hcc;
1037 : data_o <= 8'hcc;
1038 : data_o <= 8'h76;
1039 : data_o <= 8'h00;
 
// ASCII 130
1040 : data_o <= 8'h0c;
1041 : data_o <= 8'h18;
1042 : data_o <= 8'h7c;
1043 : data_o <= 8'hc6;
1044 : data_o <= 8'hfe;
1045 : data_o <= 8'hc0;
1046 : data_o <= 8'h7c;
1047 : data_o <= 8'h00;
 
// ASCII 131
1048 : data_o <= 8'h7c;
1049 : data_o <= 8'h82;
1050 : data_o <= 8'h78;
1051 : data_o <= 8'h0c;
1052 : data_o <= 8'h7c;
1053 : data_o <= 8'hcc;
1054 : data_o <= 8'h76;
1055 : data_o <= 8'h00;
 
// ASCII 132
1056 : data_o <= 8'hc6;
1057 : data_o <= 8'h00;
1058 : data_o <= 8'h78;
1059 : data_o <= 8'h0c;
1060 : data_o <= 8'h7c;
1061 : data_o <= 8'hcc;
1062 : data_o <= 8'h76;
1063 : data_o <= 8'h00;
 
// ASCII 133
1064 : data_o <= 8'h30;
1065 : data_o <= 8'h18;
1066 : data_o <= 8'h78;
1067 : data_o <= 8'h0c;
1068 : data_o <= 8'h7c;
1069 : data_o <= 8'hcc;
1070 : data_o <= 8'h76;
1071 : data_o <= 8'h00;
 
// ASCII 134
1072 : data_o <= 8'h30;
1073 : data_o <= 8'h30;
1074 : data_o <= 8'h78;
1075 : data_o <= 8'h0c;
1076 : data_o <= 8'h7c;
1077 : data_o <= 8'hcc;
1078 : data_o <= 8'h76;
1079 : data_o <= 8'h00;
 
// ASCII 135
1080 : data_o <= 8'h00;
1081 : data_o <= 8'h00;
1082 : data_o <= 8'h7e;
1083 : data_o <= 8'hc0;
1084 : data_o <= 8'hc0;
1085 : data_o <= 8'h7e;
1086 : data_o <= 8'h0c;
1087 : data_o <= 8'h38;
 
// ASCII 136
1088 : data_o <= 8'h7c;
1089 : data_o <= 8'h82;
1090 : data_o <= 8'h7c;
1091 : data_o <= 8'hc6;
1092 : data_o <= 8'hfe;
1093 : data_o <= 8'hc0;
1094 : data_o <= 8'h7c;
1095 : data_o <= 8'h00;
 
// ASCII 137
1096 : data_o <= 8'hc6;
1097 : data_o <= 8'h00;
1098 : data_o <= 8'h7c;
1099 : data_o <= 8'hc6;
1100 : data_o <= 8'hfe;
1101 : data_o <= 8'hc0;
1102 : data_o <= 8'h7c;
1103 : data_o <= 8'h00;
 
// ASCII 138
1104 : data_o <= 8'h30;
1105 : data_o <= 8'h18;
1106 : data_o <= 8'h7c;
1107 : data_o <= 8'hc6;
1108 : data_o <= 8'hfe;
1109 : data_o <= 8'hc0;
1110 : data_o <= 8'h7c;
1111 : data_o <= 8'h00;
 
// ASCII 139
1112 : data_o <= 8'h66;
1113 : data_o <= 8'h00;
1114 : data_o <= 8'h38;
1115 : data_o <= 8'h18;
1116 : data_o <= 8'h18;
1117 : data_o <= 8'h18;
1118 : data_o <= 8'h3c;
1119 : data_o <= 8'h00;
 
// ASCII 140
1120 : data_o <= 8'h7c;
1121 : data_o <= 8'h82;
1122 : data_o <= 8'h38;
1123 : data_o <= 8'h18;
1124 : data_o <= 8'h18;
1125 : data_o <= 8'h18;
1126 : data_o <= 8'h3c;
1127 : data_o <= 8'h00;
 
// ASCII 141
1128 : data_o <= 8'h30;
1129 : data_o <= 8'h18;
1130 : data_o <= 8'h00;
1131 : data_o <= 8'h38;
1132 : data_o <= 8'h18;
1133 : data_o <= 8'h18;
1134 : data_o <= 8'h3c;
1135 : data_o <= 8'h00;
 
// ASCII 142
1136 : data_o <= 8'hc6;
1137 : data_o <= 8'h38;
1138 : data_o <= 8'h6c;
1139 : data_o <= 8'hc6;
1140 : data_o <= 8'hfe;
1141 : data_o <= 8'hc6;
1142 : data_o <= 8'hc6;
1143 : data_o <= 8'h00;
 
// ASCII 143
1144 : data_o <= 8'h38;
1145 : data_o <= 8'h6c;
1146 : data_o <= 8'h7c;
1147 : data_o <= 8'hc6;
1148 : data_o <= 8'hfe;
1149 : data_o <= 8'hc6;
1150 : data_o <= 8'hc6;
1151 : data_o <= 8'h00;
 
// ASCII 144
1152 : data_o <= 8'h18;
1153 : data_o <= 8'h30;
1154 : data_o <= 8'hfe;
1155 : data_o <= 8'hc0;
1156 : data_o <= 8'hf8;
1157 : data_o <= 8'hc0;
1158 : data_o <= 8'hfe;
1159 : data_o <= 8'h00;
 
// ASCII 145
1160 : data_o <= 8'h00;
1161 : data_o <= 8'h00;
1162 : data_o <= 8'h7e;
1163 : data_o <= 8'h18;
1164 : data_o <= 8'h7e;
1165 : data_o <= 8'hd8;
1166 : data_o <= 8'h7e;
1167 : data_o <= 8'h00;
 
// ASCII 146
1168 : data_o <= 8'h3e;
1169 : data_o <= 8'h6c;
1170 : data_o <= 8'hcc;
1171 : data_o <= 8'hfe;
1172 : data_o <= 8'hcc;
1173 : data_o <= 8'hcc;
1174 : data_o <= 8'hce;
1175 : data_o <= 8'h00;
 
// ASCII 147
1176 : data_o <= 8'h7c;
1177 : data_o <= 8'h82;
1178 : data_o <= 8'h7c;
1179 : data_o <= 8'hc6;
1180 : data_o <= 8'hc6;
1181 : data_o <= 8'hc6;
1182 : data_o <= 8'h7c;
1183 : data_o <= 8'h00;
 
// ASCII 148
1184 : data_o <= 8'hc6;
1185 : data_o <= 8'h00;
1186 : data_o <= 8'h7c;
1187 : data_o <= 8'hc6;
1188 : data_o <= 8'hc6;
1189 : data_o <= 8'hc6;
1190 : data_o <= 8'h7c;
1191 : data_o <= 8'h00;
 
// ASCII 149
1192 : data_o <= 8'h30;
1193 : data_o <= 8'h18;
1194 : data_o <= 8'h7c;
1195 : data_o <= 8'hc6;
1196 : data_o <= 8'hc6;
1197 : data_o <= 8'hc6;
1198 : data_o <= 8'h7c;
1199 : data_o <= 8'h00;
 
// ASCII 150
1200 : data_o <= 8'h78;
1201 : data_o <= 8'h84;
1202 : data_o <= 8'h00;
1203 : data_o <= 8'hcc;
1204 : data_o <= 8'hcc;
1205 : data_o <= 8'hcc;
1206 : data_o <= 8'h76;
1207 : data_o <= 8'h00;
 
// ASCII 151
1208 : data_o <= 8'h60;
1209 : data_o <= 8'h30;
1210 : data_o <= 8'hcc;
1211 : data_o <= 8'hcc;
1212 : data_o <= 8'hcc;
1213 : data_o <= 8'hcc;
1214 : data_o <= 8'h76;
1215 : data_o <= 8'h00;
 
// ASCII 152
1216 : data_o <= 8'hc6;
1217 : data_o <= 8'h00;
1218 : data_o <= 8'hc6;
1219 : data_o <= 8'hc6;
1220 : data_o <= 8'hc6;
1221 : data_o <= 8'h7e;
1222 : data_o <= 8'h06;
1223 : data_o <= 8'hfc;
 
// ASCII 153
1224 : data_o <= 8'hc6;
1225 : data_o <= 8'h38;
1226 : data_o <= 8'h6c;
1227 : data_o <= 8'hc6;
1228 : data_o <= 8'hc6;
1229 : data_o <= 8'h6c;
1230 : data_o <= 8'h38;
1231 : data_o <= 8'h00;
 
// ASCII 154
1232 : data_o <= 8'hc6;
1233 : data_o <= 8'h00;
1234 : data_o <= 8'hc6;
1235 : data_o <= 8'hc6;
1236 : data_o <= 8'hc6;
1237 : data_o <= 8'hc6;
1238 : data_o <= 8'h7c;
1239 : data_o <= 8'h00;
 
// ASCII 155
1240 : data_o <= 8'h18;
1241 : data_o <= 8'h18;
1242 : data_o <= 8'h7e;
1243 : data_o <= 8'hc0;
1244 : data_o <= 8'hc0;
1245 : data_o <= 8'h7e;
1246 : data_o <= 8'h18;
1247 : data_o <= 8'h18;
 
// ASCII 156
1248 : data_o <= 8'h38;
1249 : data_o <= 8'h6c;
1250 : data_o <= 8'h64;
1251 : data_o <= 8'hf0;
1252 : data_o <= 8'h60;
1253 : data_o <= 8'h66;
1254 : data_o <= 8'hfc;
1255 : data_o <= 8'h00;
 
// ASCII 157
1256 : data_o <= 8'h66;
1257 : data_o <= 8'h66;
1258 : data_o <= 8'h3c;
1259 : data_o <= 8'h7e;
1260 : data_o <= 8'h18;
1261 : data_o <= 8'h7e;
1262 : data_o <= 8'h18;
1263 : data_o <= 8'h18;
 
// ASCII 158
1264 : data_o <= 8'hf8;
1265 : data_o <= 8'hcc;
1266 : data_o <= 8'hcc;
1267 : data_o <= 8'hfa;
1268 : data_o <= 8'hc6;
1269 : data_o <= 8'hcf;
1270 : data_o <= 8'hc6;
1271 : data_o <= 8'hc7;
 
// ASCII 159
1272 : data_o <= 8'h0e;
1273 : data_o <= 8'h1b;
1274 : data_o <= 8'h18;
1275 : data_o <= 8'h3c;
1276 : data_o <= 8'h18;
1277 : data_o <= 8'hd8;
1278 : data_o <= 8'h70;
1279 : data_o <= 8'h00;
 
// ASCII 160
1280 : data_o <= 8'h18;
1281 : data_o <= 8'h30;
1282 : data_o <= 8'h78;
1283 : data_o <= 8'h0c;
1284 : data_o <= 8'h7c;
1285 : data_o <= 8'hcc;
1286 : data_o <= 8'h76;
1287 : data_o <= 8'h00;
 
// ASCII 161
1288 : data_o <= 8'h0c;
1289 : data_o <= 8'h18;
1290 : data_o <= 8'h00;
1291 : data_o <= 8'h38;
1292 : data_o <= 8'h18;
1293 : data_o <= 8'h18;
1294 : data_o <= 8'h3c;
1295 : data_o <= 8'h00;
 
// ASCII 162
1296 : data_o <= 8'h0c;
1297 : data_o <= 8'h18;
1298 : data_o <= 8'h7c;
1299 : data_o <= 8'hc6;
1300 : data_o <= 8'hc6;
1301 : data_o <= 8'hc6;
1302 : data_o <= 8'h7c;
1303 : data_o <= 8'h00;
 
// ASCII 163
1304 : data_o <= 8'h18;
1305 : data_o <= 8'h30;
1306 : data_o <= 8'hcc;
1307 : data_o <= 8'hcc;
1308 : data_o <= 8'hcc;
1309 : data_o <= 8'hcc;
1310 : data_o <= 8'h76;
1311 : data_o <= 8'h00;
 
// ASCII 164
1312 : data_o <= 8'h76;
1313 : data_o <= 8'hdc;
1314 : data_o <= 8'h00;
1315 : data_o <= 8'hdc;
1316 : data_o <= 8'h66;
1317 : data_o <= 8'h66;
1318 : data_o <= 8'h66;
1319 : data_o <= 8'h00;
 
// ASCII 165
1320 : data_o <= 8'h76;
1321 : data_o <= 8'hdc;
1322 : data_o <= 8'h00;
1323 : data_o <= 8'he6;
1324 : data_o <= 8'hf6;
1325 : data_o <= 8'hde;
1326 : data_o <= 8'hce;
1327 : data_o <= 8'h00;
 
// ASCII 166
1328 : data_o <= 8'h3c;
1329 : data_o <= 8'h6c;
1330 : data_o <= 8'h6c;
1331 : data_o <= 8'h3e;
1332 : data_o <= 8'h00;
1333 : data_o <= 8'h7e;
1334 : data_o <= 8'h00;
1335 : data_o <= 8'h00;
 
// ASCII 167
1336 : data_o <= 8'h38;
1337 : data_o <= 8'h6c;
1338 : data_o <= 8'h6c;
1339 : data_o <= 8'h38;
1340 : data_o <= 8'h00;
1341 : data_o <= 8'h7c;
1342 : data_o <= 8'h00;
1343 : data_o <= 8'h00;
 
// ASCII 168
1344 : data_o <= 8'h18;
1345 : data_o <= 8'h00;
1346 : data_o <= 8'h18;
1347 : data_o <= 8'h18;
1348 : data_o <= 8'h30;
1349 : data_o <= 8'h63;
1350 : data_o <= 8'h3e;
1351 : data_o <= 8'h00;
 
// ASCII 169
1352 : data_o <= 8'h00;
1353 : data_o <= 8'h00;
1354 : data_o <= 8'h00;
1355 : data_o <= 8'hfe;
1356 : data_o <= 8'hc0;
1357 : data_o <= 8'hc0;
1358 : data_o <= 8'h00;
1359 : data_o <= 8'h00;
 
// ASCII 170
1360 : data_o <= 8'h00;
1361 : data_o <= 8'h00;
1362 : data_o <= 8'h00;
1363 : data_o <= 8'hfe;
1364 : data_o <= 8'h06;
1365 : data_o <= 8'h06;
1366 : data_o <= 8'h00;
1367 : data_o <= 8'h00;
 
// ASCII 171
1368 : data_o <= 8'h63;
1369 : data_o <= 8'he6;
1370 : data_o <= 8'h6c;
1371 : data_o <= 8'h7e;
1372 : data_o <= 8'h33;
1373 : data_o <= 8'h66;
1374 : data_o <= 8'hcc;
1375 : data_o <= 8'h0f;
 
// ASCII 172
1376 : data_o <= 8'h63;
1377 : data_o <= 8'he6;
1378 : data_o <= 8'h6c;
1379 : data_o <= 8'h7a;
1380 : data_o <= 8'h36;
1381 : data_o <= 8'h6a;
1382 : data_o <= 8'hdf;
1383 : data_o <= 8'h06;
 
// ASCII 173
1384 : data_o <= 8'h18;
1385 : data_o <= 8'h00;
1386 : data_o <= 8'h18;
1387 : data_o <= 8'h18;
1388 : data_o <= 8'h3c;
1389 : data_o <= 8'h3c;
1390 : data_o <= 8'h18;
1391 : data_o <= 8'h00;
 
// ASCII 174
1392 : data_o <= 8'h00;
1393 : data_o <= 8'h33;
1394 : data_o <= 8'h66;
1395 : data_o <= 8'hcc;
1396 : data_o <= 8'h66;
1397 : data_o <= 8'h33;
1398 : data_o <= 8'h00;
1399 : data_o <= 8'h00;
 
// ASCII 175
1400 : data_o <= 8'h00;
1401 : data_o <= 8'hcc;
1402 : data_o <= 8'h66;
1403 : data_o <= 8'h33;
1404 : data_o <= 8'h66;
1405 : data_o <= 8'hcc;
1406 : data_o <= 8'h00;
1407 : data_o <= 8'h00;
 
// ASCII 176
1408 : data_o <= 8'h22;
1409 : data_o <= 8'h88;
1410 : data_o <= 8'h22;
1411 : data_o <= 8'h88;
1412 : data_o <= 8'h22;
1413 : data_o <= 8'h88;
1414 : data_o <= 8'h22;
1415 : data_o <= 8'h88;
 
// ASCII 177
1416 : data_o <= 8'h55;
1417 : data_o <= 8'haa;
1418 : data_o <= 8'h55;
1419 : data_o <= 8'haa;
1420 : data_o <= 8'h55;
1421 : data_o <= 8'haa;
1422 : data_o <= 8'h55;
1423 : data_o <= 8'haa;
 
// ASCII 178
1424 : data_o <= 8'h77;
1425 : data_o <= 8'hdd;
1426 : data_o <= 8'h77;
1427 : data_o <= 8'hdd;
1428 : data_o <= 8'h77;
1429 : data_o <= 8'hdd;
1430 : data_o <= 8'h77;
1431 : data_o <= 8'hdd;
 
// ASCII 179
1432 : data_o <= 8'h18;
1433 : data_o <= 8'h18;
1434 : data_o <= 8'h18;
1435 : data_o <= 8'h18;
1436 : data_o <= 8'h18;
1437 : data_o <= 8'h18;
1438 : data_o <= 8'h18;
1439 : data_o <= 8'h18;
 
// ASCII 180
1440 : data_o <= 8'h18;
1441 : data_o <= 8'h18;
1442 : data_o <= 8'h18;
1443 : data_o <= 8'h18;
1444 : data_o <= 8'hf8;
1445 : data_o <= 8'h18;
1446 : data_o <= 8'h18;
1447 : data_o <= 8'h18;
 
// ASCII 181
1448 : data_o <= 8'h18;
1449 : data_o <= 8'h18;
1450 : data_o <= 8'hf8;
1451 : data_o <= 8'h18;
1452 : data_o <= 8'hf8;
1453 : data_o <= 8'h18;
1454 : data_o <= 8'h18;
1455 : data_o <= 8'h18;
 
// ASCII 182
1456 : data_o <= 8'h36;
1457 : data_o <= 8'h36;
1458 : data_o <= 8'h36;
1459 : data_o <= 8'h36;
1460 : data_o <= 8'hf6;
1461 : data_o <= 8'h36;
1462 : data_o <= 8'h36;
1463 : data_o <= 8'h36;
 
// ASCII 183
1464 : data_o <= 8'h00;
1465 : data_o <= 8'h00;
1466 : data_o <= 8'h00;
1467 : data_o <= 8'h00;
1468 : data_o <= 8'hfe;
1469 : data_o <= 8'h36;
1470 : data_o <= 8'h36;
1471 : data_o <= 8'h36;
 
// ASCII 184
1472 : data_o <= 8'h00;
1473 : data_o <= 8'h00;
1474 : data_o <= 8'hf8;
1475 : data_o <= 8'h18;
1476 : data_o <= 8'hf8;
1477 : data_o <= 8'h18;
1478 : data_o <= 8'h18;
1479 : data_o <= 8'h18;
 
// ASCII 185
1480 : data_o <= 8'h36;
1481 : data_o <= 8'h36;
1482 : data_o <= 8'hf6;
1483 : data_o <= 8'h06;
1484 : data_o <= 8'hf6;
1485 : data_o <= 8'h36;
1486 : data_o <= 8'h36;
1487 : data_o <= 8'h36;
 
// ASCII 186
1488 : data_o <= 8'h36;
1489 : data_o <= 8'h36;
1490 : data_o <= 8'h36;
1491 : data_o <= 8'h36;
1492 : data_o <= 8'h36;
1493 : data_o <= 8'h36;
1494 : data_o <= 8'h36;
1495 : data_o <= 8'h36;
 
// ASCII 187
1496 : data_o <= 8'h00;
1497 : data_o <= 8'h00;
1498 : data_o <= 8'hfe;
1499 : data_o <= 8'h06;
1500 : data_o <= 8'hf6;
1501 : data_o <= 8'h36;
1502 : data_o <= 8'h36;
1503 : data_o <= 8'h36;
 
// ASCII 188
1504 : data_o <= 8'h36;
1505 : data_o <= 8'h36;
1506 : data_o <= 8'hf6;
1507 : data_o <= 8'h06;
1508 : data_o <= 8'hfe;
1509 : data_o <= 8'h00;
1510 : data_o <= 8'h00;
1511 : data_o <= 8'h00;
 
// ASCII 189
1512 : data_o <= 8'h36;
1513 : data_o <= 8'h36;
1514 : data_o <= 8'h36;
1515 : data_o <= 8'h36;
1516 : data_o <= 8'hfe;
1517 : data_o <= 8'h00;
1518 : data_o <= 8'h00;
1519 : data_o <= 8'h00;
 
// ASCII 190
1520 : data_o <= 8'h18;
1521 : data_o <= 8'h18;
1522 : data_o <= 8'hf8;
1523 : data_o <= 8'h18;
1524 : data_o <= 8'hf8;
1525 : data_o <= 8'h00;
1526 : data_o <= 8'h00;
1527 : data_o <= 8'h00;
 
// ASCII 191
1528 : data_o <= 8'h00;
1529 : data_o <= 8'h00;
1530 : data_o <= 8'h00;
1531 : data_o <= 8'h00;
1532 : data_o <= 8'hf8;
1533 : data_o <= 8'h18;
1534 : data_o <= 8'h18;
1535 : data_o <= 8'h18;
 
// ASCII 192
1536 : data_o <= 8'h18;
1537 : data_o <= 8'h18;
1538 : data_o <= 8'h18;
1539 : data_o <= 8'h18;
1540 : data_o <= 8'h1f;
1541 : data_o <= 8'h00;
1542 : data_o <= 8'h00;
1543 : data_o <= 8'h00;
 
// ASCII 193
1544 : data_o <= 8'h18;
1545 : data_o <= 8'h18;
1546 : data_o <= 8'h18;
1547 : data_o <= 8'h18;
1548 : data_o <= 8'hff;
1549 : data_o <= 8'h00;
1550 : data_o <= 8'h00;
1551 : data_o <= 8'h00;
 
// ASCII 194
1552 : data_o <= 8'h00;
1553 : data_o <= 8'h00;
1554 : data_o <= 8'h00;
1555 : data_o <= 8'h00;
1556 : data_o <= 8'hff;
1557 : data_o <= 8'h18;
1558 : data_o <= 8'h18;
1559 : data_o <= 8'h18;
 
// ASCII 195
1560 : data_o <= 8'h18;
1561 : data_o <= 8'h18;
1562 : data_o <= 8'h18;
1563 : data_o <= 8'h18;
1564 : data_o <= 8'h1f;
1565 : data_o <= 8'h18;
1566 : data_o <= 8'h18;
1567 : data_o <= 8'h18;
 
// ASCII 196
1568 : data_o <= 8'h00;
1569 : data_o <= 8'h00;
1570 : data_o <= 8'h00;
1571 : data_o <= 8'h00;
1572 : data_o <= 8'hff;
1573 : data_o <= 8'h00;
1574 : data_o <= 8'h00;
1575 : data_o <= 8'h00;
 
// ASCII 197
1576 : data_o <= 8'h18;
1577 : data_o <= 8'h18;
1578 : data_o <= 8'h18;
1579 : data_o <= 8'h18;
1580 : data_o <= 8'hff;
1581 : data_o <= 8'h18;
1582 : data_o <= 8'h18;
1583 : data_o <= 8'h18;
 
// ASCII 198
1584 : data_o <= 8'h18;
1585 : data_o <= 8'h18;
1586 : data_o <= 8'h1f;
1587 : data_o <= 8'h18;
1588 : data_o <= 8'h1f;
1589 : data_o <= 8'h18;
1590 : data_o <= 8'h18;
1591 : data_o <= 8'h18;
 
// ASCII 199
1592 : data_o <= 8'h36;
1593 : data_o <= 8'h36;
1594 : data_o <= 8'h36;
1595 : data_o <= 8'h36;
1596 : data_o <= 8'h37;
1597 : data_o <= 8'h36;
1598 : data_o <= 8'h36;
1599 : data_o <= 8'h36;
 
// ASCII 200
1600 : data_o <= 8'h36;
1601 : data_o <= 8'h36;
1602 : data_o <= 8'h37;
1603 : data_o <= 8'h30;
1604 : data_o <= 8'h3f;
1605 : data_o <= 8'h00;
1606 : data_o <= 8'h00;
1607 : data_o <= 8'h00;
 
// ASCII 201
1608 : data_o <= 8'h00;
1609 : data_o <= 8'h00;
1610 : data_o <= 8'h3f;
1611 : data_o <= 8'h30;
1612 : data_o <= 8'h37;
1613 : data_o <= 8'h36;
1614 : data_o <= 8'h36;
1615 : data_o <= 8'h36;
 
// ASCII 202
1616 : data_o <= 8'h36;
1617 : data_o <= 8'h36;
1618 : data_o <= 8'hf7;
1619 : data_o <= 8'h00;
1620 : data_o <= 8'hff;
1621 : data_o <= 8'h00;
1622 : data_o <= 8'h00;
1623 : data_o <= 8'h00;
 
// ASCII 203
1624 : data_o <= 8'h00;
1625 : data_o <= 8'h00;
1626 : data_o <= 8'hff;
1627 : data_o <= 8'h00;
1628 : data_o <= 8'hf7;
1629 : data_o <= 8'h36;
1630 : data_o <= 8'h36;
1631 : data_o <= 8'h36;
 
// ASCII 204
1632 : data_o <= 8'h36;
1633 : data_o <= 8'h36;
1634 : data_o <= 8'h37;
1635 : data_o <= 8'h30;
1636 : data_o <= 8'h37;
1637 : data_o <= 8'h36;
1638 : data_o <= 8'h36;
1639 : data_o <= 8'h36;
 
// ASCII 205
1640 : data_o <= 8'h00;
1641 : data_o <= 8'h00;
1642 : data_o <= 8'hff;
1643 : data_o <= 8'h00;
1644 : data_o <= 8'hff;
1645 : data_o <= 8'h00;
1646 : data_o <= 8'h00;
1647 : data_o <= 8'h00;
 
// ASCII 206
1648 : data_o <= 8'h36;
1649 : data_o <= 8'h36;
1650 : data_o <= 8'hf7;
1651 : data_o <= 8'h00;
1652 : data_o <= 8'hf7;
1653 : data_o <= 8'h36;
1654 : data_o <= 8'h36;
1655 : data_o <= 8'h36;
 
// ASCII 207
1656 : data_o <= 8'h18;
1657 : data_o <= 8'h18;
1658 : data_o <= 8'hff;
1659 : data_o <= 8'h00;
1660 : data_o <= 8'hff;
1661 : data_o <= 8'h00;
1662 : data_o <= 8'h00;
1663 : data_o <= 8'h00;
 
// ASCII 208
1664 : data_o <= 8'h36;
1665 : data_o <= 8'h36;
1666 : data_o <= 8'h36;
1667 : data_o <= 8'h36;
1668 : data_o <= 8'hff;
1669 : data_o <= 8'h00;
1670 : data_o <= 8'h00;
1671 : data_o <= 8'h00;
 
// ASCII 209
1672 : data_o <= 8'h00;
1673 : data_o <= 8'h00;
1674 : data_o <= 8'hff;
1675 : data_o <= 8'h00;
1676 : data_o <= 8'hff;
1677 : data_o <= 8'h18;
1678 : data_o <= 8'h18;
1679 : data_o <= 8'h18;
 
// ASCII 210
1680 : data_o <= 8'h00;
1681 : data_o <= 8'h00;
1682 : data_o <= 8'h00;
1683 : data_o <= 8'h00;
1684 : data_o <= 8'hff;
1685 : data_o <= 8'h36;
1686 : data_o <= 8'h36;
1687 : data_o <= 8'h36;
 
// ASCII 211
1688 : data_o <= 8'h36;
1689 : data_o <= 8'h36;
1690 : data_o <= 8'h36;
1691 : data_o <= 8'h36;
1692 : data_o <= 8'h3f;
1693 : data_o <= 8'h00;
1694 : data_o <= 8'h00;
1695 : data_o <= 8'h00;
 
// ASCII 212
1696 : data_o <= 8'h18;
1697 : data_o <= 8'h18;
1698 : data_o <= 8'h1f;
1699 : data_o <= 8'h18;
1700 : data_o <= 8'h1f;
1701 : data_o <= 8'h00;
1702 : data_o <= 8'h00;
1703 : data_o <= 8'h00;
 
// ASCII 213
1704 : data_o <= 8'h00;
1705 : data_o <= 8'h00;
1706 : data_o <= 8'h1f;
1707 : data_o <= 8'h18;
1708 : data_o <= 8'h1f;
1709 : data_o <= 8'h18;
1710 : data_o <= 8'h18;
1711 : data_o <= 8'h18;
 
// ASCII 214
1712 : data_o <= 8'h00;
1713 : data_o <= 8'h00;
1714 : data_o <= 8'h00;
1715 : data_o <= 8'h00;
1716 : data_o <= 8'h3f;
1717 : data_o <= 8'h36;
1718 : data_o <= 8'h36;
1719 : data_o <= 8'h36;
 
// ASCII 215
1720 : data_o <= 8'h36;
1721 : data_o <= 8'h36;
1722 : data_o <= 8'h36;
1723 : data_o <= 8'h36;
1724 : data_o <= 8'hff;
1725 : data_o <= 8'h36;
1726 : data_o <= 8'h36;
1727 : data_o <= 8'h36;
 
// ASCII 216
1728 : data_o <= 8'h18;
1729 : data_o <= 8'h18;
1730 : data_o <= 8'hff;
1731 : data_o <= 8'h18;
1732 : data_o <= 8'hff;
1733 : data_o <= 8'h18;
1734 : data_o <= 8'h18;
1735 : data_o <= 8'h18;
 
// ASCII 217
1736 : data_o <= 8'h18;
1737 : data_o <= 8'h18;
1738 : data_o <= 8'h18;
1739 : data_o <= 8'h18;
1740 : data_o <= 8'hf8;
1741 : data_o <= 8'h00;
1742 : data_o <= 8'h00;
1743 : data_o <= 8'h00;
 
// ASCII 218
1744 : data_o <= 8'h00;
1745 : data_o <= 8'h00;
1746 : data_o <= 8'h00;
1747 : data_o <= 8'h00;
1748 : data_o <= 8'h1f;
1749 : data_o <= 8'h18;
1750 : data_o <= 8'h18;
1751 : data_o <= 8'h18;
 
// ASCII 219
1752 : data_o <= 8'hff;
1753 : data_o <= 8'hff;
1754 : data_o <= 8'hff;
1755 : data_o <= 8'hff;
1756 : data_o <= 8'hff;
1757 : data_o <= 8'hff;
1758 : data_o <= 8'hff;
1759 : data_o <= 8'hff;
 
// ASCII 220
1760 : data_o <= 8'h00;
1761 : data_o <= 8'h00;
1762 : data_o <= 8'h00;
1763 : data_o <= 8'h00;
1764 : data_o <= 8'hff;
1765 : data_o <= 8'hff;
1766 : data_o <= 8'hff;
1767 : data_o <= 8'hff;
 
// ASCII 221
1768 : data_o <= 8'hf0;
1769 : data_o <= 8'hf0;
1770 : data_o <= 8'hf0;
1771 : data_o <= 8'hf0;
1772 : data_o <= 8'hf0;
1773 : data_o <= 8'hf0;
1774 : data_o <= 8'hf0;
1775 : data_o <= 8'hf0;
 
// ASCII 222
1776 : data_o <= 8'h0f;
1777 : data_o <= 8'h0f;
1778 : data_o <= 8'h0f;
1779 : data_o <= 8'h0f;
1780 : data_o <= 8'h0f;
1781 : data_o <= 8'h0f;
1782 : data_o <= 8'h0f;
1783 : data_o <= 8'h0f;
 
// ASCII 223
1784 : data_o <= 8'hff;
1785 : data_o <= 8'hff;
1786 : data_o <= 8'hff;
1787 : data_o <= 8'hff;
1788 : data_o <= 8'h00;
1789 : data_o <= 8'h00;
1790 : data_o <= 8'h00;
1791 : data_o <= 8'h00;
 
// ASCII 224
1792 : data_o <= 8'h00;
1793 : data_o <= 8'h00;
1794 : data_o <= 8'h76;
1795 : data_o <= 8'hdc;
1796 : data_o <= 8'hc8;
1797 : data_o <= 8'hdc;
1798 : data_o <= 8'h76;
1799 : data_o <= 8'h00;
 
// ASCII 225
1800 : data_o <= 8'h78;
1801 : data_o <= 8'hcc;
1802 : data_o <= 8'hcc;
1803 : data_o <= 8'hd8;
1804 : data_o <= 8'hcc;
1805 : data_o <= 8'hc6;
1806 : data_o <= 8'hcc;
1807 : data_o <= 8'h00;
 
// ASCII 226
1808 : data_o <= 8'hfe;
1809 : data_o <= 8'hc6;
1810 : data_o <= 8'hc0;
1811 : data_o <= 8'hc0;
1812 : data_o <= 8'hc0;
1813 : data_o <= 8'hc0;
1814 : data_o <= 8'hc0;
1815 : data_o <= 8'h00;
 
// ASCII 227
1816 : data_o <= 8'h00;
1817 : data_o <= 8'h00;
1818 : data_o <= 8'hfe;
1819 : data_o <= 8'h6c;
1820 : data_o <= 8'h6c;
1821 : data_o <= 8'h6c;
1822 : data_o <= 8'h6c;
1823 : data_o <= 8'h00;
 
// ASCII 228
1824 : data_o <= 8'hfe;
1825 : data_o <= 8'hc6;
1826 : data_o <= 8'h60;
1827 : data_o <= 8'h30;
1828 : data_o <= 8'h60;
1829 : data_o <= 8'hc6;
1830 : data_o <= 8'hfe;
1831 : data_o <= 8'h00;
 
// ASCII 229
1832 : data_o <= 8'h00;
1833 : data_o <= 8'h00;
1834 : data_o <= 8'h7e;
1835 : data_o <= 8'hd8;
1836 : data_o <= 8'hd8;
1837 : data_o <= 8'hd8;
1838 : data_o <= 8'h70;
1839 : data_o <= 8'h00;
 
// ASCII 230
1840 : data_o <= 8'h00;
1841 : data_o <= 8'h00;
1842 : data_o <= 8'h66;
1843 : data_o <= 8'h66;
1844 : data_o <= 8'h66;
1845 : data_o <= 8'h66;
1846 : data_o <= 8'h7c;
1847 : data_o <= 8'hc0;
 
// ASCII 231
1848 : data_o <= 8'h00;
1849 : data_o <= 8'h76;
1850 : data_o <= 8'hdc;
1851 : data_o <= 8'h18;
1852 : data_o <= 8'h18;
1853 : data_o <= 8'h18;
1854 : data_o <= 8'h18;
1855 : data_o <= 8'h00;
 
// ASCII 232
1856 : data_o <= 8'h7e;
1857 : data_o <= 8'h18;
1858 : data_o <= 8'h3c;
1859 : data_o <= 8'h66;
1860 : data_o <= 8'h66;
1861 : data_o <= 8'h3c;
1862 : data_o <= 8'h18;
1863 : data_o <= 8'h7e;
 
// ASCII 233
1864 : data_o <= 8'h38;
1865 : data_o <= 8'h6c;
1866 : data_o <= 8'hc6;
1867 : data_o <= 8'hfe;
1868 : data_o <= 8'hc6;
1869 : data_o <= 8'h6c;
1870 : data_o <= 8'h38;
1871 : data_o <= 8'h00;
 
// ASCII 234
1872 : data_o <= 8'h38;
1873 : data_o <= 8'h6c;
1874 : data_o <= 8'hc6;
1875 : data_o <= 8'hc6;
1876 : data_o <= 8'h6c;
1877 : data_o <= 8'h6c;
1878 : data_o <= 8'hee;
1879 : data_o <= 8'h00;
 
// ASCII 235
1880 : data_o <= 8'h0e;
1881 : data_o <= 8'h18;
1882 : data_o <= 8'h0c;
1883 : data_o <= 8'h3e;
1884 : data_o <= 8'h66;
1885 : data_o <= 8'h66;
1886 : data_o <= 8'h3c;
1887 : data_o <= 8'h00;
 
// ASCII 236
1888 : data_o <= 8'h00;
1889 : data_o <= 8'h00;
1890 : data_o <= 8'h7e;
1891 : data_o <= 8'hdb;
1892 : data_o <= 8'hdb;
1893 : data_o <= 8'h7e;
1894 : data_o <= 8'h00;
1895 : data_o <= 8'h00;
 
// ASCII 237
1896 : data_o <= 8'h06;
1897 : data_o <= 8'h0c;
1898 : data_o <= 8'h7e;
1899 : data_o <= 8'hdb;
1900 : data_o <= 8'hdb;
1901 : data_o <= 8'h7e;
1902 : data_o <= 8'h60;
1903 : data_o <= 8'hc0;
 
// ASCII 238
1904 : data_o <= 8'h1e;
1905 : data_o <= 8'h30;
1906 : data_o <= 8'h60;
1907 : data_o <= 8'h7e;
1908 : data_o <= 8'h60;
1909 : data_o <= 8'h30;
1910 : data_o <= 8'h1e;
1911 : data_o <= 8'h00;
 
// ASCII 239
1912 : data_o <= 8'h00;
1913 : data_o <= 8'h7c;
1914 : data_o <= 8'hc6;
1915 : data_o <= 8'hc6;
1916 : data_o <= 8'hc6;
1917 : data_o <= 8'hc6;
1918 : data_o <= 8'hc6;
1919 : data_o <= 8'h00;
 
// ASCII 240
1920 : data_o <= 8'h00;
1921 : data_o <= 8'hfe;
1922 : data_o <= 8'h00;
1923 : data_o <= 8'hfe;
1924 : data_o <= 8'h00;
1925 : data_o <= 8'hfe;
1926 : data_o <= 8'h00;
1927 : data_o <= 8'h00;
 
// ASCII 241
1928 : data_o <= 8'h18;
1929 : data_o <= 8'h18;
1930 : data_o <= 8'h7e;
1931 : data_o <= 8'h18;
1932 : data_o <= 8'h18;
1933 : data_o <= 8'h00;
1934 : data_o <= 8'h7e;
1935 : data_o <= 8'h00;
 
// ASCII 242
1936 : data_o <= 8'h30;
1937 : data_o <= 8'h18;
1938 : data_o <= 8'h0c;
1939 : data_o <= 8'h18;
1940 : data_o <= 8'h30;
1941 : data_o <= 8'h00;
1942 : data_o <= 8'h7e;
1943 : data_o <= 8'h00;
 
// ASCII 243
1944 : data_o <= 8'h0c;
1945 : data_o <= 8'h18;
1946 : data_o <= 8'h30;
1947 : data_o <= 8'h18;
1948 : data_o <= 8'h0c;
1949 : data_o <= 8'h00;
1950 : data_o <= 8'h7e;
1951 : data_o <= 8'h00;
 
// ASCII 244
1952 : data_o <= 8'h0e;
1953 : data_o <= 8'h1b;
1954 : data_o <= 8'h1b;
1955 : data_o <= 8'h18;
1956 : data_o <= 8'h18;
1957 : data_o <= 8'h18;
1958 : data_o <= 8'h18;
1959 : data_o <= 8'h18;
 
// ASCII 245
1960 : data_o <= 8'h18;
1961 : data_o <= 8'h18;
1962 : data_o <= 8'h18;
1963 : data_o <= 8'h18;
1964 : data_o <= 8'h18;
1965 : data_o <= 8'hd8;
1966 : data_o <= 8'hd8;
1967 : data_o <= 8'h70;
 
// ASCII 246
1968 : data_o <= 8'h00;
1969 : data_o <= 8'h18;
1970 : data_o <= 8'h00;
1971 : data_o <= 8'h7e;
1972 : data_o <= 8'h00;
1973 : data_o <= 8'h18;
1974 : data_o <= 8'h00;
1975 : data_o <= 8'h00;
 
// ASCII 247
1976 : data_o <= 8'h00;
1977 : data_o <= 8'h76;
1978 : data_o <= 8'hdc;
1979 : data_o <= 8'h00;
1980 : data_o <= 8'h76;
1981 : data_o <= 8'hdc;
1982 : data_o <= 8'h00;
1983 : data_o <= 8'h00;
 
// ASCII 248
1984 : data_o <= 8'h38;
1985 : data_o <= 8'h6c;
1986 : data_o <= 8'h6c;
1987 : data_o <= 8'h38;
1988 : data_o <= 8'h00;
1989 : data_o <= 8'h00;
1990 : data_o <= 8'h00;
1991 : data_o <= 8'h00;
 
// ASCII 249
1992 : data_o <= 8'h00;
1993 : data_o <= 8'h00;
1994 : data_o <= 8'h00;
1995 : data_o <= 8'h18;
1996 : data_o <= 8'h18;
1997 : data_o <= 8'h00;
1998 : data_o <= 8'h00;
1999 : data_o <= 8'h00;
 
// ASCII 250
2000 : data_o <= 8'h00;
2001 : data_o <= 8'h00;
2002 : data_o <= 8'h00;
2003 : data_o <= 8'h18;
2004 : data_o <= 8'h00;
2005 : data_o <= 8'h00;
2006 : data_o <= 8'h00;
2007 : data_o <= 8'h00;
 
// ASCII 251
2008 : data_o <= 8'h0f;
2009 : data_o <= 8'h0c;
2010 : data_o <= 8'h0c;
2011 : data_o <= 8'h0c;
2012 : data_o <= 8'hec;
2013 : data_o <= 8'h6c;
2014 : data_o <= 8'h3c;
2015 : data_o <= 8'h1c;
 
// ASCII 252
2016 : data_o <= 8'h6c;
2017 : data_o <= 8'h36;
2018 : data_o <= 8'h36;
2019 : data_o <= 8'h36;
2020 : data_o <= 8'h36;
2021 : data_o <= 8'h00;
2022 : data_o <= 8'h00;
2023 : data_o <= 8'h00;
 
// ASCII 253
2024 : data_o <= 8'h78;
2025 : data_o <= 8'h0c;
2026 : data_o <= 8'h18;
2027 : data_o <= 8'h30;
2028 : data_o <= 8'h7c;
2029 : data_o <= 8'h00;
2030 : data_o <= 8'h00;
2031 : data_o <= 8'h00;
 
// ASCII 254
2032 : data_o <= 8'h00;
2033 : data_o <= 8'h00;
2034 : data_o <= 8'h3c;
2035 : data_o <= 8'h3c;
2036 : data_o <= 8'h3c;
2037 : data_o <= 8'h3c;
2038 : data_o <= 8'h00;
2039 : data_o <= 8'h00;
 
// ASCII 255
2040 : data_o <= 8'h00;
2041 : data_o <= 8'h00;
2042 : data_o <= 8'h00;
2043 : data_o <= 8'h00;
2044 : data_o <= 8'h00;
2045 : data_o <= 8'h00;
2046 : data_o <= 8'h00;
2047 : data_o <= 8'h00;
 
endcase
end
end
endmodule
/wb_text_vga/fontmap_rom.v
0,0 → 1,2597
/*
* Fontmap ROM
*
* This is the ROM containing the map for a monospaced 8x8 font.
* The address input is the concatenation of the required ASCII code [10:3] and the
* number of the line [2:0] contained into the char (starting from the top).
* It should use only one 2KByte Block RAM on a Xilinx FPGA device.
* The font design is (C) 2005 by Brian Cassidy and released under the Perl license.
* All the rest is (C) 2008 by Simply RISC LLP and released under the GPL license.
*/
 
// synthesis attribute rom_style of fontmap_rom is block;
module fontmap_rom (
input sys_clock_i,
input read_i,
input[10:0] address_i,
output reg[7:0] data_o
);
 
always @(posedge sys_clock_i) begin
if(read_i) begin
case(address_i)
 
// ASCII 0
0 : data_o <= 8'h00;
1 : data_o <= 8'h00;
2 : data_o <= 8'h00;
3 : data_o <= 8'h00;
4 : data_o <= 8'h00;
5 : data_o <= 8'h00;
6 : data_o <= 8'h00;
7 : data_o <= 8'h00;
 
// ASCII 1
8 : data_o <= 8'h7e;
9 : data_o <= 8'h81;
10 : data_o <= 8'ha5;
11 : data_o <= 8'h81;
12 : data_o <= 8'hbd;
13 : data_o <= 8'h99;
14 : data_o <= 8'h81;
15 : data_o <= 8'h7e;
 
// ASCII 2
16 : data_o <= 8'h7e;
17 : data_o <= 8'hff;
18 : data_o <= 8'hdb;
19 : data_o <= 8'hff;
20 : data_o <= 8'hc3;
21 : data_o <= 8'he7;
22 : data_o <= 8'hff;
23 : data_o <= 8'h7e;
 
// ASCII 3
24 : data_o <= 8'h6c;
25 : data_o <= 8'hfe;
26 : data_o <= 8'hfe;
27 : data_o <= 8'hfe;
28 : data_o <= 8'h7c;
29 : data_o <= 8'h38;
30 : data_o <= 8'h10;
31 : data_o <= 8'h00;
 
// ASCII 4
32 : data_o <= 8'h10;
33 : data_o <= 8'h38;
34 : data_o <= 8'h7c;
35 : data_o <= 8'hfe;
36 : data_o <= 8'h7c;
37 : data_o <= 8'h38;
38 : data_o <= 8'h10;
39 : data_o <= 8'h00;
 
// ASCII 5
40 : data_o <= 8'h38;
41 : data_o <= 8'h7c;
42 : data_o <= 8'h38;
43 : data_o <= 8'hfe;
44 : data_o <= 8'hfe;
45 : data_o <= 8'hd6;
46 : data_o <= 8'h10;
47 : data_o <= 8'h38;
 
// ASCII 6
48 : data_o <= 8'h10;
49 : data_o <= 8'h38;
50 : data_o <= 8'h7c;
51 : data_o <= 8'hfe;
52 : data_o <= 8'hfe;
53 : data_o <= 8'h7c;
54 : data_o <= 8'h10;
55 : data_o <= 8'h38;
 
// ASCII 7
56 : data_o <= 8'h00;
57 : data_o <= 8'h00;
58 : data_o <= 8'h18;
59 : data_o <= 8'h3c;
60 : data_o <= 8'h3c;
61 : data_o <= 8'h18;
62 : data_o <= 8'h00;
63 : data_o <= 8'h00;
 
// ASCII 8
64 : data_o <= 8'hff;
65 : data_o <= 8'hff;
66 : data_o <= 8'he7;
67 : data_o <= 8'hc3;
68 : data_o <= 8'hc3;
69 : data_o <= 8'he7;
70 : data_o <= 8'hff;
71 : data_o <= 8'hff;
 
// ASCII 9
72 : data_o <= 8'h00;
73 : data_o <= 8'h3c;
74 : data_o <= 8'h66;
75 : data_o <= 8'h42;
76 : data_o <= 8'h42;
77 : data_o <= 8'h66;
78 : data_o <= 8'h3c;
79 : data_o <= 8'h00;
 
// ASCII 10
/*
80 : data_o <= 8'hff;
81 : data_o <= 8'hc3;
82 : data_o <= 8'h99;
83 : data_o <= 8'hbd;
84 : data_o <= 8'hbd;
85 : data_o <= 8'h99;
86 : data_o <= 8'hc3;
87 : data_o <= 8'hff;
*/
80 : data_o <= 8'h00;
81 : data_o <= 8'h00;
82 : data_o <= 8'h00;
83 : data_o <= 8'h00;
84 : data_o <= 8'h00;
85 : data_o <= 8'h00;
86 : data_o <= 8'h00;
87 : data_o <= 8'h00;
 
// ASCII 11
88 : data_o <= 8'h0f;
89 : data_o <= 8'h07;
90 : data_o <= 8'h0f;
91 : data_o <= 8'h7d;
92 : data_o <= 8'hcc;
93 : data_o <= 8'hcc;
94 : data_o <= 8'hcc;
95 : data_o <= 8'h78;
 
// ASCII 12
96 : data_o <= 8'h3c;
97 : data_o <= 8'h66;
98 : data_o <= 8'h66;
99 : data_o <= 8'h66;
100 : data_o <= 8'h3c;
101 : data_o <= 8'h18;
102 : data_o <= 8'h7e;
103 : data_o <= 8'h18;
 
// ASCII 13
104 : data_o <= 8'h3f;
105 : data_o <= 8'h33;
106 : data_o <= 8'h3f;
107 : data_o <= 8'h30;
108 : data_o <= 8'h30;
109 : data_o <= 8'h70;
110 : data_o <= 8'hf0;
111 : data_o <= 8'he0;
 
// ASCII 14
112 : data_o <= 8'h7f;
113 : data_o <= 8'h63;
114 : data_o <= 8'h7f;
115 : data_o <= 8'h63;
116 : data_o <= 8'h63;
117 : data_o <= 8'h67;
118 : data_o <= 8'he6;
119 : data_o <= 8'hc0;
 
// ASCII 15
120 : data_o <= 8'h18;
121 : data_o <= 8'hdb;
122 : data_o <= 8'h3c;
123 : data_o <= 8'he7;
124 : data_o <= 8'he7;
125 : data_o <= 8'h3c;
126 : data_o <= 8'hdb;
127 : data_o <= 8'h18;
 
// ASCII 16
128 : data_o <= 8'h80;
129 : data_o <= 8'he0;
130 : data_o <= 8'hf8;
131 : data_o <= 8'hfe;
132 : data_o <= 8'hf8;
133 : data_o <= 8'he0;
134 : data_o <= 8'h80;
135 : data_o <= 8'h00;
 
// ASCII 17
136 : data_o <= 8'h02;
137 : data_o <= 8'h0e;
138 : data_o <= 8'h3e;
139 : data_o <= 8'hfe;
140 : data_o <= 8'h3e;
141 : data_o <= 8'h0e;
142 : data_o <= 8'h02;
143 : data_o <= 8'h00;
 
// ASCII 18
144 : data_o <= 8'h18;
145 : data_o <= 8'h3c;
146 : data_o <= 8'h7e;
147 : data_o <= 8'h18;
148 : data_o <= 8'h18;
149 : data_o <= 8'h7e;
150 : data_o <= 8'h3c;
151 : data_o <= 8'h18;
 
// ASCII 19
152 : data_o <= 8'h66;
153 : data_o <= 8'h66;
154 : data_o <= 8'h66;
155 : data_o <= 8'h66;
156 : data_o <= 8'h66;
157 : data_o <= 8'h00;
158 : data_o <= 8'h66;
159 : data_o <= 8'h00;
 
// ASCII 20
160 : data_o <= 8'h7f;
161 : data_o <= 8'hdb;
162 : data_o <= 8'hdb;
163 : data_o <= 8'h7b;
164 : data_o <= 8'h1b;
165 : data_o <= 8'h1b;
166 : data_o <= 8'h1b;
167 : data_o <= 8'h00;
 
// ASCII 21
168 : data_o <= 8'h3e;
169 : data_o <= 8'h61;
170 : data_o <= 8'h3c;
171 : data_o <= 8'h66;
172 : data_o <= 8'h66;
173 : data_o <= 8'h3c;
174 : data_o <= 8'h86;
175 : data_o <= 8'h7c;
 
// ASCII 22
176 : data_o <= 8'h00;
177 : data_o <= 8'h00;
178 : data_o <= 8'h00;
179 : data_o <= 8'h00;
180 : data_o <= 8'h7e;
181 : data_o <= 8'h7e;
182 : data_o <= 8'h7e;
183 : data_o <= 8'h00;
 
// ASCII 23
184 : data_o <= 8'h18;
185 : data_o <= 8'h3c;
186 : data_o <= 8'h7e;
187 : data_o <= 8'h18;
188 : data_o <= 8'h7e;
189 : data_o <= 8'h3c;
190 : data_o <= 8'h18;
191 : data_o <= 8'hff;
 
// ASCII 24
192 : data_o <= 8'h18;
193 : data_o <= 8'h3c;
194 : data_o <= 8'h7e;
195 : data_o <= 8'h18;
196 : data_o <= 8'h18;
197 : data_o <= 8'h18;
198 : data_o <= 8'h18;
199 : data_o <= 8'h00;
 
// ASCII 25
200 : data_o <= 8'h18;
201 : data_o <= 8'h18;
202 : data_o <= 8'h18;
203 : data_o <= 8'h18;
204 : data_o <= 8'h7e;
205 : data_o <= 8'h3c;
206 : data_o <= 8'h18;
207 : data_o <= 8'h00;
 
// ASCII 26
208 : data_o <= 8'h00;
209 : data_o <= 8'h18;
210 : data_o <= 8'h0c;
211 : data_o <= 8'hfe;
212 : data_o <= 8'h0c;
213 : data_o <= 8'h18;
214 : data_o <= 8'h00;
215 : data_o <= 8'h00;
 
// ASCII 27
216 : data_o <= 8'h00;
217 : data_o <= 8'h30;
218 : data_o <= 8'h60;
219 : data_o <= 8'hfe;
220 : data_o <= 8'h60;
221 : data_o <= 8'h30;
222 : data_o <= 8'h00;
223 : data_o <= 8'h00;
 
// ASCII 28
224 : data_o <= 8'h00;
225 : data_o <= 8'h00;
226 : data_o <= 8'hc0;
227 : data_o <= 8'hc0;
228 : data_o <= 8'hc0;
229 : data_o <= 8'hfe;
230 : data_o <= 8'h00;
231 : data_o <= 8'h00;
 
// ASCII 29
232 : data_o <= 8'h00;
233 : data_o <= 8'h24;
234 : data_o <= 8'h66;
235 : data_o <= 8'hff;
236 : data_o <= 8'h66;
237 : data_o <= 8'h24;
238 : data_o <= 8'h00;
239 : data_o <= 8'h00;
 
// ASCII 30
240 : data_o <= 8'h00;
241 : data_o <= 8'h18;
242 : data_o <= 8'h3c;
243 : data_o <= 8'h7e;
244 : data_o <= 8'hff;
245 : data_o <= 8'hff;
246 : data_o <= 8'h00;
247 : data_o <= 8'h00;
 
// ASCII 31
248 : data_o <= 8'h00;
249 : data_o <= 8'hff;
250 : data_o <= 8'hff;
251 : data_o <= 8'h7e;
252 : data_o <= 8'h3c;
253 : data_o <= 8'h18;
254 : data_o <= 8'h00;
255 : data_o <= 8'h00;
 
// ASCII 32
256 : data_o <= 8'h00;
257 : data_o <= 8'h00;
258 : data_o <= 8'h00;
259 : data_o <= 8'h00;
260 : data_o <= 8'h00;
261 : data_o <= 8'h00;
262 : data_o <= 8'h00;
263 : data_o <= 8'h00;
 
// ASCII 33
264 : data_o <= 8'h18;
265 : data_o <= 8'h3c;
266 : data_o <= 8'h3c;
267 : data_o <= 8'h18;
268 : data_o <= 8'h18;
269 : data_o <= 8'h00;
270 : data_o <= 8'h18;
271 : data_o <= 8'h00;
 
// ASCII 34
272 : data_o <= 8'h66;
273 : data_o <= 8'h66;
274 : data_o <= 8'h24;
275 : data_o <= 8'h00;
276 : data_o <= 8'h00;
277 : data_o <= 8'h00;
278 : data_o <= 8'h00;
279 : data_o <= 8'h00;
 
// ASCII 35
280 : data_o <= 8'h6c;
281 : data_o <= 8'h6c;
282 : data_o <= 8'hfe;
283 : data_o <= 8'h6c;
284 : data_o <= 8'hfe;
285 : data_o <= 8'h6c;
286 : data_o <= 8'h6c;
287 : data_o <= 8'h00;
 
// ASCII 36
288 : data_o <= 8'h18;
289 : data_o <= 8'h3e;
290 : data_o <= 8'h60;
291 : data_o <= 8'h3c;
292 : data_o <= 8'h06;
293 : data_o <= 8'h7c;
294 : data_o <= 8'h18;
295 : data_o <= 8'h00;
 
// ASCII 37
296 : data_o <= 8'h00;
297 : data_o <= 8'hc6;
298 : data_o <= 8'hcc;
299 : data_o <= 8'h18;
300 : data_o <= 8'h30;
301 : data_o <= 8'h66;
302 : data_o <= 8'hc6;
303 : data_o <= 8'h00;
 
// ASCII 38
304 : data_o <= 8'h38;
305 : data_o <= 8'h6c;
306 : data_o <= 8'h38;
307 : data_o <= 8'h76;
308 : data_o <= 8'hdc;
309 : data_o <= 8'hcc;
310 : data_o <= 8'h76;
311 : data_o <= 8'h00;
 
// ASCII 39
312 : data_o <= 8'h18;
313 : data_o <= 8'h18;
314 : data_o <= 8'h30;
315 : data_o <= 8'h00;
316 : data_o <= 8'h00;
317 : data_o <= 8'h00;
318 : data_o <= 8'h00;
319 : data_o <= 8'h00;
 
// ASCII 40
320 : data_o <= 8'h0c;
321 : data_o <= 8'h18;
322 : data_o <= 8'h30;
323 : data_o <= 8'h30;
324 : data_o <= 8'h30;
325 : data_o <= 8'h18;
326 : data_o <= 8'h0c;
327 : data_o <= 8'h00;
 
// ASCII 41
328 : data_o <= 8'h30;
329 : data_o <= 8'h18;
330 : data_o <= 8'h0c;
331 : data_o <= 8'h0c;
332 : data_o <= 8'h0c;
333 : data_o <= 8'h18;
334 : data_o <= 8'h30;
335 : data_o <= 8'h00;
 
// ASCII 42
336 : data_o <= 8'h00;
337 : data_o <= 8'h66;
338 : data_o <= 8'h3c;
339 : data_o <= 8'hff;
340 : data_o <= 8'h3c;
341 : data_o <= 8'h66;
342 : data_o <= 8'h00;
343 : data_o <= 8'h00;
 
// ASCII 43
344 : data_o <= 8'h00;
345 : data_o <= 8'h18;
346 : data_o <= 8'h18;
347 : data_o <= 8'h7e;
348 : data_o <= 8'h18;
349 : data_o <= 8'h18;
350 : data_o <= 8'h00;
351 : data_o <= 8'h00;
 
// ASCII 44
352 : data_o <= 8'h00;
353 : data_o <= 8'h00;
354 : data_o <= 8'h00;
355 : data_o <= 8'h00;
356 : data_o <= 8'h00;
357 : data_o <= 8'h18;
358 : data_o <= 8'h18;
359 : data_o <= 8'h30;
 
// ASCII 45
360 : data_o <= 8'h00;
361 : data_o <= 8'h00;
362 : data_o <= 8'h00;
363 : data_o <= 8'h7e;
364 : data_o <= 8'h00;
365 : data_o <= 8'h00;
366 : data_o <= 8'h00;
367 : data_o <= 8'h00;
 
// ASCII 46
368 : data_o <= 8'h00;
369 : data_o <= 8'h00;
370 : data_o <= 8'h00;
371 : data_o <= 8'h00;
372 : data_o <= 8'h00;
373 : data_o <= 8'h18;
374 : data_o <= 8'h18;
375 : data_o <= 8'h00;
 
// ASCII 47
376 : data_o <= 8'h06;
377 : data_o <= 8'h0c;
378 : data_o <= 8'h18;
379 : data_o <= 8'h30;
380 : data_o <= 8'h60;
381 : data_o <= 8'hc0;
382 : data_o <= 8'h80;
383 : data_o <= 8'h00;
 
// ASCII 48
384 : data_o <= 8'h38;
385 : data_o <= 8'h6c;
386 : data_o <= 8'hc6;
387 : data_o <= 8'hd6;
388 : data_o <= 8'hc6;
389 : data_o <= 8'h6c;
390 : data_o <= 8'h38;
391 : data_o <= 8'h00;
 
// ASCII 49
392 : data_o <= 8'h18;
393 : data_o <= 8'h38;
394 : data_o <= 8'h18;
395 : data_o <= 8'h18;
396 : data_o <= 8'h18;
397 : data_o <= 8'h18;
398 : data_o <= 8'h7e;
399 : data_o <= 8'h00;
 
// ASCII 50
400 : data_o <= 8'h7c;
401 : data_o <= 8'hc6;
402 : data_o <= 8'h06;
403 : data_o <= 8'h1c;
404 : data_o <= 8'h30;
405 : data_o <= 8'h66;
406 : data_o <= 8'hfe;
407 : data_o <= 8'h00;
 
// ASCII 51
408 : data_o <= 8'h7c;
409 : data_o <= 8'hc6;
410 : data_o <= 8'h06;
411 : data_o <= 8'h3c;
412 : data_o <= 8'h06;
413 : data_o <= 8'hc6;
414 : data_o <= 8'h7c;
415 : data_o <= 8'h00;
 
// ASCII 52
416 : data_o <= 8'h1c;
417 : data_o <= 8'h3c;
418 : data_o <= 8'h6c;
419 : data_o <= 8'hcc;
420 : data_o <= 8'hfe;
421 : data_o <= 8'h0c;
422 : data_o <= 8'h1e;
423 : data_o <= 8'h00;
 
// ASCII 53
424 : data_o <= 8'hfe;
425 : data_o <= 8'hc0;
426 : data_o <= 8'hc0;
427 : data_o <= 8'hfc;
428 : data_o <= 8'h06;
429 : data_o <= 8'hc6;
430 : data_o <= 8'h7c;
431 : data_o <= 8'h00;
 
// ASCII 54
432 : data_o <= 8'h38;
433 : data_o <= 8'h60;
434 : data_o <= 8'hc0;
435 : data_o <= 8'hfc;
436 : data_o <= 8'hc6;
437 : data_o <= 8'hc6;
438 : data_o <= 8'h7c;
439 : data_o <= 8'h00;
 
// ASCII 55
440 : data_o <= 8'hfe;
441 : data_o <= 8'hc6;
442 : data_o <= 8'h0c;
443 : data_o <= 8'h18;
444 : data_o <= 8'h30;
445 : data_o <= 8'h30;
446 : data_o <= 8'h30;
447 : data_o <= 8'h00;
 
// ASCII 56
448 : data_o <= 8'h7c;
449 : data_o <= 8'hc6;
450 : data_o <= 8'hc6;
451 : data_o <= 8'h7c;
452 : data_o <= 8'hc6;
453 : data_o <= 8'hc6;
454 : data_o <= 8'h7c;
455 : data_o <= 8'h00;
 
// ASCII 57
456 : data_o <= 8'h7c;
457 : data_o <= 8'hc6;
458 : data_o <= 8'hc6;
459 : data_o <= 8'h7e;
460 : data_o <= 8'h06;
461 : data_o <= 8'h0c;
462 : data_o <= 8'h78;
463 : data_o <= 8'h00;
 
// ASCII 58
464 : data_o <= 8'h00;
465 : data_o <= 8'h18;
466 : data_o <= 8'h18;
467 : data_o <= 8'h00;
468 : data_o <= 8'h00;
469 : data_o <= 8'h18;
470 : data_o <= 8'h18;
471 : data_o <= 8'h00;
 
// ASCII 59
472 : data_o <= 8'h00;
473 : data_o <= 8'h18;
474 : data_o <= 8'h18;
475 : data_o <= 8'h00;
476 : data_o <= 8'h00;
477 : data_o <= 8'h18;
478 : data_o <= 8'h18;
479 : data_o <= 8'h30;
 
// ASCII 60
480 : data_o <= 8'h06;
481 : data_o <= 8'h0c;
482 : data_o <= 8'h18;
483 : data_o <= 8'h30;
484 : data_o <= 8'h18;
485 : data_o <= 8'h0c;
486 : data_o <= 8'h06;
487 : data_o <= 8'h00;
 
// ASCII 61
488 : data_o <= 8'h00;
489 : data_o <= 8'h00;
490 : data_o <= 8'h7e;
491 : data_o <= 8'h00;
492 : data_o <= 8'h00;
493 : data_o <= 8'h7e;
494 : data_o <= 8'h00;
495 : data_o <= 8'h00;
 
// ASCII 62
496 : data_o <= 8'h60;
497 : data_o <= 8'h30;
498 : data_o <= 8'h18;
499 : data_o <= 8'h0c;
500 : data_o <= 8'h18;
501 : data_o <= 8'h30;
502 : data_o <= 8'h60;
503 : data_o <= 8'h00;
 
// ASCII 63
504 : data_o <= 8'h7c;
505 : data_o <= 8'hc6;
506 : data_o <= 8'h0c;
507 : data_o <= 8'h18;
508 : data_o <= 8'h18;
509 : data_o <= 8'h00;
510 : data_o <= 8'h18;
511 : data_o <= 8'h00;
 
// ASCII 64
512 : data_o <= 8'h7c;
513 : data_o <= 8'hc6;
514 : data_o <= 8'hde;
515 : data_o <= 8'hde;
516 : data_o <= 8'hde;
517 : data_o <= 8'hc0;
518 : data_o <= 8'h78;
519 : data_o <= 8'h00;
 
// ASCII 65
520 : data_o <= 8'h38;
521 : data_o <= 8'h6c;
522 : data_o <= 8'hc6;
523 : data_o <= 8'hfe;
524 : data_o <= 8'hc6;
525 : data_o <= 8'hc6;
526 : data_o <= 8'hc6;
527 : data_o <= 8'h00;
 
// ASCII 66
528 : data_o <= 8'hfc;
529 : data_o <= 8'h66;
530 : data_o <= 8'h66;
531 : data_o <= 8'h7c;
532 : data_o <= 8'h66;
533 : data_o <= 8'h66;
534 : data_o <= 8'hfc;
535 : data_o <= 8'h00;
 
// ASCII 67
536 : data_o <= 8'h3c;
537 : data_o <= 8'h66;
538 : data_o <= 8'hc0;
539 : data_o <= 8'hc0;
540 : data_o <= 8'hc0;
541 : data_o <= 8'h66;
542 : data_o <= 8'h3c;
543 : data_o <= 8'h00;
 
// ASCII 68
544 : data_o <= 8'hf8;
545 : data_o <= 8'h6c;
546 : data_o <= 8'h66;
547 : data_o <= 8'h66;
548 : data_o <= 8'h66;
549 : data_o <= 8'h6c;
550 : data_o <= 8'hf8;
551 : data_o <= 8'h00;
 
// ASCII 69
552 : data_o <= 8'hfe;
553 : data_o <= 8'h62;
554 : data_o <= 8'h68;
555 : data_o <= 8'h78;
556 : data_o <= 8'h68;
557 : data_o <= 8'h62;
558 : data_o <= 8'hfe;
559 : data_o <= 8'h00;
 
// ASCII 70
560 : data_o <= 8'hfe;
561 : data_o <= 8'h62;
562 : data_o <= 8'h68;
563 : data_o <= 8'h78;
564 : data_o <= 8'h68;
565 : data_o <= 8'h60;
566 : data_o <= 8'hf0;
567 : data_o <= 8'h00;
 
// ASCII 71
568 : data_o <= 8'h3c;
569 : data_o <= 8'h66;
570 : data_o <= 8'hc0;
571 : data_o <= 8'hc0;
572 : data_o <= 8'hce;
573 : data_o <= 8'h66;
574 : data_o <= 8'h3a;
575 : data_o <= 8'h00;
 
// ASCII 72
576 : data_o <= 8'hc6;
577 : data_o <= 8'hc6;
578 : data_o <= 8'hc6;
579 : data_o <= 8'hfe;
580 : data_o <= 8'hc6;
581 : data_o <= 8'hc6;
582 : data_o <= 8'hc6;
583 : data_o <= 8'h00;
 
// ASCII 73
584 : data_o <= 8'h3c;
585 : data_o <= 8'h18;
586 : data_o <= 8'h18;
587 : data_o <= 8'h18;
588 : data_o <= 8'h18;
589 : data_o <= 8'h18;
590 : data_o <= 8'h3c;
591 : data_o <= 8'h00;
 
// ASCII 74
592 : data_o <= 8'h1e;
593 : data_o <= 8'h0c;
594 : data_o <= 8'h0c;
595 : data_o <= 8'h0c;
596 : data_o <= 8'hcc;
597 : data_o <= 8'hcc;
598 : data_o <= 8'h78;
599 : data_o <= 8'h00;
 
// ASCII 75
600 : data_o <= 8'he6;
601 : data_o <= 8'h66;
602 : data_o <= 8'h6c;
603 : data_o <= 8'h78;
604 : data_o <= 8'h6c;
605 : data_o <= 8'h66;
606 : data_o <= 8'he6;
607 : data_o <= 8'h00;
 
// ASCII 76
608 : data_o <= 8'hf0;
609 : data_o <= 8'h60;
610 : data_o <= 8'h60;
611 : data_o <= 8'h60;
612 : data_o <= 8'h62;
613 : data_o <= 8'h66;
614 : data_o <= 8'hfe;
615 : data_o <= 8'h00;
 
// ASCII 77
616 : data_o <= 8'hc6;
617 : data_o <= 8'hee;
618 : data_o <= 8'hfe;
619 : data_o <= 8'hfe;
620 : data_o <= 8'hd6;
621 : data_o <= 8'hc6;
622 : data_o <= 8'hc6;
623 : data_o <= 8'h00;
 
// ASCII 78
624 : data_o <= 8'hc6;
625 : data_o <= 8'he6;
626 : data_o <= 8'hf6;
627 : data_o <= 8'hde;
628 : data_o <= 8'hce;
629 : data_o <= 8'hc6;
630 : data_o <= 8'hc6;
631 : data_o <= 8'h00;
 
// ASCII 79
632 : data_o <= 8'h7c;
633 : data_o <= 8'hc6;
634 : data_o <= 8'hc6;
635 : data_o <= 8'hc6;
636 : data_o <= 8'hc6;
637 : data_o <= 8'hc6;
638 : data_o <= 8'h7c;
639 : data_o <= 8'h00;
 
// ASCII 80
640 : data_o <= 8'hfc;
641 : data_o <= 8'h66;
642 : data_o <= 8'h66;
643 : data_o <= 8'h7c;
644 : data_o <= 8'h60;
645 : data_o <= 8'h60;
646 : data_o <= 8'hf0;
647 : data_o <= 8'h00;
 
// ASCII 81
648 : data_o <= 8'h7c;
649 : data_o <= 8'hc6;
650 : data_o <= 8'hc6;
651 : data_o <= 8'hc6;
652 : data_o <= 8'hc6;
653 : data_o <= 8'hce;
654 : data_o <= 8'h7c;
655 : data_o <= 8'h0e;
 
// ASCII 82
656 : data_o <= 8'hfc;
657 : data_o <= 8'h66;
658 : data_o <= 8'h66;
659 : data_o <= 8'h7c;
660 : data_o <= 8'h6c;
661 : data_o <= 8'h66;
662 : data_o <= 8'he6;
663 : data_o <= 8'h00;
 
// ASCII 83
664 : data_o <= 8'h3c;
665 : data_o <= 8'h66;
666 : data_o <= 8'h30;
667 : data_o <= 8'h18;
668 : data_o <= 8'h0c;
669 : data_o <= 8'h66;
670 : data_o <= 8'h3c;
671 : data_o <= 8'h00;
 
// ASCII 84
672 : data_o <= 8'h7e;
673 : data_o <= 8'h7e;
674 : data_o <= 8'h5a;
675 : data_o <= 8'h18;
676 : data_o <= 8'h18;
677 : data_o <= 8'h18;
678 : data_o <= 8'h3c;
679 : data_o <= 8'h00;
 
// ASCII 85
680 : data_o <= 8'hc6;
681 : data_o <= 8'hc6;
682 : data_o <= 8'hc6;
683 : data_o <= 8'hc6;
684 : data_o <= 8'hc6;
685 : data_o <= 8'hc6;
686 : data_o <= 8'h7c;
687 : data_o <= 8'h00;
 
// ASCII 86
688 : data_o <= 8'hc6;
689 : data_o <= 8'hc6;
690 : data_o <= 8'hc6;
691 : data_o <= 8'hc6;
692 : data_o <= 8'hc6;
693 : data_o <= 8'h6c;
694 : data_o <= 8'h38;
695 : data_o <= 8'h00;
 
// ASCII 87
696 : data_o <= 8'hc6;
697 : data_o <= 8'hc6;
698 : data_o <= 8'hc6;
699 : data_o <= 8'hd6;
700 : data_o <= 8'hd6;
701 : data_o <= 8'hfe;
702 : data_o <= 8'h6c;
703 : data_o <= 8'h00;
 
// ASCII 88
704 : data_o <= 8'hc6;
705 : data_o <= 8'hc6;
706 : data_o <= 8'h6c;
707 : data_o <= 8'h38;
708 : data_o <= 8'h6c;
709 : data_o <= 8'hc6;
710 : data_o <= 8'hc6;
711 : data_o <= 8'h00;
 
// ASCII 89
712 : data_o <= 8'h66;
713 : data_o <= 8'h66;
714 : data_o <= 8'h66;
715 : data_o <= 8'h3c;
716 : data_o <= 8'h18;
717 : data_o <= 8'h18;
718 : data_o <= 8'h3c;
719 : data_o <= 8'h00;
 
// ASCII 90
720 : data_o <= 8'hfe;
721 : data_o <= 8'hc6;
722 : data_o <= 8'h8c;
723 : data_o <= 8'h18;
724 : data_o <= 8'h32;
725 : data_o <= 8'h66;
726 : data_o <= 8'hfe;
727 : data_o <= 8'h00;
 
// ASCII 91
728 : data_o <= 8'h3c;
729 : data_o <= 8'h30;
730 : data_o <= 8'h30;
731 : data_o <= 8'h30;
732 : data_o <= 8'h30;
733 : data_o <= 8'h30;
734 : data_o <= 8'h3c;
735 : data_o <= 8'h00;
 
// ASCII 92
736 : data_o <= 8'hc0;
737 : data_o <= 8'h60;
738 : data_o <= 8'h30;
739 : data_o <= 8'h18;
740 : data_o <= 8'h0c;
741 : data_o <= 8'h06;
742 : data_o <= 8'h02;
743 : data_o <= 8'h00;
 
// ASCII 93
744 : data_o <= 8'h3c;
745 : data_o <= 8'h0c;
746 : data_o <= 8'h0c;
747 : data_o <= 8'h0c;
748 : data_o <= 8'h0c;
749 : data_o <= 8'h0c;
750 : data_o <= 8'h3c;
751 : data_o <= 8'h00;
 
// ASCII 94
752 : data_o <= 8'h10;
753 : data_o <= 8'h38;
754 : data_o <= 8'h6c;
755 : data_o <= 8'hc6;
756 : data_o <= 8'h00;
757 : data_o <= 8'h00;
758 : data_o <= 8'h00;
759 : data_o <= 8'h00;
 
// ASCII 95
760 : data_o <= 8'h00;
761 : data_o <= 8'h00;
762 : data_o <= 8'h00;
763 : data_o <= 8'h00;
764 : data_o <= 8'h00;
765 : data_o <= 8'h00;
766 : data_o <= 8'h00;
767 : data_o <= 8'hff;
 
// ASCII 96
768 : data_o <= 8'h30;
769 : data_o <= 8'h18;
770 : data_o <= 8'h0c;
771 : data_o <= 8'h00;
772 : data_o <= 8'h00;
773 : data_o <= 8'h00;
774 : data_o <= 8'h00;
775 : data_o <= 8'h00;
 
// ASCII 97
776 : data_o <= 8'h00;
777 : data_o <= 8'h00;
778 : data_o <= 8'h78;
779 : data_o <= 8'h0c;
780 : data_o <= 8'h7c;
781 : data_o <= 8'hcc;
782 : data_o <= 8'h76;
783 : data_o <= 8'h00;
 
// ASCII 98
784 : data_o <= 8'he0;
785 : data_o <= 8'h60;
786 : data_o <= 8'h7c;
787 : data_o <= 8'h66;
788 : data_o <= 8'h66;
789 : data_o <= 8'h66;
790 : data_o <= 8'hdc;
791 : data_o <= 8'h00;
 
// ASCII 99
792 : data_o <= 8'h00;
793 : data_o <= 8'h00;
794 : data_o <= 8'h7c;
795 : data_o <= 8'hc6;
796 : data_o <= 8'hc0;
797 : data_o <= 8'hc6;
798 : data_o <= 8'h7c;
799 : data_o <= 8'h00;
 
// ASCII 100
800 : data_o <= 8'h1c;
801 : data_o <= 8'h0c;
802 : data_o <= 8'h7c;
803 : data_o <= 8'hcc;
804 : data_o <= 8'hcc;
805 : data_o <= 8'hcc;
806 : data_o <= 8'h76;
807 : data_o <= 8'h00;
 
// ASCII 101
808 : data_o <= 8'h00;
809 : data_o <= 8'h00;
810 : data_o <= 8'h7c;
811 : data_o <= 8'hc6;
812 : data_o <= 8'hfe;
813 : data_o <= 8'hc0;
814 : data_o <= 8'h7c;
815 : data_o <= 8'h00;
 
// ASCII 102
816 : data_o <= 8'h3c;
817 : data_o <= 8'h66;
818 : data_o <= 8'h60;
819 : data_o <= 8'hf8;
820 : data_o <= 8'h60;
821 : data_o <= 8'h60;
822 : data_o <= 8'hf0;
823 : data_o <= 8'h00;
 
// ASCII 103
824 : data_o <= 8'h00;
825 : data_o <= 8'h00;
826 : data_o <= 8'h76;
827 : data_o <= 8'hcc;
828 : data_o <= 8'hcc;
829 : data_o <= 8'h7c;
830 : data_o <= 8'h0c;
831 : data_o <= 8'hf8;
 
// ASCII 104
832 : data_o <= 8'he0;
833 : data_o <= 8'h60;
834 : data_o <= 8'h6c;
835 : data_o <= 8'h76;
836 : data_o <= 8'h66;
837 : data_o <= 8'h66;
838 : data_o <= 8'he6;
839 : data_o <= 8'h00;
 
// ASCII 105
840 : data_o <= 8'h18;
841 : data_o <= 8'h00;
842 : data_o <= 8'h38;
843 : data_o <= 8'h18;
844 : data_o <= 8'h18;
845 : data_o <= 8'h18;
846 : data_o <= 8'h3c;
847 : data_o <= 8'h00;
 
// ASCII 106
848 : data_o <= 8'h06;
849 : data_o <= 8'h00;
850 : data_o <= 8'h06;
851 : data_o <= 8'h06;
852 : data_o <= 8'h06;
853 : data_o <= 8'h66;
854 : data_o <= 8'h66;
855 : data_o <= 8'h3c;
 
// ASCII 107
856 : data_o <= 8'he0;
857 : data_o <= 8'h60;
858 : data_o <= 8'h66;
859 : data_o <= 8'h6c;
860 : data_o <= 8'h78;
861 : data_o <= 8'h6c;
862 : data_o <= 8'he6;
863 : data_o <= 8'h00;
 
// ASCII 108
864 : data_o <= 8'h38;
865 : data_o <= 8'h18;
866 : data_o <= 8'h18;
867 : data_o <= 8'h18;
868 : data_o <= 8'h18;
869 : data_o <= 8'h18;
870 : data_o <= 8'h3c;
871 : data_o <= 8'h00;
 
// ASCII 109
872 : data_o <= 8'h00;
873 : data_o <= 8'h00;
874 : data_o <= 8'hec;
875 : data_o <= 8'hfe;
876 : data_o <= 8'hd6;
877 : data_o <= 8'hd6;
878 : data_o <= 8'hd6;
879 : data_o <= 8'h00;
 
// ASCII 110
880 : data_o <= 8'h00;
881 : data_o <= 8'h00;
882 : data_o <= 8'hdc;
883 : data_o <= 8'h66;
884 : data_o <= 8'h66;
885 : data_o <= 8'h66;
886 : data_o <= 8'h66;
887 : data_o <= 8'h00;
 
// ASCII 111
888 : data_o <= 8'h00;
889 : data_o <= 8'h00;
890 : data_o <= 8'h7c;
891 : data_o <= 8'hc6;
892 : data_o <= 8'hc6;
893 : data_o <= 8'hc6;
894 : data_o <= 8'h7c;
895 : data_o <= 8'h00;
 
// ASCII 112
896 : data_o <= 8'h00;
897 : data_o <= 8'h00;
898 : data_o <= 8'hdc;
899 : data_o <= 8'h66;
900 : data_o <= 8'h66;
901 : data_o <= 8'h7c;
902 : data_o <= 8'h60;
903 : data_o <= 8'hf0;
 
// ASCII 113
904 : data_o <= 8'h00;
905 : data_o <= 8'h00;
906 : data_o <= 8'h76;
907 : data_o <= 8'hcc;
908 : data_o <= 8'hcc;
909 : data_o <= 8'h7c;
910 : data_o <= 8'h0c;
911 : data_o <= 8'h1e;
 
// ASCII 114
912 : data_o <= 8'h00;
913 : data_o <= 8'h00;
914 : data_o <= 8'hdc;
915 : data_o <= 8'h76;
916 : data_o <= 8'h60;
917 : data_o <= 8'h60;
918 : data_o <= 8'hf0;
919 : data_o <= 8'h00;
 
// ASCII 115
920 : data_o <= 8'h00;
921 : data_o <= 8'h00;
922 : data_o <= 8'h7e;
923 : data_o <= 8'hc0;
924 : data_o <= 8'h7c;
925 : data_o <= 8'h06;
926 : data_o <= 8'hfc;
927 : data_o <= 8'h00;
 
// ASCII 116
928 : data_o <= 8'h30;
929 : data_o <= 8'h30;
930 : data_o <= 8'hfc;
931 : data_o <= 8'h30;
932 : data_o <= 8'h30;
933 : data_o <= 8'h36;
934 : data_o <= 8'h1c;
935 : data_o <= 8'h00;
 
// ASCII 117
936 : data_o <= 8'h00;
937 : data_o <= 8'h00;
938 : data_o <= 8'hcc;
939 : data_o <= 8'hcc;
940 : data_o <= 8'hcc;
941 : data_o <= 8'hcc;
942 : data_o <= 8'h76;
943 : data_o <= 8'h00;
 
// ASCII 118
944 : data_o <= 8'h00;
945 : data_o <= 8'h00;
946 : data_o <= 8'hc6;
947 : data_o <= 8'hc6;
948 : data_o <= 8'hc6;
949 : data_o <= 8'h6c;
950 : data_o <= 8'h38;
951 : data_o <= 8'h00;
 
// ASCII 119
952 : data_o <= 8'h00;
953 : data_o <= 8'h00;
954 : data_o <= 8'hc6;
955 : data_o <= 8'hd6;
956 : data_o <= 8'hd6;
957 : data_o <= 8'hfe;
958 : data_o <= 8'h6c;
959 : data_o <= 8'h00;
 
// ASCII 120
960 : data_o <= 8'h00;
961 : data_o <= 8'h00;
962 : data_o <= 8'hc6;
963 : data_o <= 8'h6c;
964 : data_o <= 8'h38;
965 : data_o <= 8'h6c;
966 : data_o <= 8'hc6;
967 : data_o <= 8'h00;
 
// ASCII 121
968 : data_o <= 8'h00;
969 : data_o <= 8'h00;
970 : data_o <= 8'hc6;
971 : data_o <= 8'hc6;
972 : data_o <= 8'hc6;
973 : data_o <= 8'h7e;
974 : data_o <= 8'h06;
975 : data_o <= 8'hfc;
 
// ASCII 122
976 : data_o <= 8'h00;
977 : data_o <= 8'h00;
978 : data_o <= 8'h7e;
979 : data_o <= 8'h4c;
980 : data_o <= 8'h18;
981 : data_o <= 8'h32;
982 : data_o <= 8'h7e;
983 : data_o <= 8'h00;
 
// ASCII 123
984 : data_o <= 8'h0e;
985 : data_o <= 8'h18;
986 : data_o <= 8'h18;
987 : data_o <= 8'h70;
988 : data_o <= 8'h18;
989 : data_o <= 8'h18;
990 : data_o <= 8'h0e;
991 : data_o <= 8'h00;
 
// ASCII 124
992 : data_o <= 8'h18;
993 : data_o <= 8'h18;
994 : data_o <= 8'h18;
995 : data_o <= 8'h18;
996 : data_o <= 8'h18;
997 : data_o <= 8'h18;
998 : data_o <= 8'h18;
999 : data_o <= 8'h00;
 
// ASCII 125
1000 : data_o <= 8'h70;
1001 : data_o <= 8'h18;
1002 : data_o <= 8'h18;
1003 : data_o <= 8'h0e;
1004 : data_o <= 8'h18;
1005 : data_o <= 8'h18;
1006 : data_o <= 8'h70;
1007 : data_o <= 8'h00;
 
// ASCII 126
1008 : data_o <= 8'h76;
1009 : data_o <= 8'hdc;
1010 : data_o <= 8'h00;
1011 : data_o <= 8'h00;
1012 : data_o <= 8'h00;
1013 : data_o <= 8'h00;
1014 : data_o <= 8'h00;
1015 : data_o <= 8'h00;
 
// ASCII 127
1016 : data_o <= 8'h00;
1017 : data_o <= 8'h10;
1018 : data_o <= 8'h38;
1019 : data_o <= 8'h6c;
1020 : data_o <= 8'hc6;
1021 : data_o <= 8'hc6;
1022 : data_o <= 8'hfe;
1023 : data_o <= 8'h00;
 
// ASCII 128
1024 : data_o <= 8'h7c;
1025 : data_o <= 8'hc6;
1026 : data_o <= 8'hc0;
1027 : data_o <= 8'hc0;
1028 : data_o <= 8'hc6;
1029 : data_o <= 8'h7c;
1030 : data_o <= 8'h0c;
1031 : data_o <= 8'h78;
 
// ASCII 129
1032 : data_o <= 8'hcc;
1033 : data_o <= 8'h00;
1034 : data_o <= 8'hcc;
1035 : data_o <= 8'hcc;
1036 : data_o <= 8'hcc;
1037 : data_o <= 8'hcc;
1038 : data_o <= 8'h76;
1039 : data_o <= 8'h00;
 
// ASCII 130
1040 : data_o <= 8'h0c;
1041 : data_o <= 8'h18;
1042 : data_o <= 8'h7c;
1043 : data_o <= 8'hc6;
1044 : data_o <= 8'hfe;
1045 : data_o <= 8'hc0;
1046 : data_o <= 8'h7c;
1047 : data_o <= 8'h00;
 
// ASCII 131
1048 : data_o <= 8'h7c;
1049 : data_o <= 8'h82;
1050 : data_o <= 8'h78;
1051 : data_o <= 8'h0c;
1052 : data_o <= 8'h7c;
1053 : data_o <= 8'hcc;
1054 : data_o <= 8'h76;
1055 : data_o <= 8'h00;
 
// ASCII 132
1056 : data_o <= 8'hc6;
1057 : data_o <= 8'h00;
1058 : data_o <= 8'h78;
1059 : data_o <= 8'h0c;
1060 : data_o <= 8'h7c;
1061 : data_o <= 8'hcc;
1062 : data_o <= 8'h76;
1063 : data_o <= 8'h00;
 
// ASCII 133
1064 : data_o <= 8'h30;
1065 : data_o <= 8'h18;
1066 : data_o <= 8'h78;
1067 : data_o <= 8'h0c;
1068 : data_o <= 8'h7c;
1069 : data_o <= 8'hcc;
1070 : data_o <= 8'h76;
1071 : data_o <= 8'h00;
 
// ASCII 134
1072 : data_o <= 8'h30;
1073 : data_o <= 8'h30;
1074 : data_o <= 8'h78;
1075 : data_o <= 8'h0c;
1076 : data_o <= 8'h7c;
1077 : data_o <= 8'hcc;
1078 : data_o <= 8'h76;
1079 : data_o <= 8'h00;
 
// ASCII 135
1080 : data_o <= 8'h00;
1081 : data_o <= 8'h00;
1082 : data_o <= 8'h7e;
1083 : data_o <= 8'hc0;
1084 : data_o <= 8'hc0;
1085 : data_o <= 8'h7e;
1086 : data_o <= 8'h0c;
1087 : data_o <= 8'h38;
 
// ASCII 136
1088 : data_o <= 8'h7c;
1089 : data_o <= 8'h82;
1090 : data_o <= 8'h7c;
1091 : data_o <= 8'hc6;
1092 : data_o <= 8'hfe;
1093 : data_o <= 8'hc0;
1094 : data_o <= 8'h7c;
1095 : data_o <= 8'h00;
 
// ASCII 137
1096 : data_o <= 8'hc6;
1097 : data_o <= 8'h00;
1098 : data_o <= 8'h7c;
1099 : data_o <= 8'hc6;
1100 : data_o <= 8'hfe;
1101 : data_o <= 8'hc0;
1102 : data_o <= 8'h7c;
1103 : data_o <= 8'h00;
 
// ASCII 138
1104 : data_o <= 8'h30;
1105 : data_o <= 8'h18;
1106 : data_o <= 8'h7c;
1107 : data_o <= 8'hc6;
1108 : data_o <= 8'hfe;
1109 : data_o <= 8'hc0;
1110 : data_o <= 8'h7c;
1111 : data_o <= 8'h00;
 
// ASCII 139
1112 : data_o <= 8'h66;
1113 : data_o <= 8'h00;
1114 : data_o <= 8'h38;
1115 : data_o <= 8'h18;
1116 : data_o <= 8'h18;
1117 : data_o <= 8'h18;
1118 : data_o <= 8'h3c;
1119 : data_o <= 8'h00;
 
// ASCII 140
1120 : data_o <= 8'h7c;
1121 : data_o <= 8'h82;
1122 : data_o <= 8'h38;
1123 : data_o <= 8'h18;
1124 : data_o <= 8'h18;
1125 : data_o <= 8'h18;
1126 : data_o <= 8'h3c;
1127 : data_o <= 8'h00;
 
// ASCII 141
1128 : data_o <= 8'h30;
1129 : data_o <= 8'h18;
1130 : data_o <= 8'h00;
1131 : data_o <= 8'h38;
1132 : data_o <= 8'h18;
1133 : data_o <= 8'h18;
1134 : data_o <= 8'h3c;
1135 : data_o <= 8'h00;
 
// ASCII 142
1136 : data_o <= 8'hc6;
1137 : data_o <= 8'h38;
1138 : data_o <= 8'h6c;
1139 : data_o <= 8'hc6;
1140 : data_o <= 8'hfe;
1141 : data_o <= 8'hc6;
1142 : data_o <= 8'hc6;
1143 : data_o <= 8'h00;
 
// ASCII 143
1144 : data_o <= 8'h38;
1145 : data_o <= 8'h6c;
1146 : data_o <= 8'h7c;
1147 : data_o <= 8'hc6;
1148 : data_o <= 8'hfe;
1149 : data_o <= 8'hc6;
1150 : data_o <= 8'hc6;
1151 : data_o <= 8'h00;
 
// ASCII 144
1152 : data_o <= 8'h18;
1153 : data_o <= 8'h30;
1154 : data_o <= 8'hfe;
1155 : data_o <= 8'hc0;
1156 : data_o <= 8'hf8;
1157 : data_o <= 8'hc0;
1158 : data_o <= 8'hfe;
1159 : data_o <= 8'h00;
 
// ASCII 145
1160 : data_o <= 8'h00;
1161 : data_o <= 8'h00;
1162 : data_o <= 8'h7e;
1163 : data_o <= 8'h18;
1164 : data_o <= 8'h7e;
1165 : data_o <= 8'hd8;
1166 : data_o <= 8'h7e;
1167 : data_o <= 8'h00;
 
// ASCII 146
1168 : data_o <= 8'h3e;
1169 : data_o <= 8'h6c;
1170 : data_o <= 8'hcc;
1171 : data_o <= 8'hfe;
1172 : data_o <= 8'hcc;
1173 : data_o <= 8'hcc;
1174 : data_o <= 8'hce;
1175 : data_o <= 8'h00;
 
// ASCII 147
1176 : data_o <= 8'h7c;
1177 : data_o <= 8'h82;
1178 : data_o <= 8'h7c;
1179 : data_o <= 8'hc6;
1180 : data_o <= 8'hc6;
1181 : data_o <= 8'hc6;
1182 : data_o <= 8'h7c;
1183 : data_o <= 8'h00;
 
// ASCII 148
1184 : data_o <= 8'hc6;
1185 : data_o <= 8'h00;
1186 : data_o <= 8'h7c;
1187 : data_o <= 8'hc6;
1188 : data_o <= 8'hc6;
1189 : data_o <= 8'hc6;
1190 : data_o <= 8'h7c;
1191 : data_o <= 8'h00;
 
// ASCII 149
1192 : data_o <= 8'h30;
1193 : data_o <= 8'h18;
1194 : data_o <= 8'h7c;
1195 : data_o <= 8'hc6;
1196 : data_o <= 8'hc6;
1197 : data_o <= 8'hc6;
1198 : data_o <= 8'h7c;
1199 : data_o <= 8'h00;
 
// ASCII 150
1200 : data_o <= 8'h78;
1201 : data_o <= 8'h84;
1202 : data_o <= 8'h00;
1203 : data_o <= 8'hcc;
1204 : data_o <= 8'hcc;
1205 : data_o <= 8'hcc;
1206 : data_o <= 8'h76;
1207 : data_o <= 8'h00;
 
// ASCII 151
1208 : data_o <= 8'h60;
1209 : data_o <= 8'h30;
1210 : data_o <= 8'hcc;
1211 : data_o <= 8'hcc;
1212 : data_o <= 8'hcc;
1213 : data_o <= 8'hcc;
1214 : data_o <= 8'h76;
1215 : data_o <= 8'h00;
 
// ASCII 152
1216 : data_o <= 8'hc6;
1217 : data_o <= 8'h00;
1218 : data_o <= 8'hc6;
1219 : data_o <= 8'hc6;
1220 : data_o <= 8'hc6;
1221 : data_o <= 8'h7e;
1222 : data_o <= 8'h06;
1223 : data_o <= 8'hfc;
 
// ASCII 153
1224 : data_o <= 8'hc6;
1225 : data_o <= 8'h38;
1226 : data_o <= 8'h6c;
1227 : data_o <= 8'hc6;
1228 : data_o <= 8'hc6;
1229 : data_o <= 8'h6c;
1230 : data_o <= 8'h38;
1231 : data_o <= 8'h00;
 
// ASCII 154
1232 : data_o <= 8'hc6;
1233 : data_o <= 8'h00;
1234 : data_o <= 8'hc6;
1235 : data_o <= 8'hc6;
1236 : data_o <= 8'hc6;
1237 : data_o <= 8'hc6;
1238 : data_o <= 8'h7c;
1239 : data_o <= 8'h00;
 
// ASCII 155
1240 : data_o <= 8'h18;
1241 : data_o <= 8'h18;
1242 : data_o <= 8'h7e;
1243 : data_o <= 8'hc0;
1244 : data_o <= 8'hc0;
1245 : data_o <= 8'h7e;
1246 : data_o <= 8'h18;
1247 : data_o <= 8'h18;
 
// ASCII 156
1248 : data_o <= 8'h38;
1249 : data_o <= 8'h6c;
1250 : data_o <= 8'h64;
1251 : data_o <= 8'hf0;
1252 : data_o <= 8'h60;
1253 : data_o <= 8'h66;
1254 : data_o <= 8'hfc;
1255 : data_o <= 8'h00;
 
// ASCII 157
1256 : data_o <= 8'h66;
1257 : data_o <= 8'h66;
1258 : data_o <= 8'h3c;
1259 : data_o <= 8'h7e;
1260 : data_o <= 8'h18;
1261 : data_o <= 8'h7e;
1262 : data_o <= 8'h18;
1263 : data_o <= 8'h18;
 
// ASCII 158
1264 : data_o <= 8'hf8;
1265 : data_o <= 8'hcc;
1266 : data_o <= 8'hcc;
1267 : data_o <= 8'hfa;
1268 : data_o <= 8'hc6;
1269 : data_o <= 8'hcf;
1270 : data_o <= 8'hc6;
1271 : data_o <= 8'hc7;
 
// ASCII 159
1272 : data_o <= 8'h0e;
1273 : data_o <= 8'h1b;
1274 : data_o <= 8'h18;
1275 : data_o <= 8'h3c;
1276 : data_o <= 8'h18;
1277 : data_o <= 8'hd8;
1278 : data_o <= 8'h70;
1279 : data_o <= 8'h00;
 
// ASCII 160
1280 : data_o <= 8'h18;
1281 : data_o <= 8'h30;
1282 : data_o <= 8'h78;
1283 : data_o <= 8'h0c;
1284 : data_o <= 8'h7c;
1285 : data_o <= 8'hcc;
1286 : data_o <= 8'h76;
1287 : data_o <= 8'h00;
 
// ASCII 161
1288 : data_o <= 8'h0c;
1289 : data_o <= 8'h18;
1290 : data_o <= 8'h00;
1291 : data_o <= 8'h38;
1292 : data_o <= 8'h18;
1293 : data_o <= 8'h18;
1294 : data_o <= 8'h3c;
1295 : data_o <= 8'h00;
 
// ASCII 162
1296 : data_o <= 8'h0c;
1297 : data_o <= 8'h18;
1298 : data_o <= 8'h7c;
1299 : data_o <= 8'hc6;
1300 : data_o <= 8'hc6;
1301 : data_o <= 8'hc6;
1302 : data_o <= 8'h7c;
1303 : data_o <= 8'h00;
 
// ASCII 163
1304 : data_o <= 8'h18;
1305 : data_o <= 8'h30;
1306 : data_o <= 8'hcc;
1307 : data_o <= 8'hcc;
1308 : data_o <= 8'hcc;
1309 : data_o <= 8'hcc;
1310 : data_o <= 8'h76;
1311 : data_o <= 8'h00;
 
// ASCII 164
1312 : data_o <= 8'h76;
1313 : data_o <= 8'hdc;
1314 : data_o <= 8'h00;
1315 : data_o <= 8'hdc;
1316 : data_o <= 8'h66;
1317 : data_o <= 8'h66;
1318 : data_o <= 8'h66;
1319 : data_o <= 8'h00;
 
// ASCII 165
1320 : data_o <= 8'h76;
1321 : data_o <= 8'hdc;
1322 : data_o <= 8'h00;
1323 : data_o <= 8'he6;
1324 : data_o <= 8'hf6;
1325 : data_o <= 8'hde;
1326 : data_o <= 8'hce;
1327 : data_o <= 8'h00;
 
// ASCII 166
1328 : data_o <= 8'h3c;
1329 : data_o <= 8'h6c;
1330 : data_o <= 8'h6c;
1331 : data_o <= 8'h3e;
1332 : data_o <= 8'h00;
1333 : data_o <= 8'h7e;
1334 : data_o <= 8'h00;
1335 : data_o <= 8'h00;
 
// ASCII 167
1336 : data_o <= 8'h38;
1337 : data_o <= 8'h6c;
1338 : data_o <= 8'h6c;
1339 : data_o <= 8'h38;
1340 : data_o <= 8'h00;
1341 : data_o <= 8'h7c;
1342 : data_o <= 8'h00;
1343 : data_o <= 8'h00;
 
// ASCII 168
1344 : data_o <= 8'h18;
1345 : data_o <= 8'h00;
1346 : data_o <= 8'h18;
1347 : data_o <= 8'h18;
1348 : data_o <= 8'h30;
1349 : data_o <= 8'h63;
1350 : data_o <= 8'h3e;
1351 : data_o <= 8'h00;
 
// ASCII 169
1352 : data_o <= 8'h00;
1353 : data_o <= 8'h00;
1354 : data_o <= 8'h00;
1355 : data_o <= 8'hfe;
1356 : data_o <= 8'hc0;
1357 : data_o <= 8'hc0;
1358 : data_o <= 8'h00;
1359 : data_o <= 8'h00;
 
// ASCII 170
1360 : data_o <= 8'h00;
1361 : data_o <= 8'h00;
1362 : data_o <= 8'h00;
1363 : data_o <= 8'hfe;
1364 : data_o <= 8'h06;
1365 : data_o <= 8'h06;
1366 : data_o <= 8'h00;
1367 : data_o <= 8'h00;
 
// ASCII 171
1368 : data_o <= 8'h63;
1369 : data_o <= 8'he6;
1370 : data_o <= 8'h6c;
1371 : data_o <= 8'h7e;
1372 : data_o <= 8'h33;
1373 : data_o <= 8'h66;
1374 : data_o <= 8'hcc;
1375 : data_o <= 8'h0f;
 
// ASCII 172
1376 : data_o <= 8'h63;
1377 : data_o <= 8'he6;
1378 : data_o <= 8'h6c;
1379 : data_o <= 8'h7a;
1380 : data_o <= 8'h36;
1381 : data_o <= 8'h6a;
1382 : data_o <= 8'hdf;
1383 : data_o <= 8'h06;
 
// ASCII 173
1384 : data_o <= 8'h18;
1385 : data_o <= 8'h00;
1386 : data_o <= 8'h18;
1387 : data_o <= 8'h18;
1388 : data_o <= 8'h3c;
1389 : data_o <= 8'h3c;
1390 : data_o <= 8'h18;
1391 : data_o <= 8'h00;
 
// ASCII 174
1392 : data_o <= 8'h00;
1393 : data_o <= 8'h33;
1394 : data_o <= 8'h66;
1395 : data_o <= 8'hcc;
1396 : data_o <= 8'h66;
1397 : data_o <= 8'h33;
1398 : data_o <= 8'h00;
1399 : data_o <= 8'h00;
 
// ASCII 175
1400 : data_o <= 8'h00;
1401 : data_o <= 8'hcc;
1402 : data_o <= 8'h66;
1403 : data_o <= 8'h33;
1404 : data_o <= 8'h66;
1405 : data_o <= 8'hcc;
1406 : data_o <= 8'h00;
1407 : data_o <= 8'h00;
 
// ASCII 176
1408 : data_o <= 8'h22;
1409 : data_o <= 8'h88;
1410 : data_o <= 8'h22;
1411 : data_o <= 8'h88;
1412 : data_o <= 8'h22;
1413 : data_o <= 8'h88;
1414 : data_o <= 8'h22;
1415 : data_o <= 8'h88;
 
// ASCII 177
1416 : data_o <= 8'h55;
1417 : data_o <= 8'haa;
1418 : data_o <= 8'h55;
1419 : data_o <= 8'haa;
1420 : data_o <= 8'h55;
1421 : data_o <= 8'haa;
1422 : data_o <= 8'h55;
1423 : data_o <= 8'haa;
 
// ASCII 178
1424 : data_o <= 8'h77;
1425 : data_o <= 8'hdd;
1426 : data_o <= 8'h77;
1427 : data_o <= 8'hdd;
1428 : data_o <= 8'h77;
1429 : data_o <= 8'hdd;
1430 : data_o <= 8'h77;
1431 : data_o <= 8'hdd;
 
// ASCII 179
1432 : data_o <= 8'h18;
1433 : data_o <= 8'h18;
1434 : data_o <= 8'h18;
1435 : data_o <= 8'h18;
1436 : data_o <= 8'h18;
1437 : data_o <= 8'h18;
1438 : data_o <= 8'h18;
1439 : data_o <= 8'h18;
 
// ASCII 180
1440 : data_o <= 8'h18;
1441 : data_o <= 8'h18;
1442 : data_o <= 8'h18;
1443 : data_o <= 8'h18;
1444 : data_o <= 8'hf8;
1445 : data_o <= 8'h18;
1446 : data_o <= 8'h18;
1447 : data_o <= 8'h18;
 
// ASCII 181
1448 : data_o <= 8'h18;
1449 : data_o <= 8'h18;
1450 : data_o <= 8'hf8;
1451 : data_o <= 8'h18;
1452 : data_o <= 8'hf8;
1453 : data_o <= 8'h18;
1454 : data_o <= 8'h18;
1455 : data_o <= 8'h18;
 
// ASCII 182
1456 : data_o <= 8'h36;
1457 : data_o <= 8'h36;
1458 : data_o <= 8'h36;
1459 : data_o <= 8'h36;
1460 : data_o <= 8'hf6;
1461 : data_o <= 8'h36;
1462 : data_o <= 8'h36;
1463 : data_o <= 8'h36;
 
// ASCII 183
1464 : data_o <= 8'h00;
1465 : data_o <= 8'h00;
1466 : data_o <= 8'h00;
1467 : data_o <= 8'h00;
1468 : data_o <= 8'hfe;
1469 : data_o <= 8'h36;
1470 : data_o <= 8'h36;
1471 : data_o <= 8'h36;
 
// ASCII 184
1472 : data_o <= 8'h00;
1473 : data_o <= 8'h00;
1474 : data_o <= 8'hf8;
1475 : data_o <= 8'h18;
1476 : data_o <= 8'hf8;
1477 : data_o <= 8'h18;
1478 : data_o <= 8'h18;
1479 : data_o <= 8'h18;
 
// ASCII 185
1480 : data_o <= 8'h36;
1481 : data_o <= 8'h36;
1482 : data_o <= 8'hf6;
1483 : data_o <= 8'h06;
1484 : data_o <= 8'hf6;
1485 : data_o <= 8'h36;
1486 : data_o <= 8'h36;
1487 : data_o <= 8'h36;
 
// ASCII 186
1488 : data_o <= 8'h36;
1489 : data_o <= 8'h36;
1490 : data_o <= 8'h36;
1491 : data_o <= 8'h36;
1492 : data_o <= 8'h36;
1493 : data_o <= 8'h36;
1494 : data_o <= 8'h36;
1495 : data_o <= 8'h36;
 
// ASCII 187
1496 : data_o <= 8'h00;
1497 : data_o <= 8'h00;
1498 : data_o <= 8'hfe;
1499 : data_o <= 8'h06;
1500 : data_o <= 8'hf6;
1501 : data_o <= 8'h36;
1502 : data_o <= 8'h36;
1503 : data_o <= 8'h36;
 
// ASCII 188
1504 : data_o <= 8'h36;
1505 : data_o <= 8'h36;
1506 : data_o <= 8'hf6;
1507 : data_o <= 8'h06;
1508 : data_o <= 8'hfe;
1509 : data_o <= 8'h00;
1510 : data_o <= 8'h00;
1511 : data_o <= 8'h00;
 
// ASCII 189
1512 : data_o <= 8'h36;
1513 : data_o <= 8'h36;
1514 : data_o <= 8'h36;
1515 : data_o <= 8'h36;
1516 : data_o <= 8'hfe;
1517 : data_o <= 8'h00;
1518 : data_o <= 8'h00;
1519 : data_o <= 8'h00;
 
// ASCII 190
1520 : data_o <= 8'h18;
1521 : data_o <= 8'h18;
1522 : data_o <= 8'hf8;
1523 : data_o <= 8'h18;
1524 : data_o <= 8'hf8;
1525 : data_o <= 8'h00;
1526 : data_o <= 8'h00;
1527 : data_o <= 8'h00;
 
// ASCII 191
1528 : data_o <= 8'h00;
1529 : data_o <= 8'h00;
1530 : data_o <= 8'h00;
1531 : data_o <= 8'h00;
1532 : data_o <= 8'hf8;
1533 : data_o <= 8'h18;
1534 : data_o <= 8'h18;
1535 : data_o <= 8'h18;
 
// ASCII 192
1536 : data_o <= 8'h18;
1537 : data_o <= 8'h18;
1538 : data_o <= 8'h18;
1539 : data_o <= 8'h18;
1540 : data_o <= 8'h1f;
1541 : data_o <= 8'h00;
1542 : data_o <= 8'h00;
1543 : data_o <= 8'h00;
 
// ASCII 193
1544 : data_o <= 8'h18;
1545 : data_o <= 8'h18;
1546 : data_o <= 8'h18;
1547 : data_o <= 8'h18;
1548 : data_o <= 8'hff;
1549 : data_o <= 8'h00;
1550 : data_o <= 8'h00;
1551 : data_o <= 8'h00;
 
// ASCII 194
1552 : data_o <= 8'h00;
1553 : data_o <= 8'h00;
1554 : data_o <= 8'h00;
1555 : data_o <= 8'h00;
1556 : data_o <= 8'hff;
1557 : data_o <= 8'h18;
1558 : data_o <= 8'h18;
1559 : data_o <= 8'h18;
 
// ASCII 195
1560 : data_o <= 8'h18;
1561 : data_o <= 8'h18;
1562 : data_o <= 8'h18;
1563 : data_o <= 8'h18;
1564 : data_o <= 8'h1f;
1565 : data_o <= 8'h18;
1566 : data_o <= 8'h18;
1567 : data_o <= 8'h18;
 
// ASCII 196
1568 : data_o <= 8'h00;
1569 : data_o <= 8'h00;
1570 : data_o <= 8'h00;
1571 : data_o <= 8'h00;
1572 : data_o <= 8'hff;
1573 : data_o <= 8'h00;
1574 : data_o <= 8'h00;
1575 : data_o <= 8'h00;
 
// ASCII 197
1576 : data_o <= 8'h18;
1577 : data_o <= 8'h18;
1578 : data_o <= 8'h18;
1579 : data_o <= 8'h18;
1580 : data_o <= 8'hff;
1581 : data_o <= 8'h18;
1582 : data_o <= 8'h18;
1583 : data_o <= 8'h18;
 
// ASCII 198
1584 : data_o <= 8'h18;
1585 : data_o <= 8'h18;
1586 : data_o <= 8'h1f;
1587 : data_o <= 8'h18;
1588 : data_o <= 8'h1f;
1589 : data_o <= 8'h18;
1590 : data_o <= 8'h18;
1591 : data_o <= 8'h18;
 
// ASCII 199
1592 : data_o <= 8'h36;
1593 : data_o <= 8'h36;
1594 : data_o <= 8'h36;
1595 : data_o <= 8'h36;
1596 : data_o <= 8'h37;
1597 : data_o <= 8'h36;
1598 : data_o <= 8'h36;
1599 : data_o <= 8'h36;
 
// ASCII 200
1600 : data_o <= 8'h36;
1601 : data_o <= 8'h36;
1602 : data_o <= 8'h37;
1603 : data_o <= 8'h30;
1604 : data_o <= 8'h3f;
1605 : data_o <= 8'h00;
1606 : data_o <= 8'h00;
1607 : data_o <= 8'h00;
 
// ASCII 201
1608 : data_o <= 8'h00;
1609 : data_o <= 8'h00;
1610 : data_o <= 8'h3f;
1611 : data_o <= 8'h30;
1612 : data_o <= 8'h37;
1613 : data_o <= 8'h36;
1614 : data_o <= 8'h36;
1615 : data_o <= 8'h36;
 
// ASCII 202
1616 : data_o <= 8'h36;
1617 : data_o <= 8'h36;
1618 : data_o <= 8'hf7;
1619 : data_o <= 8'h00;
1620 : data_o <= 8'hff;
1621 : data_o <= 8'h00;
1622 : data_o <= 8'h00;
1623 : data_o <= 8'h00;
 
// ASCII 203
1624 : data_o <= 8'h00;
1625 : data_o <= 8'h00;
1626 : data_o <= 8'hff;
1627 : data_o <= 8'h00;
1628 : data_o <= 8'hf7;
1629 : data_o <= 8'h36;
1630 : data_o <= 8'h36;
1631 : data_o <= 8'h36;
 
// ASCII 204
1632 : data_o <= 8'h36;
1633 : data_o <= 8'h36;
1634 : data_o <= 8'h37;
1635 : data_o <= 8'h30;
1636 : data_o <= 8'h37;
1637 : data_o <= 8'h36;
1638 : data_o <= 8'h36;
1639 : data_o <= 8'h36;
 
// ASCII 205
1640 : data_o <= 8'h00;
1641 : data_o <= 8'h00;
1642 : data_o <= 8'hff;
1643 : data_o <= 8'h00;
1644 : data_o <= 8'hff;
1645 : data_o <= 8'h00;
1646 : data_o <= 8'h00;
1647 : data_o <= 8'h00;
 
// ASCII 206
1648 : data_o <= 8'h36;
1649 : data_o <= 8'h36;
1650 : data_o <= 8'hf7;
1651 : data_o <= 8'h00;
1652 : data_o <= 8'hf7;
1653 : data_o <= 8'h36;
1654 : data_o <= 8'h36;
1655 : data_o <= 8'h36;
 
// ASCII 207
1656 : data_o <= 8'h18;
1657 : data_o <= 8'h18;
1658 : data_o <= 8'hff;
1659 : data_o <= 8'h00;
1660 : data_o <= 8'hff;
1661 : data_o <= 8'h00;
1662 : data_o <= 8'h00;
1663 : data_o <= 8'h00;
 
// ASCII 208
1664 : data_o <= 8'h36;
1665 : data_o <= 8'h36;
1666 : data_o <= 8'h36;
1667 : data_o <= 8'h36;
1668 : data_o <= 8'hff;
1669 : data_o <= 8'h00;
1670 : data_o <= 8'h00;
1671 : data_o <= 8'h00;
 
// ASCII 209
1672 : data_o <= 8'h00;
1673 : data_o <= 8'h00;
1674 : data_o <= 8'hff;
1675 : data_o <= 8'h00;
1676 : data_o <= 8'hff;
1677 : data_o <= 8'h18;
1678 : data_o <= 8'h18;
1679 : data_o <= 8'h18;
 
// ASCII 210
1680 : data_o <= 8'h00;
1681 : data_o <= 8'h00;
1682 : data_o <= 8'h00;
1683 : data_o <= 8'h00;
1684 : data_o <= 8'hff;
1685 : data_o <= 8'h36;
1686 : data_o <= 8'h36;
1687 : data_o <= 8'h36;
 
// ASCII 211
1688 : data_o <= 8'h36;
1689 : data_o <= 8'h36;
1690 : data_o <= 8'h36;
1691 : data_o <= 8'h36;
1692 : data_o <= 8'h3f;
1693 : data_o <= 8'h00;
1694 : data_o <= 8'h00;
1695 : data_o <= 8'h00;
 
// ASCII 212
1696 : data_o <= 8'h18;
1697 : data_o <= 8'h18;
1698 : data_o <= 8'h1f;
1699 : data_o <= 8'h18;
1700 : data_o <= 8'h1f;
1701 : data_o <= 8'h00;
1702 : data_o <= 8'h00;
1703 : data_o <= 8'h00;
 
// ASCII 213
1704 : data_o <= 8'h00;
1705 : data_o <= 8'h00;
1706 : data_o <= 8'h1f;
1707 : data_o <= 8'h18;
1708 : data_o <= 8'h1f;
1709 : data_o <= 8'h18;
1710 : data_o <= 8'h18;
1711 : data_o <= 8'h18;
 
// ASCII 214
1712 : data_o <= 8'h00;
1713 : data_o <= 8'h00;
1714 : data_o <= 8'h00;
1715 : data_o <= 8'h00;
1716 : data_o <= 8'h3f;
1717 : data_o <= 8'h36;
1718 : data_o <= 8'h36;
1719 : data_o <= 8'h36;
 
// ASCII 215
1720 : data_o <= 8'h36;
1721 : data_o <= 8'h36;
1722 : data_o <= 8'h36;
1723 : data_o <= 8'h36;
1724 : data_o <= 8'hff;
1725 : data_o <= 8'h36;
1726 : data_o <= 8'h36;
1727 : data_o <= 8'h36;
 
// ASCII 216
1728 : data_o <= 8'h18;
1729 : data_o <= 8'h18;
1730 : data_o <= 8'hff;
1731 : data_o <= 8'h18;
1732 : data_o <= 8'hff;
1733 : data_o <= 8'h18;
1734 : data_o <= 8'h18;
1735 : data_o <= 8'h18;
 
// ASCII 217
1736 : data_o <= 8'h18;
1737 : data_o <= 8'h18;
1738 : data_o <= 8'h18;
1739 : data_o <= 8'h18;
1740 : data_o <= 8'hf8;
1741 : data_o <= 8'h00;
1742 : data_o <= 8'h00;
1743 : data_o <= 8'h00;
 
// ASCII 218
1744 : data_o <= 8'h00;
1745 : data_o <= 8'h00;
1746 : data_o <= 8'h00;
1747 : data_o <= 8'h00;
1748 : data_o <= 8'h1f;
1749 : data_o <= 8'h18;
1750 : data_o <= 8'h18;
1751 : data_o <= 8'h18;
 
// ASCII 219
1752 : data_o <= 8'hff;
1753 : data_o <= 8'hff;
1754 : data_o <= 8'hff;
1755 : data_o <= 8'hff;
1756 : data_o <= 8'hff;
1757 : data_o <= 8'hff;
1758 : data_o <= 8'hff;
1759 : data_o <= 8'hff;
 
// ASCII 220
1760 : data_o <= 8'h00;
1761 : data_o <= 8'h00;
1762 : data_o <= 8'h00;
1763 : data_o <= 8'h00;
1764 : data_o <= 8'hff;
1765 : data_o <= 8'hff;
1766 : data_o <= 8'hff;
1767 : data_o <= 8'hff;
 
// ASCII 221
1768 : data_o <= 8'hf0;
1769 : data_o <= 8'hf0;
1770 : data_o <= 8'hf0;
1771 : data_o <= 8'hf0;
1772 : data_o <= 8'hf0;
1773 : data_o <= 8'hf0;
1774 : data_o <= 8'hf0;
1775 : data_o <= 8'hf0;
 
// ASCII 222
1776 : data_o <= 8'h0f;
1777 : data_o <= 8'h0f;
1778 : data_o <= 8'h0f;
1779 : data_o <= 8'h0f;
1780 : data_o <= 8'h0f;
1781 : data_o <= 8'h0f;
1782 : data_o <= 8'h0f;
1783 : data_o <= 8'h0f;
 
// ASCII 223
1784 : data_o <= 8'hff;
1785 : data_o <= 8'hff;
1786 : data_o <= 8'hff;
1787 : data_o <= 8'hff;
1788 : data_o <= 8'h00;
1789 : data_o <= 8'h00;
1790 : data_o <= 8'h00;
1791 : data_o <= 8'h00;
 
// ASCII 224
1792 : data_o <= 8'h00;
1793 : data_o <= 8'h00;
1794 : data_o <= 8'h76;
1795 : data_o <= 8'hdc;
1796 : data_o <= 8'hc8;
1797 : data_o <= 8'hdc;
1798 : data_o <= 8'h76;
1799 : data_o <= 8'h00;
 
// ASCII 225
1800 : data_o <= 8'h78;
1801 : data_o <= 8'hcc;
1802 : data_o <= 8'hcc;
1803 : data_o <= 8'hd8;
1804 : data_o <= 8'hcc;
1805 : data_o <= 8'hc6;
1806 : data_o <= 8'hcc;
1807 : data_o <= 8'h00;
 
// ASCII 226
1808 : data_o <= 8'hfe;
1809 : data_o <= 8'hc6;
1810 : data_o <= 8'hc0;
1811 : data_o <= 8'hc0;
1812 : data_o <= 8'hc0;
1813 : data_o <= 8'hc0;
1814 : data_o <= 8'hc0;
1815 : data_o <= 8'h00;
 
// ASCII 227
1816 : data_o <= 8'h00;
1817 : data_o <= 8'h00;
1818 : data_o <= 8'hfe;
1819 : data_o <= 8'h6c;
1820 : data_o <= 8'h6c;
1821 : data_o <= 8'h6c;
1822 : data_o <= 8'h6c;
1823 : data_o <= 8'h00;
 
// ASCII 228
1824 : data_o <= 8'hfe;
1825 : data_o <= 8'hc6;
1826 : data_o <= 8'h60;
1827 : data_o <= 8'h30;
1828 : data_o <= 8'h60;
1829 : data_o <= 8'hc6;
1830 : data_o <= 8'hfe;
1831 : data_o <= 8'h00;
 
// ASCII 229
1832 : data_o <= 8'h00;
1833 : data_o <= 8'h00;
1834 : data_o <= 8'h7e;
1835 : data_o <= 8'hd8;
1836 : data_o <= 8'hd8;
1837 : data_o <= 8'hd8;
1838 : data_o <= 8'h70;
1839 : data_o <= 8'h00;
 
// ASCII 230
1840 : data_o <= 8'h00;
1841 : data_o <= 8'h00;
1842 : data_o <= 8'h66;
1843 : data_o <= 8'h66;
1844 : data_o <= 8'h66;
1845 : data_o <= 8'h66;
1846 : data_o <= 8'h7c;
1847 : data_o <= 8'hc0;
 
// ASCII 231
1848 : data_o <= 8'h00;
1849 : data_o <= 8'h76;
1850 : data_o <= 8'hdc;
1851 : data_o <= 8'h18;
1852 : data_o <= 8'h18;
1853 : data_o <= 8'h18;
1854 : data_o <= 8'h18;
1855 : data_o <= 8'h00;
 
// ASCII 232
1856 : data_o <= 8'h7e;
1857 : data_o <= 8'h18;
1858 : data_o <= 8'h3c;
1859 : data_o <= 8'h66;
1860 : data_o <= 8'h66;
1861 : data_o <= 8'h3c;
1862 : data_o <= 8'h18;
1863 : data_o <= 8'h7e;
 
// ASCII 233
1864 : data_o <= 8'h38;
1865 : data_o <= 8'h6c;
1866 : data_o <= 8'hc6;
1867 : data_o <= 8'hfe;
1868 : data_o <= 8'hc6;
1869 : data_o <= 8'h6c;
1870 : data_o <= 8'h38;
1871 : data_o <= 8'h00;
 
// ASCII 234
1872 : data_o <= 8'h38;
1873 : data_o <= 8'h6c;
1874 : data_o <= 8'hc6;
1875 : data_o <= 8'hc6;
1876 : data_o <= 8'h6c;
1877 : data_o <= 8'h6c;
1878 : data_o <= 8'hee;
1879 : data_o <= 8'h00;
 
// ASCII 235
1880 : data_o <= 8'h0e;
1881 : data_o <= 8'h18;
1882 : data_o <= 8'h0c;
1883 : data_o <= 8'h3e;
1884 : data_o <= 8'h66;
1885 : data_o <= 8'h66;
1886 : data_o <= 8'h3c;
1887 : data_o <= 8'h00;
 
// ASCII 236
1888 : data_o <= 8'h00;
1889 : data_o <= 8'h00;
1890 : data_o <= 8'h7e;
1891 : data_o <= 8'hdb;
1892 : data_o <= 8'hdb;
1893 : data_o <= 8'h7e;
1894 : data_o <= 8'h00;
1895 : data_o <= 8'h00;
 
// ASCII 237
1896 : data_o <= 8'h06;
1897 : data_o <= 8'h0c;
1898 : data_o <= 8'h7e;
1899 : data_o <= 8'hdb;
1900 : data_o <= 8'hdb;
1901 : data_o <= 8'h7e;
1902 : data_o <= 8'h60;
1903 : data_o <= 8'hc0;
 
// ASCII 238
1904 : data_o <= 8'h1e;
1905 : data_o <= 8'h30;
1906 : data_o <= 8'h60;
1907 : data_o <= 8'h7e;
1908 : data_o <= 8'h60;
1909 : data_o <= 8'h30;
1910 : data_o <= 8'h1e;
1911 : data_o <= 8'h00;
 
// ASCII 239
1912 : data_o <= 8'h00;
1913 : data_o <= 8'h7c;
1914 : data_o <= 8'hc6;
1915 : data_o <= 8'hc6;
1916 : data_o <= 8'hc6;
1917 : data_o <= 8'hc6;
1918 : data_o <= 8'hc6;
1919 : data_o <= 8'h00;
 
// ASCII 240
1920 : data_o <= 8'h00;
1921 : data_o <= 8'hfe;
1922 : data_o <= 8'h00;
1923 : data_o <= 8'hfe;
1924 : data_o <= 8'h00;
1925 : data_o <= 8'hfe;
1926 : data_o <= 8'h00;
1927 : data_o <= 8'h00;
 
// ASCII 241
1928 : data_o <= 8'h18;
1929 : data_o <= 8'h18;
1930 : data_o <= 8'h7e;
1931 : data_o <= 8'h18;
1932 : data_o <= 8'h18;
1933 : data_o <= 8'h00;
1934 : data_o <= 8'h7e;
1935 : data_o <= 8'h00;
 
// ASCII 242
1936 : data_o <= 8'h30;
1937 : data_o <= 8'h18;
1938 : data_o <= 8'h0c;
1939 : data_o <= 8'h18;
1940 : data_o <= 8'h30;
1941 : data_o <= 8'h00;
1942 : data_o <= 8'h7e;
1943 : data_o <= 8'h00;
 
// ASCII 243
1944 : data_o <= 8'h0c;
1945 : data_o <= 8'h18;
1946 : data_o <= 8'h30;
1947 : data_o <= 8'h18;
1948 : data_o <= 8'h0c;
1949 : data_o <= 8'h00;
1950 : data_o <= 8'h7e;
1951 : data_o <= 8'h00;
 
// ASCII 244
1952 : data_o <= 8'h0e;
1953 : data_o <= 8'h1b;
1954 : data_o <= 8'h1b;
1955 : data_o <= 8'h18;
1956 : data_o <= 8'h18;
1957 : data_o <= 8'h18;
1958 : data_o <= 8'h18;
1959 : data_o <= 8'h18;
 
// ASCII 245
1960 : data_o <= 8'h18;
1961 : data_o <= 8'h18;
1962 : data_o <= 8'h18;
1963 : data_o <= 8'h18;
1964 : data_o <= 8'h18;
1965 : data_o <= 8'hd8;
1966 : data_o <= 8'hd8;
1967 : data_o <= 8'h70;
 
// ASCII 246
1968 : data_o <= 8'h00;
1969 : data_o <= 8'h18;
1970 : data_o <= 8'h00;
1971 : data_o <= 8'h7e;
1972 : data_o <= 8'h00;
1973 : data_o <= 8'h18;
1974 : data_o <= 8'h00;
1975 : data_o <= 8'h00;
 
// ASCII 247
1976 : data_o <= 8'h00;
1977 : data_o <= 8'h76;
1978 : data_o <= 8'hdc;
1979 : data_o <= 8'h00;
1980 : data_o <= 8'h76;
1981 : data_o <= 8'hdc;
1982 : data_o <= 8'h00;
1983 : data_o <= 8'h00;
 
// ASCII 248
1984 : data_o <= 8'h38;
1985 : data_o <= 8'h6c;
1986 : data_o <= 8'h6c;
1987 : data_o <= 8'h38;
1988 : data_o <= 8'h00;
1989 : data_o <= 8'h00;
1990 : data_o <= 8'h00;
1991 : data_o <= 8'h00;
 
// ASCII 249
1992 : data_o <= 8'h00;
1993 : data_o <= 8'h00;
1994 : data_o <= 8'h00;
1995 : data_o <= 8'h18;
1996 : data_o <= 8'h18;
1997 : data_o <= 8'h00;
1998 : data_o <= 8'h00;
1999 : data_o <= 8'h00;
 
// ASCII 250
2000 : data_o <= 8'h00;
2001 : data_o <= 8'h00;
2002 : data_o <= 8'h00;
2003 : data_o <= 8'h18;
2004 : data_o <= 8'h00;
2005 : data_o <= 8'h00;
2006 : data_o <= 8'h00;
2007 : data_o <= 8'h00;
 
// ASCII 251
2008 : data_o <= 8'h0f;
2009 : data_o <= 8'h0c;
2010 : data_o <= 8'h0c;
2011 : data_o <= 8'h0c;
2012 : data_o <= 8'hec;
2013 : data_o <= 8'h6c;
2014 : data_o <= 8'h3c;
2015 : data_o <= 8'h1c;
 
// ASCII 252
2016 : data_o <= 8'h6c;
2017 : data_o <= 8'h36;
2018 : data_o <= 8'h36;
2019 : data_o <= 8'h36;
2020 : data_o <= 8'h36;
2021 : data_o <= 8'h00;
2022 : data_o <= 8'h00;
2023 : data_o <= 8'h00;
 
// ASCII 253
2024 : data_o <= 8'h78;
2025 : data_o <= 8'h0c;
2026 : data_o <= 8'h18;
2027 : data_o <= 8'h30;
2028 : data_o <= 8'h7c;
2029 : data_o <= 8'h00;
2030 : data_o <= 8'h00;
2031 : data_o <= 8'h00;
 
// ASCII 254
2032 : data_o <= 8'h00;
2033 : data_o <= 8'h00;
2034 : data_o <= 8'h3c;
2035 : data_o <= 8'h3c;
2036 : data_o <= 8'h3c;
2037 : data_o <= 8'h3c;
2038 : data_o <= 8'h00;
2039 : data_o <= 8'h00;
 
// ASCII 255
2040 : data_o <= 8'h00;
2041 : data_o <= 8'h00;
2042 : data_o <= 8'h00;
2043 : data_o <= 8'h00;
2044 : data_o <= 8'h00;
2045 : data_o <= 8'h00;
2046 : data_o <= 8'h00;
2047 : data_o <= 8'h00;
 
endcase
end
end
endmodule
/wb_text_vga/video_ram.v
0,0 → 1,45
/*
* Text-only Video RAM
*
* Dual-port RAM containing the ASCII codes for chars to be displayed on screen.
* Text resolution is 64x32 or less (e.g. 40x30).
* Address bits [10:5] specify the column and bits [4:0] the row.
*/
 
// synthesis attribute ram_style of video_ram is block;
module video_ram (
 
// System
input sys_clock_i,
 
// Port 1 (read/write)
input write1_i,
input[10:0] address1_i,
input [7:0] data1_i,
output reg[7:0] data1_o,
 
// Port 2 (read-only)
input[10:0] address2_i,
output reg[7:0] data2_o
 
);
 
// Memory array
reg[7:0] VRAM[2047:0];
 
// Initialize memory content
integer i;
initial begin
for(i=0; i<2048; i=i+1)
VRAM[i] <= 8'h00;
end
 
always @(posedge sys_clock_i) begin
if (write1_i) begin
VRAM[address1_i] <= data1_i;
end
data1_o <= VRAM[address1_i];
data2_o <= VRAM[address2_i];
end
 
endmodule
/wb_text_vga/wb_text_vga.v
0,0 → 1,207
/*
* Text-only VGA Controller with Wishbone interface
*
* Includes a small Video RAM containing the chars to be shown on screen.
* Handles the VGA display in common VGA resolution (640x480 @ 60 Hz).
* Fonts are designed with 8x8 resolution and then spread over 16x16 pixels
* in order to save memory, thus obtaining 40 columns and 30 rows.
* It should use only 2 Block RAMs on Xilinx devices (2KB+2KB), one ROM to
* store the bitmap for each of the 256 chars of the ASCII table and a Video
* RAM to store the ASCII code for each of the 1200 chars on screen.
* How it works: just write a byte using the Wishbone slave interface and it
* will show on screen in black & white.
*/
 
`define HSYNC_COUNTER_MAX 1600
`define HSYNC_PULSE_START 1312
`define HSYNC_PULSE_STOP 1504
 
`define VSYNC_COUNTER_MAX 521
`define VSYNC_PULSE_START 490
`define VSYNC_PULSE_STOP 492
 
module wb_text_vga (
 
// System
input sys_clock_i,
input sys_reset_i,
 
// Wishbone slave interface
input wb_cyc_i,
input wb_stb_i,
input wb_we_i,
input[3:0] wb_sel_i,
input[31:0] wb_adr_i,
input[31:0] wb_dat_i,
output wb_ack_o,
output[31:0] wb_dat_o,
 
// VGA Port
output vga_rgb_r_o,
output vga_rgb_g_o,
output vga_rgb_b_o,
output reg vga_hsync_o,
output reg vga_vsync_o
 
);
 
/*
* Registers
*/
 
// Current position of the cursor
reg[5:0] text_col;
reg[4:0] text_row;
 
// Horizontal and vertical counters
reg[10:0] hcounter;
reg[9:0] vcounter;
 
/*
* Wires
*/
 
// Coordinates of the pixel being drawn
wire[9:0] pixel_x;
wire[8:0] pixel_y;
 
// Video RAM port 1 wires (read/write)
wire ram_write1;
wire[10:0] ram_address1;
wire[7:0] ram_wdata1;
wire[7:0] ram_rdata1;
 
// Video RAM port 2 wires (read-only)
wire[10:0] ram_address2;
wire[7:0] ram_rdata2;
 
// Fontmap ROM wires
wire rom_enable;
wire[10:0] rom_address;
wire[7:0] rom_data;
 
/*
* Module instances
*/
 
// Video RAM instance
video_ram video_ram_0 (
 
// System
.sys_clock_i(sys_clock_i),
 
// Port 1 (read/write)
.write1_i(ram_write1),
.address1_i(ram_address1),
.data1_i(ram_wdata1),
.data1_o(ram_rdata1),
 
// Port 2 (read-only)
.address2_i(ram_address2),
.data2_o(ram_rdata2)
);
 
// Fontmap ROM instance
fontmap_rom fontmap_rom_0 (
.sys_clock_i(sys_clock_i),
.read_i(rom_enable),
.address_i(rom_address),
.data_o(rom_data)
);
 
/*
* Combinational logic
*/
 
// Wishbone request is always served immediately
assign wb_ack_o = (wb_cyc_i && wb_stb_i);
 
// No Wishbone read allowed
assign wb_dat_o = 32'h00000000;
 
// Wishbone writes go directly to Video RAM
assign ram_write1 = (wb_cyc_i && wb_stb_i && wb_we_i);
assign ram_wdata1 = wb_dat_i[7:0];
 
// The address of the write to Video RAM is the coordinate of the next char
assign ram_address1 = { text_row , text_col };
 
// The second port of the Video RAM is used to retrieve the ASCII code of the char to be shown on screen
assign ram_address2 = { vcounter[9:5] , hcounter[10:5] };
 
// Read continuously from ROM
assign rom_enable = 1;
 
// The address of the read from Fontmap ROM is the ASCII code concatenated with the number of line in the char
assign rom_address = { ram_rdata2 , vcounter[4:2] };
 
// Now draw the pixel in black & white
assign vga_rgb_r_o = rom_data[8-hcounter[4:2]];
assign vga_rgb_g_o = rom_data[8-hcounter[4:2]];
assign vga_rgb_b_o = rom_data[8-hcounter[4:2]];
 
/*
* Sequential logic
*/
 
always @(posedge sys_clock_i) begin
 
if(sys_reset_i) begin
 
// Reset registers
text_row <= 0;
text_col <= 0;
hcounter <= 0;
vcounter <= 0;
 
// Clear outputs
vga_hsync_o <= 1;
vga_vsync_o <= 1;
 
end else begin
 
// Update counters and handle upper bounds
if (hcounter == (`HSYNC_COUNTER_MAX-1) ) begin
hcounter <= 0;
if (vcounter == (`VSYNC_COUNTER_MAX-1) ) begin
vcounter <= 0;
end else begin
vcounter <= vcounter + 1;
end
end else begin
hcounter <= hcounter + 1;
end
 
// Drive sync outputs
if(hcounter>=`HSYNC_PULSE_START && hcounter<`HSYNC_PULSE_STOP)
vga_hsync_o <= 0;
else
vga_hsync_o <= 1;
if(vcounter>=`VSYNC_PULSE_START && vcounter<`VSYNC_PULSE_STOP)
vga_vsync_o <= 0;
else
vga_vsync_o <= 1;
 
// Handle the writing from the Wishbone bus
if(wb_cyc_i && wb_stb_i && wb_we_i) begin
 
// Handle cursor position including New Line Feed
if(text_col==39 || wb_dat_i[7:0]==8'h0A) begin
text_col <= 0;
if(text_row==29) begin
text_row <= 0;
end else begin
text_row <= text_row + 1;
end
end else begin
text_col <= text_col + 1;
end
 
// During simulation print char to stdout
$display("WB-TEXT: Print char '%c'", wb_dat_i[7:0]);
 
end
end
end
 
endmodule
/wb_ps2_keyboard/ps2_io_ctrl.v
0,0 → 1,109
//////////////////////////////////////////////////////////////////////
//// ////
//// ps2_io_ctrl.v ////
//// ////
//// This file is part of the "ps2" project ////
//// http://www.opencores.org/cores/ps2/ ////
//// ////
//// Author(s): ////
//// - mihad@opencores.org ////
//// - Miha Dolenc ////
//// ////
//// All additional information is avaliable in the README.txt ////
//// file. ////
//// ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2000 Miha Dolenc, mihad@opencores.org ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer. ////
//// ////
//// This source file is free software; you can redistribute it ////
//// and/or modify it under the terms of the GNU Lesser General ////
//// Public License as published by the Free Software Foundation; ////
//// either version 2.1 of the License, or (at your option) any ////
//// later version. ////
//// ////
//// This source is distributed in the hope that it will be ////
//// useful, but WITHOUT ANY WARRANTY; without even the implied ////
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
//// PURPOSE. See the GNU Lesser General Public License for more ////
//// details. ////
//// ////
//// You should have received a copy of the GNU Lesser General ////
//// Public License along with this source; if not, download it ////
//// from http://www.opencores.org/lgpl.shtml ////
//// ////
//////////////////////////////////////////////////////////////////////
//
// CVS Revision History
//
// $Log: not supported by cvs2svn $
// Revision 1.2 2002/04/09 13:21:15 mihad
// Added mouse interface and everything for its handling, cleaned up some unused code
//
// Revision 1.1.1.1 2002/02/18 16:16:56 mihad
// Initial project import - working
//
//
 
// synopsys translate_off
`include "timescale.v"
// synopsys translate_on
 
module ps2_io_ctrl
(
clk_i,
rst_i,
ps2_ctrl_clk_en_i_,
ps2_ctrl_data_en_i_,
ps2_clk_pad_i,
ps2_clk_pad_oe_o,
ps2_data_pad_oe_o,
inhibit_if_i,
ps2_ctrl_clk_o
);
 
input clk_i,
rst_i,
ps2_ctrl_clk_en_i_,
ps2_ctrl_data_en_i_,
ps2_clk_pad_i,
inhibit_if_i ;
 
output ps2_clk_pad_oe_o,
ps2_data_pad_oe_o,
ps2_ctrl_clk_o ;
 
reg ps2_clk_pad_oe_o,
ps2_data_pad_oe_o ;
 
always@(posedge clk_i or posedge rst_i)
begin
if ( rst_i )
begin
ps2_clk_pad_oe_o <= #1 1'b0 ;
ps2_data_pad_oe_o <= #1 1'b0 ;
end
else
begin
ps2_clk_pad_oe_o <= #1 !ps2_ctrl_clk_en_i_ || inhibit_if_i ;
ps2_data_pad_oe_o <= #1 !ps2_ctrl_data_en_i_ ;
end
end
 
reg inhibit_if_previous ;
always@(posedge clk_i or posedge rst_i)
begin
if ( rst_i )
inhibit_if_previous <= #1 1'b1 ;
else
inhibit_if_previous <= #1 inhibit_if_i ;
end
 
assign ps2_ctrl_clk_o = ps2_clk_pad_i || ps2_clk_pad_oe_o && inhibit_if_previous ;
endmodule // ps2_io_ctrl
/wb_ps2_keyboard/ps2_defines.v
0,0 → 1,81
//////////////////////////////////////////////////////////////////////
//// ////
//// ps2_defines.v ////
//// ////
//// This file is part of the "ps2" project ////
//// http://www.opencores.org/cores/ps2/ ////
//// ////
//// Author(s): ////
//// - mihad@opencores.org ////
//// - Miha Dolenc ////
//// ////
//// All additional information is avaliable in the README.txt ////
//// file. ////
//// ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2000 Miha Dolenc, mihad@opencores.org ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer. ////
//// ////
//// This source file is free software; you can redistribute it ////
//// and/or modify it under the terms of the GNU Lesser General ////
//// Public License as published by the Free Software Foundation; ////
//// either version 2.1 of the License, or (at your option) any ////
//// later version. ////
//// ////
//// This source is distributed in the hope that it will be ////
//// useful, but WITHOUT ANY WARRANTY; without even the implied ////
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
//// PURPOSE. See the GNU Lesser General Public License for more ////
//// details. ////
//// ////
//// You should have received a copy of the GNU Lesser General ////
//// Public License along with this source; if not, download it ////
//// from http://www.opencores.org/lgpl.shtml ////
//// ////
//////////////////////////////////////////////////////////////////////
//
// CVS Revision History
//
// $Log: not supported by cvs2svn $
// Revision 1.5 2003/10/03 10:16:52 primozs
// support for configurable devider added
//
// Revision 1.4 2003/07/01 12:34:03 mihad
// Added an option to use constant values instead of RAM
// in the translation table.
//
// Revision 1.3 2002/04/09 13:21:15 mihad
// Added mouse interface and everything for its handling, cleaned up some unused code
//
// Revision 1.2 2002/02/18 16:33:08 mihad
// Changed defines for simulation to work without xilinx primitives
//
// Revision 1.1.1.1 2002/02/18 16:16:56 mihad
// Initial project import - working
//
//
 
//`define PS2_RAMB4
`define PS2_CONSTANTS_ROM
 
`define PS2_TRANSLATION_TABLE_31_0 256'h5b03111e1f2c71665a02101d702a386559290f3e40424464583c3b3d3f4143ff
`define PS2_TRANSLATION_TABLE_63_32 256'h5f0908162432726a5e071522233031695d061314212f39685c040512202d2e67
`define PS2_TRANSLATION_TABLE_95_64 256'h76632b751b1c363a6e620d1a7428736d610c19272635346c600a0b181725336b
`define PS2_TRANSLATION_TABLE_127_96 256'h544649374a514e574501484d4c5053526f7f7e474b7d4f7c7b0e7a7978775655
`define PS2_TRANSLATION_TABLE_159_128 256'h9f9e9d9c9b9a999897969594939291908f8e8d8c8b8a89888786855441828180
`define PS2_TRANSLATION_TABLE_191_160 256'hbfbebdbcbbbab9b8b7b6b5b4b3b2b1b0afaeadacabaaa9a8a7a6a5a4a3a2a1a0
`define PS2_TRANSLATION_TABLE_223_192 256'hdfdedddcdbdad9d8d7d6d5d4d3d2d1d0cfcecdcccbcac9c8c7c6c5c4c3c2c1c0
`define PS2_TRANSLATION_TABLE_255_224 256'hfffefdfcfbfaf9f8f7f6f5f4f3f2f1f0efeeedecebeae9e8e7e6e5e4e3e2e1e0
 
`define PS2_TIMER_60USEC_VALUE_PP 12 // Number of sys_clks for 60usec.
`define PS2_TIMER_60USEC_BITS_PP 4 // Number of bits needed for timer
`define PS2_TIMER_5USEC_VALUE_PP 500 // Number of sys_clks for debounce
`define PS2_TIMER_5USEC_BITS_PP 16 // Number of bits needed for timer
 
//`define PS2_AUX
/wb_ps2_keyboard/ps2_keyboard.v
0,0 → 1,568
//-------------------------------------------------------------------------------------
//
// Author: John Clayton
// Date : April 30, 2001
// Update: 4/30/01 copied this file from lcd_2.v (pared down).
// Update: 5/24/01 changed the first module from "ps2_keyboard_receiver"
// to "ps2_keyboard_interface"
// Update: 5/29/01 Added input synchronizing flip-flops. Changed state
// encoding (m1) for good operation after part config.
// Update: 5/31/01 Added low drive strength and slow transitions to ps2_clk
// and ps2_data in the constraints file. Added the signal
// "tx_shifting_done" as distinguished from "rx_shifting_done."
// Debugged the transmitter portion in the lab.
// Update: 6/01/01 Added horizontal tab to the ascii output.
// Update: 6/01/01 Added parameter TRAP_SHIFT_KEYS.
// Update: 6/05/01 Debugged the "debounce" timer functionality.
// Used 60usec timer as a "watchdog" timeout during
// receive from the keyboard. This means that a keyboard
// can now be "hot plugged" into the interface, without
// messing up the bit_count, since the bit_count is reset
// to zero during periods of inactivity anyway. This was
// difficult to debug. I ended up using the logic analyzer,
// and had to scratch my head quite a bit.
// Update: 6/06/01 Removed extra comments before the input synchronizing
// flip-flops. Used the correct parameter to size the
// 5usec_timer_count. Changed the name of this file from
// ps2.v to ps2_keyboard.v
// Update: 6/06/01 Removed "&& q[7:0]" in output_strobe logic. Removed extra
// commented out "else" condition in the shift register and
// bit counter.
// Update: 6/07/01 Changed default values for 60usec timer parameters so that
// they correspond to 60usec for a 49.152MHz clock.
//
//
//
//
//
// Description
//-------------------------------------------------------------------------------------
// This is a state-machine driven serial-to-parallel and parallel-to-serial
// interface to the ps2 style keyboard interface. The details of the operation
// of the keyboard interface were obtained from the following website:
//
// http://www.beyondlogic.org/keyboard/keybrd.htm
//
// Some aspects of the keyboard interface are not implemented (e.g, parity
// checking for the receive side, and recognition of the various commands
// which the keyboard sends out, such as "power on selt test passed," "Error"
// and "Resend.") However, if the user wishes to recognize these reply
// messages, the scan code output can always be used to extend functionality
// as desired.
//
// Note that the "Extended" (0xE0) and "Released" (0xF0) codes are recognized.
// The rx interface provides separate indicator flags for these two conditions
// with every valid character scan code which it provides. The shift keys are
// also trapped by the interface, in order to provide correct uppercase ASCII
// characters at the ascii output, although the scan codes for the shift keys
// are still provided at the scan code output. So, the left/right ALT keys
// can be differentiated by the presence of the rx_entended signal, while the
// left/right shift keys are differentiable by the different scan codes
// received.
//
// The interface to the ps2 keyboard uses ps2_clk clock rates of
// 30-40 kHz, dependent upon the keyboard itself. The rate at which the state
// machine runs should be at least twice the rate of the ps2_clk, so that the
// states can accurately follow the clock signal itself. Four times
// oversampling is better. Say 200kHz at least. The upper limit for clocking
// the state machine will undoubtedly be determined by delays in the logic
// which decodes the scan codes into ASCII equivalents. The maximum speed
// will be most likely many megahertz, depending upon target technology.
// In order to run the state machine extremely fast, synchronizing flip-flops
// have been added to the ps2_clk and ps2_data inputs of the state machine.
// This avoids poor performance related to slow transitions of the inputs.
//
// Because this is a bi-directional interface, while reading from the keyboard
// the ps2_clk and ps2_data lines are used as inputs. While writing to the
// keyboard, however (which may be done at any time. If writing interrupts a
// read from the keyboard, the keyboard will buffer up its data, and send
// it later) both the ps2_clk and ps2_data lines are occasionally pulled low,
// and pullup resistors are used to bring the lines high again, by setting
// the drivers to high impedance state.
//
// The tx interface, for writing to the keyboard, does not provide any special
// pre-processing. It simply transmits the 8-bit command value to the
// keyboard.
//
// Pullups MUST BE USED on the ps2_clk and ps2_data lines for this design,
// whether they be internal to an FPGA I/O pad, or externally placed.
// If internal pullups are used, they may be fairly weak, causing bounces
// due to crosstalk, etc. There is a "debounce timer" implemented in order
// to eliminate erroneous state transitions which would occur based on bounce.
//
// Parameters are provided in order to configure and appropriately size the
// counter of a 60 microsecond timer used in the transmitter, depending on
// the clock frequency used. The 60 microsecond period is guaranteed to be
// more than one period of the ps2_clk_s signal.
//
// Also, a smaller 5 microsecond timer has been included for "debounce".
// This is used because, with internal pullups on the ps2_clk and ps2_data
// lines, there is some bouncing around which occurs
//
// A parameter TRAP_SHIFT_KEYS allows the user to eliminate shift keypresses
// from producing scan codes (along with their "undefined" ASCII equivalents)
// at the output of the interface. If TRAP_SHIFT_KEYS is non-zero, the shift
// key status will only be reported by rx_shift_key_on. No ascii or scan
// codes will be reported for the shift keys. This is useful for those who
// wish to use the ASCII data stream, and who don't want to have to "filter
// out" the shift key codes.
//
//-------------------------------------------------------------------------------------
 
 
// synopsys translate_off
`include "timescale.v"
// synopsys translate_on
`define TOTAL_BITS 11
`define RELEASE_CODE 16'hF0
 
module ps2_keyboard (
clk,
reset,
ps2_clk_en_o_,
ps2_data_en_o_,
ps2_clk_i,
ps2_data_i,
rx_released,
rx_scan_code,
rx_data_ready, // rx_read_o
rx_read, // rx_read_ack_i
tx_data,
tx_write,
tx_write_ack_o,
tx_error_no_keyboard_ack,
translate,
devide_reg_i
);
 
// Parameters
 
 
// The timer value can be up to (2^bits) inclusive.
parameter TIMER_60USEC_VALUE_PP = 2950; // Number of sys_clks for 60usec.
parameter TIMER_60USEC_BITS_PP = 12; // Number of bits needed for timer
parameter TIMER_5USEC_VALUE_PP = 186; // Number of sys_clks for debounce
parameter TIMER_5USEC_BITS_PP = 8; // Number of bits needed for timer
 
// State encodings, provided as parameters
// for flexibility to the one instantiating the module.
// In general, the default values need not be changed.
 
// State "m1_rx_clk_l" has been chosen on purpose. Since the input
// synchronizing flip-flops initially contain zero, it takes one clk
// for them to update to reflect the actual (idle = high) status of
// the I/O lines from the keyboard. Therefore, choosing 0 for m1_rx_clk_l
// allows the state machine to transition to m1_rx_clk_h when the true
// values of the input signals become present at the outputs of the
// synchronizing flip-flops. This initial transition is harmless, and it
// eliminates the need for a "reset" pulse before the interface can operate.
 
parameter m1_rx_clk_h = 1;
parameter m1_rx_clk_l = 0;
parameter m1_rx_falling_edge_marker = 13;
parameter m1_rx_rising_edge_marker = 14;
parameter m1_tx_force_clk_l = 3;
parameter m1_tx_first_wait_clk_h = 10;
parameter m1_tx_first_wait_clk_l = 11;
parameter m1_tx_reset_timer = 12;
parameter m1_tx_wait_clk_h = 2;
parameter m1_tx_clk_h = 4;
parameter m1_tx_clk_l = 5;
parameter m1_tx_wait_keyboard_ack = 6;
parameter m1_tx_done_recovery = 7;
parameter m1_tx_error_no_keyboard_ack = 8;
parameter m1_tx_rising_edge_marker = 9;
parameter m2_rx_data_ready = 1;
parameter m2_rx_data_ready_ack = 0;
 
 
// I/O declarations
input clk;
input reset;
output ps2_clk_en_o_ ;
output ps2_data_en_o_ ;
input ps2_clk_i ;
input ps2_data_i ;
output rx_released;
output [7:0] rx_scan_code;
output rx_data_ready;
input rx_read;
input [7:0] tx_data;
input tx_write;
output tx_write_ack_o;
output tx_error_no_keyboard_ack;
input translate ;
 
input [15:0] devide_reg_i;
 
reg rx_released;
reg [7:0] rx_scan_code;
reg rx_data_ready;
reg tx_error_no_keyboard_ack;
 
// Internal signal declarations
wire timer_60usec_done;
wire timer_5usec_done;
wire released;
 
// NOTE: These two signals used to be one. They
// were split into two signals because of
// shift key trapping. With shift key
// trapping, no event is generated externally,
// but the "hold" data must still be cleared
// anyway regardless, in preparation for the
// next scan codes.
wire rx_output_event; // Used only to clear: hold_released, hold_extended
wire rx_output_strobe; // Used to produce the actual output.
 
wire tx_parity_bit;
wire rx_shifting_done;
wire tx_shifting_done;
 
reg [`TOTAL_BITS-1:0] q;
reg [3:0] m1_state;
reg [3:0] m1_next_state;
reg m2_state;
reg m2_next_state;
reg [3:0] bit_count;
reg enable_timer_60usec;
reg enable_timer_5usec;
reg [TIMER_60USEC_BITS_PP-1:0] timer_60usec_count;
reg [TIMER_5USEC_BITS_PP-1:0] timer_5usec_count;
reg hold_released; // Holds prior value, cleared at rx_output_strobe
reg ps2_clk_s; // Synchronous version of this input
reg ps2_data_s; // Synchronous version of this input
reg ps2_clk_hi_z; // Without keyboard, high Z equals 1 due to pullups.
reg ps2_data_hi_z; // Without keyboard, high Z equals 1 due to pullups.
reg ps2_clk_ms;
reg ps2_data_ms;
 
 
reg [15:0] timer_5usec;
reg timer_done;
 
 
 
//--------------------------------------------------------------------------
// Module code
 
assign ps2_clk_en_o_ = ps2_clk_hi_z ;
assign ps2_data_en_o_ = ps2_data_hi_z ;
 
// Input "synchronizing" logic -- synchronizes the inputs to the state
// machine clock, thus avoiding errors related to
// spurious state machine transitions.
always @(posedge clk)
begin
ps2_clk_ms <= #1 ps2_clk_i;
ps2_data_ms <= #1 ps2_data_i;
 
ps2_clk_s <= #1 ps2_clk_ms;
ps2_data_s <= #1 ps2_data_ms;
 
end
 
// State register
always @(posedge clk or posedge reset)
begin : m1_state_register
if (reset) m1_state <= #1 m1_rx_clk_h;
else m1_state <= #1 m1_next_state;
end
 
// State transition logic
always @(m1_state
or q
or tx_shifting_done
or tx_write
or ps2_clk_s
or ps2_data_s
or timer_60usec_done
or timer_5usec_done
)
begin : m1_state_logic
 
// Output signals default to this value, unless changed in a state condition.
ps2_clk_hi_z <= #1 1;
ps2_data_hi_z <= #1 1;
tx_error_no_keyboard_ack <= #1 1'b0;
enable_timer_60usec <= #1 0;
enable_timer_5usec <= #1 0;
 
case (m1_state)
 
m1_rx_clk_h :
begin
enable_timer_60usec <= #1 1;
if (tx_write) m1_next_state <= #1 m1_tx_reset_timer;
else if (~ps2_clk_s) m1_next_state <= #1 m1_rx_falling_edge_marker;
else m1_next_state <= #1 m1_rx_clk_h;
end
 
m1_rx_falling_edge_marker :
begin
enable_timer_60usec <= #1 0;
m1_next_state <= #1 m1_rx_clk_l;
end
 
m1_rx_rising_edge_marker :
begin
enable_timer_60usec <= #1 0;
m1_next_state <= #1 m1_rx_clk_h;
end
 
 
m1_rx_clk_l :
begin
enable_timer_60usec <= #1 1;
if (tx_write) m1_next_state <= #1 m1_tx_reset_timer;
else if (ps2_clk_s) m1_next_state <= #1 m1_rx_rising_edge_marker;
else m1_next_state <= #1 m1_rx_clk_l;
end
 
m1_tx_reset_timer:
begin
enable_timer_60usec <= #1 0;
m1_next_state <= #1 m1_tx_force_clk_l;
end
 
m1_tx_force_clk_l :
begin
enable_timer_60usec <= #1 1;
ps2_clk_hi_z <= #1 0; // Force the ps2_clk line low.
if (timer_60usec_done) m1_next_state <= #1 m1_tx_first_wait_clk_h;
else m1_next_state <= #1 m1_tx_force_clk_l;
end
 
m1_tx_first_wait_clk_h :
begin
enable_timer_5usec <= #1 1;
ps2_data_hi_z <= #1 0; // Start bit.
if (~ps2_clk_s && timer_5usec_done)
m1_next_state <= #1 m1_tx_clk_l;
else
m1_next_state <= #1 m1_tx_first_wait_clk_h;
end
 
// This state must be included because the device might possibly
// delay for up to 10 milliseconds before beginning its clock pulses.
// During that waiting time, we cannot drive the data (q[0]) because it
// is possibly 1, which would cause the keyboard to abort its receive
// and the expected clocks would then never be generated.
m1_tx_first_wait_clk_l :
begin
ps2_data_hi_z <= #1 0;
if (~ps2_clk_s) m1_next_state <= #1 m1_tx_clk_l;
else m1_next_state <= #1 m1_tx_first_wait_clk_l;
end
 
m1_tx_wait_clk_h :
begin
enable_timer_5usec <= #1 1;
ps2_data_hi_z <= #1 q[0];
if (ps2_clk_s && timer_5usec_done)
m1_next_state <= #1 m1_tx_rising_edge_marker;
else
m1_next_state <= #1 m1_tx_wait_clk_h;
end
 
m1_tx_rising_edge_marker :
begin
ps2_data_hi_z <= #1 q[0];
m1_next_state <= #1 m1_tx_clk_h;
end
 
m1_tx_clk_h :
begin
ps2_data_hi_z <= #1 q[0];
if (tx_shifting_done) m1_next_state <= #1 m1_tx_wait_keyboard_ack;
else if (~ps2_clk_s) m1_next_state <= #1 m1_tx_clk_l;
else m1_next_state <= #1 m1_tx_clk_h;
end
 
m1_tx_clk_l :
begin
ps2_data_hi_z <= #1 q[0];
if (ps2_clk_s) m1_next_state <= #1 m1_tx_wait_clk_h;
else m1_next_state <= #1 m1_tx_clk_l;
end
 
m1_tx_wait_keyboard_ack :
begin
if (~ps2_clk_s && ps2_data_s)
m1_next_state <= #1 m1_tx_error_no_keyboard_ack;
else if (~ps2_clk_s && ~ps2_data_s)
m1_next_state <= #1 m1_tx_done_recovery;
else m1_next_state <= #1 m1_tx_wait_keyboard_ack;
end
 
m1_tx_done_recovery :
begin
if (ps2_clk_s && ps2_data_s) m1_next_state <= #1 m1_rx_clk_h;
else m1_next_state <= #1 m1_tx_done_recovery;
end
 
m1_tx_error_no_keyboard_ack :
begin
tx_error_no_keyboard_ack <= #1 1;
if (ps2_clk_s && ps2_data_s) m1_next_state <= #1 m1_rx_clk_h;
else m1_next_state <= #1 m1_tx_error_no_keyboard_ack;
end
 
default : m1_next_state <= #1 m1_rx_clk_h;
endcase
end
 
// State register
always @(posedge clk or posedge reset)
begin : m2_state_register
if (reset) m2_state <= #1 m2_rx_data_ready_ack;
else m2_state <= #1 m2_next_state;
end
 
// State transition logic
always @(m2_state or rx_output_strobe or rx_read)
begin : m2_state_logic
case (m2_state)
m2_rx_data_ready_ack:
begin
rx_data_ready <= #1 1'b0;
if (rx_output_strobe) m2_next_state <= #1 m2_rx_data_ready;
else m2_next_state <= #1 m2_rx_data_ready_ack;
end
m2_rx_data_ready:
begin
rx_data_ready <= #1 1'b1;
if (rx_read) m2_next_state <= #1 m2_rx_data_ready_ack;
else m2_next_state <= #1 m2_rx_data_ready;
end
default : m2_next_state <= #1 m2_rx_data_ready_ack;
endcase
end
 
// This is the bit counter
always @(posedge clk or posedge reset)
begin
if ( reset) bit_count <= #1 0;
else if ( rx_shifting_done || (m1_state == m1_tx_wait_keyboard_ack) // After tx is done.
) bit_count <= #1 0; // normal reset
else if (timer_60usec_done
&& (m1_state == m1_rx_clk_h)
&& (ps2_clk_s)
) bit_count <= #1 0; // rx watchdog timer reset
else if ( (m1_state == m1_rx_falling_edge_marker) // increment for rx
||(m1_state == m1_tx_rising_edge_marker) // increment for tx
)
bit_count <= #1 bit_count + 1;
end
// This signal is high for one clock at the end of the timer count.
assign rx_shifting_done = (bit_count == `TOTAL_BITS);
assign tx_shifting_done = (bit_count == `TOTAL_BITS-1);
 
// This is the signal which enables loading of the shift register.
// It also indicates "ack" to the device writing to the transmitter.
assign tx_write_ack_o = ( (tx_write && (m1_state == m1_rx_clk_h))
||(tx_write && (m1_state == m1_rx_clk_l))
);
 
// This is the ODD parity bit for the transmitted word.
assign tx_parity_bit = ~^tx_data;
 
// This is the shift register
always @(posedge clk or posedge reset)
begin
if (reset) q <= #1 0;
else if (tx_write_ack_o) q <= #1 {1'b1,tx_parity_bit,tx_data,1'b0};
else if ( (m1_state == m1_rx_falling_edge_marker)
||(m1_state == m1_tx_rising_edge_marker) )
q <= #1 {ps2_data_s,q[`TOTAL_BITS-1:1]};
end
 
// This is the 60usec timer counter
always @(posedge clk)
begin
if (~enable_timer_60usec) timer_60usec_count <= #1 0;
else if ( timer_done && !timer_60usec_done)
timer_60usec_count<= #1 timer_60usec_count +1;
end
assign timer_60usec_done = (timer_60usec_count == (TIMER_60USEC_VALUE_PP ));
 
 
 
always @(posedge clk or posedge reset)
if (reset) timer_5usec <= #1 1;
else if (!enable_timer_60usec) timer_5usec <= #1 1;
else if (timer_5usec == devide_reg_i)
begin
timer_5usec <= #1 1;
timer_done <= #1 1;
end
else
begin
timer_5usec<= #1 timer_5usec +1;
timer_done <= #1 0;
end
 
// This is the 5usec timer counter
always @(posedge clk)
begin
if (~enable_timer_5usec) timer_5usec_count <= #1 0;
else if (~timer_5usec_done) timer_5usec_count <= #1 timer_5usec_count + 1;
end
assign timer_5usec_done = (timer_5usec_count == devide_reg_i -1);
 
 
// Create the signals which indicate special scan codes received.
// These are the "unlatched versions."
assign released = (q[8:1] == `RELEASE_CODE) && rx_shifting_done && translate ;
 
// Store the special scan code status bits
// Not the final output, but an intermediate storage place,
// until the entire set of output data can be assembled.
always @(posedge clk or posedge reset)
begin
if (reset) hold_released <= #1 0;
else if (rx_output_event)
begin
hold_released <= #1 0;
end
else
begin
if (rx_shifting_done && released) hold_released <= #1 1;
end
end
 
// Output the special scan code flags, the scan code and the ascii
always @(posedge clk or posedge reset)
begin
if (reset)
begin
rx_released <= #1 0;
rx_scan_code <= #1 0;
end
else if (rx_output_strobe)
begin
rx_released <= #1 hold_released;
rx_scan_code <= #1 q[8:1];
end
end
 
// Store the final rx output data only when all extend and release codes
// are received and the next (actual key) scan code is also ready.
// (the presence of rx_extended or rx_released refers to the
// the current latest scan code received, not the previously latched flags.)
assign rx_output_event = (rx_shifting_done
&& ~released
);
 
assign rx_output_strobe = (rx_shifting_done
&& ~released
);
 
endmodule
 
//`undefine TOTAL_BITS
//`undefine EXTEND_CODE
//`undefine RELEASE_CODE
//`undefine LEFT_SHIFT
//`undefine RIGHT_SHIFT
 
/wb_ps2_keyboard/ps2_top.v
0,0 → 1,308
//////////////////////////////////////////////////////////////////////
//// ////
//// ps2_top.v ////
//// ////
//// This file is part of the "ps2" project ////
//// http://www.opencores.org/cores/ps2/ ////
//// ////
//// Author(s): ////
//// - mihad@opencores.org ////
//// - Miha Dolenc ////
//// ////
//// All additional information is avaliable in the README.txt ////
//// file. ////
//// ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2000 Miha Dolenc, mihad@opencores.org ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer. ////
//// ////
//// This source file is free software; you can redistribute it ////
//// and/or modify it under the terms of the GNU Lesser General ////
//// Public License as published by the Free Software Foundation; ////
//// either version 2.1 of the License, or (at your option) any ////
//// later version. ////
//// ////
//// This source is distributed in the hope that it will be ////
//// useful, but WITHOUT ANY WARRANTY; without even the implied ////
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
//// PURPOSE. See the GNU Lesser General Public License for more ////
//// details. ////
//// ////
//// You should have received a copy of the GNU Lesser General ////
//// Public License along with this source; if not, download it ////
//// from http://www.opencores.org/lgpl.shtml ////
//// ////
//////////////////////////////////////////////////////////////////////
//
// CVS Revision History
//
// $Log: not supported by cvs2svn $
// Revision 1.6 2003/10/03 10:16:52 primozs
// support for configurable devider added
//
// Revision 1.5 2003/06/30 15:29:27 simons
// Error fixed again.
//
// Revision 1.4 2003/06/30 15:25:45 simons
// Error fixed.
//
// Revision 1.3 2003/05/28 16:27:09 simons
// Change the address width.
//
// Revision 1.2 2002/04/09 13:21:15 mihad
// Added mouse interface and everything for its handling, cleaned up some unused code
//
// Revision 1.1.1.1 2002/02/18 16:16:56 mihad
// Initial project import - working
//
//
 
`include "ps2_defines.v"
// synopsys translate_off
`include "timescale.v"
// synopsys translate_on
 
module ps2_top
(
wb_clk_i,
wb_rst_i,
wb_cyc_i,
wb_stb_i,
wb_we_i,
wb_sel_i,
wb_adr_i,
wb_dat_i,
wb_dat_o,
wb_ack_o,
 
wb_int_o,
 
ps2_kbd_clk_pad_i,
ps2_kbd_data_pad_i,
ps2_kbd_clk_pad_o,
ps2_kbd_data_pad_o,
ps2_kbd_clk_pad_oe_o,
ps2_kbd_data_pad_oe_o
`ifdef PS2_AUX
,
wb_intb_o,
 
ps2_aux_clk_pad_i,
ps2_aux_data_pad_i,
ps2_aux_clk_pad_o,
ps2_aux_data_pad_o,
ps2_aux_clk_pad_oe_o,
ps2_aux_data_pad_oe_o
`endif
) ;
 
input wb_clk_i,
wb_rst_i,
wb_cyc_i,
wb_stb_i,
wb_we_i ;
 
input [3:0] wb_sel_i ;
 
input [3:0] wb_adr_i ;
input [31:0] wb_dat_i ;
 
output [31:0] wb_dat_o ;
 
output wb_ack_o ;
 
output wb_int_o ;
 
input ps2_kbd_clk_pad_i,
ps2_kbd_data_pad_i ;
 
output ps2_kbd_clk_pad_o,
ps2_kbd_data_pad_o,
ps2_kbd_clk_pad_oe_o,
ps2_kbd_data_pad_oe_o ;
 
`ifdef PS2_AUX
output wb_intb_o ;
input ps2_aux_clk_pad_i,
ps2_aux_data_pad_i ;
 
output ps2_aux_clk_pad_o,
ps2_aux_data_pad_o,
ps2_aux_clk_pad_oe_o,
ps2_aux_data_pad_oe_o ;
 
assign ps2_aux_clk_pad_o = 1'b0 ;
assign ps2_aux_data_pad_o = 1'b0 ;
`endif
 
wire rx_released,
rx_kbd_data_ready,
rx_translated_data_ready,
rx_kbd_read_wb,
rx_kbd_read_tt,
tx_kbd_write,
tx_kbd_write_ack,
tx_error_no_keyboard_ack,
ps2_ctrl_kbd_data_en_,
ps2_ctrl_kbd_clk_en_,
ps2_ctrl_kbd_clk,
inhibit_kbd_if ;
 
wire [15:0] devide_reg;
 
wire [7:0] rx_scan_code,
rx_translated_scan_code,
tx_kbd_data ;
 
assign ps2_kbd_clk_pad_o = 1'b0 ;
assign ps2_kbd_data_pad_o = 1'b0 ;
 
ps2_io_ctrl i_ps2_io_ctrl_keyboard
(
.clk_i (wb_clk_i),
.rst_i (wb_rst_i),
.ps2_ctrl_clk_en_i_ (ps2_ctrl_kbd_clk_en_),
.ps2_ctrl_data_en_i_ (ps2_ctrl_kbd_data_en_),
.ps2_clk_pad_i (ps2_kbd_clk_pad_i),
.ps2_clk_pad_oe_o (ps2_kbd_clk_pad_oe_o),
.ps2_data_pad_oe_o (ps2_kbd_data_pad_oe_o),
.inhibit_if_i (inhibit_kbd_if),
.ps2_ctrl_clk_o (ps2_ctrl_kbd_clk)
);
 
`ifdef PS2_AUX
wire rx_aux_data_ready,
rx_aux_read,
tx_aux_write,
tx_aux_write_ack,
tx_error_no_aux_ack,
ps2_ctrl_aux_data_en_,
ps2_ctrl_aux_clk_en_,
ps2_ctrl_aux_clk,
inhibit_aux_if ;
 
wire [7:0] rx_aux_data,
tx_aux_data ;
 
ps2_io_ctrl i_ps2_io_ctrl_auxiliary
(
.clk_i (wb_clk_i),
.rst_i (wb_rst_i),
.ps2_ctrl_clk_en_i_ (ps2_ctrl_aux_clk_en_),
.ps2_ctrl_data_en_i_ (ps2_ctrl_aux_data_en_),
.ps2_clk_pad_i (ps2_aux_clk_pad_i),
.ps2_clk_pad_oe_o (ps2_aux_clk_pad_oe_o),
.ps2_data_pad_oe_o (ps2_aux_data_pad_oe_o),
.inhibit_if_i (inhibit_aux_if),
.ps2_ctrl_clk_o (ps2_ctrl_aux_clk)
);
 
ps2_mouse #(`PS2_TIMER_60USEC_VALUE_PP, `PS2_TIMER_60USEC_BITS_PP, `PS2_TIMER_5USEC_VALUE_PP, `PS2_TIMER_5USEC_BITS_PP)
i_ps2_mouse
(
.clk (wb_clk_i),
.reset (wb_rst_i),
.ps2_clk_en_o_ (ps2_ctrl_aux_clk_en_),
.ps2_data_en_o_ (ps2_ctrl_aux_data_en_),
.ps2_clk_i (ps2_ctrl_aux_clk),
.ps2_data_i (ps2_aux_data_pad_i),
.rx_scan_code (rx_aux_data),
.rx_data_ready (rx_aux_data_ready),
.rx_read (rx_aux_read),
.tx_data (tx_aux_data),
.tx_write (tx_aux_write),
.tx_write_ack_o (tx_aux_write_ack),
.tx_error_no_ack (tx_error_no_aux_ack),
.devide_reg_i (devide_reg)
);
 
`endif
 
ps2_keyboard #(`PS2_TIMER_60USEC_VALUE_PP, `PS2_TIMER_60USEC_BITS_PP, `PS2_TIMER_5USEC_VALUE_PP, `PS2_TIMER_5USEC_BITS_PP)
i_ps2_keyboard
(
.clk (wb_clk_i),
.reset (wb_rst_i),
.ps2_clk_en_o_ (ps2_ctrl_kbd_clk_en_),
.ps2_data_en_o_ (ps2_ctrl_kbd_data_en_),
.ps2_clk_i (ps2_ctrl_kbd_clk),
.ps2_data_i (ps2_kbd_data_pad_i),
.rx_released (rx_released),
.rx_scan_code (rx_scan_code),
.rx_data_ready (rx_kbd_data_ready),
.rx_read (rx_kbd_read_tt),
.tx_data (tx_kbd_data),
.tx_write (tx_kbd_write),
.tx_write_ack_o (tx_kbd_write_ack),
.tx_error_no_keyboard_ack (tx_error_no_keyboard_ack),
.translate (translate),
.devide_reg_i (devide_reg)
);
 
ps2_wb_if i_ps2_wb_if
(
.wb_clk_i (wb_clk_i),
.wb_rst_i (wb_rst_i),
.wb_cyc_i (wb_cyc_i),
.wb_stb_i (wb_stb_i),
.wb_we_i (wb_we_i),
.wb_sel_i (wb_sel_i),
.wb_adr_i (wb_adr_i),
.wb_dat_i (wb_dat_i),
.wb_dat_o (wb_dat_o),
.wb_ack_o (wb_ack_o),
 
.wb_int_o (wb_int_o),
 
.devide_reg_o (devide_reg),
 
.rx_scancode_i (rx_translated_scan_code),
.rx_kbd_data_ready_i (rx_translated_data_ready),
.rx_kbd_read_o (rx_kbd_read_wb),
.tx_kbd_data_o (tx_kbd_data),
.tx_kbd_write_o (tx_kbd_write),
.tx_kbd_write_ack_i (tx_kbd_write_ack),
.translate_o (translate),
.ps2_kbd_clk_i (ps2_kbd_clk_pad_i),
.inhibit_kbd_if_o (inhibit_kbd_if)
`ifdef PS2_AUX
,
.wb_intb_o (wb_intb_o),
 
.rx_aux_data_i (rx_aux_data),
.rx_aux_data_ready_i (rx_aux_data_ready),
.rx_aux_read_o (rx_aux_read),
.tx_aux_data_o (tx_aux_data),
.tx_aux_write_o (tx_aux_write),
.tx_aux_write_ack_i (tx_aux_write_ack),
.ps2_aux_clk_i (ps2_aux_clk_pad_i),
.inhibit_aux_if_o (inhibit_aux_if)
`endif
) ;
 
ps2_translation_table i_ps2_translation_table
(
.reset_i (wb_rst_i),
.clock_i (wb_clk_i),
.translate_i (translate),
.code_i (rx_scan_code),
.code_o (rx_translated_scan_code),
.address_i (8'h00),
.data_i (8'h00),
.we_i (1'b0),
.re_i (1'b0),
.data_o (),
.rx_data_ready_i (rx_kbd_data_ready),
.rx_translated_data_ready_o (rx_translated_data_ready),
.rx_read_i (rx_kbd_read_wb),
.rx_read_o (rx_kbd_read_tt),
.rx_released_i (rx_released)
) ;
 
endmodule // ps2_top
/wb_ps2_keyboard/timescale.v
0,0 → 1,308
`timescale 1ns/1ps
/wb_ps2_keyboard/ps2_translation_table.v
0,0 → 1,294
//////////////////////////////////////////////////////////////////////
//// ////
//// ps2_translation_table.v ////
//// ////
//// This file is part of the "ps2" project ////
//// http://www.opencores.org/cores/ps2/ ////
//// ////
//// Author(s): ////
//// - mihad@opencores.org ////
//// - Miha Dolenc ////
//// ////
//// All additional information is avaliable in the README.txt ////
//// file. ////
//// ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2000 Miha Dolenc, mihad@opencores.org ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer. ////
//// ////
//// This source file is free software; you can redistribute it ////
//// and/or modify it under the terms of the GNU Lesser General ////
//// Public License as published by the Free Software Foundation; ////
//// either version 2.1 of the License, or (at your option) any ////
//// later version. ////
//// ////
//// This source is distributed in the hope that it will be ////
//// useful, but WITHOUT ANY WARRANTY; without even the implied ////
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
//// PURPOSE. See the GNU Lesser General Public License for more ////
//// details. ////
//// ////
//// You should have received a copy of the GNU Lesser General ////
//// Public License along with this source; if not, download it ////
//// from http://www.opencores.org/lgpl.shtml ////
//// ////
//////////////////////////////////////////////////////////////////////
//
// CVS Revision History
//
// $Log: not supported by cvs2svn $
// Revision 1.4 2003/07/01 12:34:03 mihad
// Added an option to use constant values instead of RAM
// in the translation table.
//
// Revision 1.3 2003/06/02 17:13:22 simons
// resetall keyword removed. ifdef moved to a separated line.
//
// Revision 1.2 2002/04/09 13:21:15 mihad
// Added mouse interface and everything for its handling, cleaned up some unused code
//
// Revision 1.1.1.1 2002/02/18 16:16:56 mihad
// Initial project import - working
//
//
 
`include "ps2_defines.v"
 
// synopsys translate_off
`include "timescale.v"
// synopsys translate_on
 
module ps2_translation_table
(
reset_i,
clock_i,
translate_i,
code_i,
code_o,
address_i,
data_i,
we_i,
re_i,
data_o,
rx_data_ready_i,
rx_translated_data_ready_o,
rx_read_i,
rx_read_o,
rx_released_i
) ;
 
input reset_i,
clock_i,
translate_i ;
 
input [7:0] code_i ;
output [7:0] code_o ;
input [7:0] address_i ;
input [7:0] data_i ;
input we_i,
re_i ;
 
output [7:0] data_o ;
 
input rx_data_ready_i,
rx_read_i ;
 
output rx_translated_data_ready_o ;
output rx_read_o ;
 
input rx_released_i ;
 
wire translation_table_write_enable = we_i && (!translate_i || !rx_data_ready_i) ;
wire [7:0] translation_table_address = ((we_i || re_i) && (!rx_data_ready_i || !translate_i)) ? address_i : code_i ;
wire translation_table_enable = we_i || re_i || (translate_i && rx_data_ready_i) ;
 
reg rx_translated_data_ready ;
always@(posedge clock_i or posedge reset_i)
begin
if ( reset_i )
rx_translated_data_ready <= #1 1'b0 ;
else if ( rx_read_i || !translate_i )
rx_translated_data_ready <= #1 1'b0 ;
else
rx_translated_data_ready <= #1 rx_data_ready_i ;
end
 
`ifdef PS2_RAMB4
`define PS2_RAM_SELECTED
 
wire [7:0] ram_out ;
RAMB4_S8
`ifdef SIM
#("ignore",
`PS2_TRANSLATION_TABLE_31_0,
`PS2_TRANSLATION_TABLE_63_32,
`PS2_TRANSLATION_TABLE_95_64,
`PS2_TRANSLATION_TABLE_127_96,
`PS2_TRANSLATION_TABLE_159_128,
`PS2_TRANSLATION_TABLE_191_160,
`PS2_TRANSLATION_TABLE_223_192,
`PS2_TRANSLATION_TABLE_255_224)
`endif
ps2_ram
(
.DO (ram_out),
.ADDR ({1'b0, translation_table_address}),
.DI (data_i),
.EN (translation_table_enable),
.CLK (clock_i),
.WE (translation_table_write_enable),
.RST (reset_i)
) ;
 
`endif
 
`ifdef PS2_CONSTANTS_ROM
`define PS2_RAM_SELECTED
 
reg [32 * 8 - 1:0] ps2_32byte_constant ;
reg [7:0] ram_out ;
 
always@(translation_table_address)
begin
case (translation_table_address[7:5])
3'b000:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_31_0 ;
3'b001:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_63_32 ;
3'b010:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_95_64 ;
3'b011:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_127_96 ;
3'b100:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_159_128 ;
3'b101:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_191_160 ;
3'b110:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_223_192 ;
3'b111:ps2_32byte_constant = `PS2_TRANSLATION_TABLE_255_224 ;
endcase
end
 
always@(posedge clock_i or posedge reset_i)
begin
if ( reset_i )
ram_out <= #1 8'h0 ;
else if ( translation_table_enable )
begin:get_dat_out
reg [7:0] bit_num ;
bit_num = translation_table_address[4:0] << 3 ;
 
repeat(8)
begin
ram_out[bit_num % 8] <= #1 ps2_32byte_constant[bit_num] ;
bit_num = bit_num + 1'b1 ;
end
end
end
 
`endif
 
`ifdef PS2_RAM_SELECTED
`else
`define PS2_RAM_SELECTED
 
reg [7:0] ps2_ram [0:255] ;
reg [7:0] ram_out ;
 
always@(posedge clock_i or posedge reset_i)
begin
if ( reset_i )
ram_out <= #1 8'h0 ;
else if ( translation_table_enable )
ram_out <= #1 ps2_ram[translation_table_address] ;
end
 
always@(posedge clock_i)
begin
if ( translation_table_write_enable )
ps2_ram[translation_table_address] <= #1 data_i ;
end
 
// synopsys translate_off
initial
begin:ps2_ram_init
integer i ;
reg [255:0] temp_init_val ;
 
temp_init_val = `PS2_TRANSLATION_TABLE_31_0 ;
 
for ( i = 0 ; i <= 31 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
 
temp_init_val = `PS2_TRANSLATION_TABLE_63_32 ;
 
for ( i = 32 ; i <= 63 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
 
temp_init_val = `PS2_TRANSLATION_TABLE_95_64 ;
 
for ( i = 64 ; i <= 95 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
 
temp_init_val = `PS2_TRANSLATION_TABLE_127_96 ;
 
for ( i = 96 ; i <= 127 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
 
temp_init_val = `PS2_TRANSLATION_TABLE_159_128 ;
 
for ( i = 128 ; i <= 159 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
 
temp_init_val = `PS2_TRANSLATION_TABLE_191_160 ;
 
for ( i = 160 ; i <= 191 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
 
temp_init_val = `PS2_TRANSLATION_TABLE_223_192 ;
 
for ( i = 192 ; i <= 223 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
 
temp_init_val = `PS2_TRANSLATION_TABLE_255_224 ;
 
for ( i = 224 ; i <= 255 ; i = i + 1 )
begin
ps2_ram[i] = temp_init_val[7:0] ;
temp_init_val = temp_init_val >> 8 ;
end
end
 
// synopsys translate_on
 
`endif
 
assign data_o = ram_out ;
assign code_o = translate_i ? {(rx_released_i | ram_out[7]), ram_out[6:0]} : code_i ;
assign rx_translated_data_ready_o = translate_i ? rx_translated_data_ready : rx_data_ready_i ;
assign rx_read_o = rx_read_i ;
 
`undef PS2_RAM_SELECTED
 
endmodule //ps2_translation_table
/wb_ps2_keyboard/ps2_wb_if.v
0,0 → 1,730
//////////////////////////////////////////////////////////////////////
//// ////
//// ps2_wb_if.v ////
//// ////
//// This file is part of the "ps2" project ////
//// http://www.opencores.org/cores/ps2/ ////
//// ////
//// Author(s): ////
//// - mihad@opencores.org ////
//// - Miha Dolenc ////
//// ////
//// All additional information is avaliable in the README.txt ////
//// file. ////
//// ////
//// ////
//////////////////////////////////////////////////////////////////////
//// ////
//// Copyright (C) 2000 Miha Dolenc, mihad@opencores.org ////
//// ////
//// This source file may be used and distributed without ////
//// restriction provided that this copyright statement is not ////
//// removed from the file and that any derivative work contains ////
//// the original copyright notice and the associated disclaimer. ////
//// ////
//// This source file is free software; you can redistribute it ////
//// and/or modify it under the terms of the GNU Lesser General ////
//// Public License as published by the Free Software Foundation; ////
//// either version 2.1 of the License, or (at your option) any ////
//// later version. ////
//// ////
//// This source is distributed in the hope that it will be ////
//// useful, but WITHOUT ANY WARRANTY; without even the implied ////
//// warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR ////
//// PURPOSE. See the GNU Lesser General Public License for more ////
//// details. ////
//// ////
//// You should have received a copy of the GNU Lesser General ////
//// Public License along with this source; if not, download it ////
//// from http://www.opencores.org/lgpl.shtml ////
//// ////
//////////////////////////////////////////////////////////////////////
//
// CVS Revision History
//
// $Log: not supported by cvs2svn $
// Revision 1.8 2003/11/06 18:47:46 gorand
// added 8-bit access to divider register.
//
// Revision 1.7 2003/10/03 10:16:52 primozs
// support for configurable devider added
//
// Revision 1.6 2003/05/28 16:27:09 simons
// Change the address width.
//
// Revision 1.5 2002/04/09 13:24:11 mihad
// Added mouse interface and everything for its handling, cleaned up some unused code
//
// Revision 1.4 2002/02/20 16:35:43 mihad
// Little/big endian changes continued
//
// Revision 1.3 2002/02/20 15:20:10 mihad
// Little/big endian changes incorporated
//
// Revision 1.2 2002/02/18 18:07:55 mihad
// One bug fixed
//
// Revision 1.1.1.1 2002/02/18 16:16:56 mihad
// Initial project import - working
//
//
 
// synopsys translate_off
`include "timescale.v"
// synopsys translate_on
 
module ps2_wb_if
(
wb_clk_i,
wb_rst_i,
wb_cyc_i,
wb_stb_i,
wb_we_i,
wb_sel_i,
wb_adr_i,
wb_dat_i,
wb_dat_o,
wb_ack_o,
 
wb_int_o,
 
tx_kbd_write_ack_i,
tx_kbd_data_o,
tx_kbd_write_o,
rx_scancode_i,
rx_kbd_data_ready_i,
rx_kbd_read_o,
translate_o,
ps2_kbd_clk_i,
devide_reg_o,
inhibit_kbd_if_o
`ifdef PS2_AUX
,
wb_intb_o,
 
rx_aux_data_i,
rx_aux_data_ready_i,
rx_aux_read_o,
tx_aux_data_o,
tx_aux_write_o,
tx_aux_write_ack_i,
ps2_aux_clk_i,
inhibit_aux_if_o
`endif
) ;
 
input wb_clk_i,
wb_rst_i,
wb_cyc_i,
wb_stb_i,
wb_we_i ;
 
input [3:0] wb_sel_i ;
 
input [3:0] wb_adr_i ;
 
input [31:0] wb_dat_i ;
 
output [31:0] wb_dat_o ;
 
output wb_ack_o ;
 
reg wb_ack_o ;
 
output wb_int_o ;
reg wb_int_o ;
 
input tx_kbd_write_ack_i ;
 
input [7:0] rx_scancode_i ;
input rx_kbd_data_ready_i ;
output rx_kbd_read_o ;
 
output tx_kbd_write_o ;
output [7:0] tx_kbd_data_o ;
 
output translate_o ;
input ps2_kbd_clk_i ;
 
output inhibit_kbd_if_o ;
 
reg [7:0] input_buffer,
output_buffer ;
 
output [15:0] devide_reg_o;
reg [15:0] devide_reg;
assign devide_reg_o = devide_reg;
 
 
reg [15:0] wb_dat_i_sampled ;
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
wb_dat_i_sampled <= #1 0 ;
else if ( wb_cyc_i && wb_stb_i && wb_we_i )
wb_dat_i_sampled <= #1 wb_dat_i[31:16] ;
end
 
`ifdef PS2_AUX
output wb_intb_o ;
reg wb_intb_o ;
 
input [7:0] rx_aux_data_i ;
input rx_aux_data_ready_i ;
output rx_aux_read_o ;
output [7:0] tx_aux_data_o ;
output tx_aux_write_o ;
input tx_aux_write_ack_i ;
input ps2_aux_clk_i ;
output inhibit_aux_if_o ;
reg inhibit_aux_if_o ;
reg aux_output_buffer_full ;
reg aux_input_buffer_full ;
reg interrupt2 ;
reg enable2 ;
assign tx_aux_data_o = output_buffer ;
assign tx_aux_write_o = aux_output_buffer_full ;
`else
wire aux_input_buffer_full = 1'b0 ;
wire aux_output_buffer_full = 1'b0 ;
wire interrupt2 = 1'b0 ;
wire enable2 = 1'b1 ;
`endif
 
assign tx_kbd_data_o = output_buffer ;
 
reg input_buffer_full, // receive buffer
output_buffer_full ; // transmit buffer
 
assign tx_kbd_write_o = output_buffer_full ;
 
wire system_flag ;
wire a2 = 1'b0 ;
wire kbd_inhibit = ps2_kbd_clk_i ;
wire timeout = 1'b0 ;
wire perr = 1'b0 ;
 
wire [7:0] status_byte = {perr, timeout, aux_input_buffer_full, kbd_inhibit, a2, system_flag, output_buffer_full || aux_output_buffer_full, input_buffer_full} ;
 
reg read_input_buffer_reg ;
wire read_input_buffer = wb_cyc_i && wb_stb_i && wb_sel_i[3] && !wb_ack_o && !read_input_buffer_reg && !wb_we_i && (wb_adr_i[3:0] == 4'h0) ;
 
reg write_output_buffer_reg ;
wire write_output_buffer = wb_cyc_i && wb_stb_i && wb_sel_i[3] && !wb_ack_o && !write_output_buffer_reg && wb_we_i && (wb_adr_i[3:0] == 4'h0) ;
 
reg read_status_register_reg ;
wire read_status_register = wb_cyc_i && wb_stb_i && wb_sel_i[3] && !wb_ack_o && !read_status_register_reg && !wb_we_i && (wb_adr_i[3:0] == 4'h4) ;
 
reg send_command_reg ;
wire send_command = wb_cyc_i && wb_stb_i && wb_sel_i[3] && !wb_ack_o && !send_command_reg && wb_we_i && (wb_adr_i[3:0] == 4'h4) ;
 
reg write_devide_reg0 ;
wire write_devide0 = wb_cyc_i && wb_stb_i && wb_sel_i[2] && !wb_ack_o && !write_devide_reg0 && wb_we_i && (wb_adr_i[3:0] == 4'h8) ;
 
//reg read_devide_reg ;
wire read_devide = wb_cyc_i && wb_stb_i && ( wb_sel_i[2]|| wb_sel_i [3] ) && !wb_we_i && (wb_adr_i[3:0] == 4'h8) ;
 
reg write_devide_reg1 ;
wire write_devide1 = wb_cyc_i && wb_stb_i && wb_sel_i[3] && !wb_ack_o && !write_devide_reg1 && wb_we_i && (wb_adr_i[3:0] == 4'h8) ;
 
 
reg translate_o,
enable1,
system,
interrupt1 ;
 
reg inhibit_kbd_if_o ;
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
inhibit_kbd_if_o <= #1 1'b0 ;
else if ( ps2_kbd_clk_i && rx_kbd_data_ready_i && !enable1)
inhibit_kbd_if_o <= #1 1'b1 ;
else if ( !rx_kbd_data_ready_i || enable1 )
inhibit_kbd_if_o <= #1 1'b0 ;
 
end
 
`ifdef PS2_AUX
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
inhibit_aux_if_o <= #1 1'b1 ;
else if ( ps2_aux_clk_i && rx_aux_data_ready_i && !enable2 )
inhibit_aux_if_o <= #1 1'b1 ;
else if ( !rx_aux_data_ready_i || enable2 )
inhibit_aux_if_o <= #1 1'b0 ;
 
end
`endif
 
assign system_flag = system ;
 
wire [7:0] command_byte = {1'b0, translate_o, enable2, enable1, 1'b0, system, interrupt2, interrupt1} ;
 
reg [7:0] current_command ;
reg [7:0] current_command_output ;
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
begin
send_command_reg <= #1 1'b0 ;
read_input_buffer_reg <= #1 1'b0 ;
write_output_buffer_reg <= #1 1'b0 ;
read_status_register_reg <= #1 1'b0 ;
write_devide_reg0 <= #1 1'b0 ;
//read_devide_reg <= #1 1'b0 ;
write_devide_reg1 <= #1 1'b0 ;
end
else
begin
send_command_reg <= #1 send_command ;
read_input_buffer_reg <= #1 read_input_buffer ;
write_output_buffer_reg <= #1 write_output_buffer ;
read_status_register_reg <= #1 read_status_register ;
write_devide_reg0 <= #1 write_devide0 ;
//read_devide_reg <= #1 read_devide ;
write_devide_reg1 <= #1 write_devide1 ;
end
end
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
current_command <= #1 8'h0 ;
else if ( send_command_reg )
current_command <= #1 wb_dat_i_sampled[15:8] ;
end
 
reg current_command_valid,
current_command_returns_value,
current_command_gets_parameter,
current_command_gets_null_terminated_string ;
 
reg write_output_buffer_reg_previous ;
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
write_output_buffer_reg_previous <= #1 1'b0 ;
else
write_output_buffer_reg_previous <= #1 write_output_buffer_reg ;
end
 
wire invalidate_current_command =
current_command_valid &&
(( current_command_returns_value && read_input_buffer_reg && input_buffer_full) ||
( current_command_gets_parameter && write_output_buffer_reg_previous ) ||
( current_command_gets_null_terminated_string && write_output_buffer_reg_previous && (output_buffer == 8'h00) ) ||
( !current_command_returns_value && !current_command_gets_parameter && !current_command_gets_null_terminated_string )
) ;
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
current_command_valid <= #1 1'b0 ;
else if ( invalidate_current_command )
current_command_valid <= #1 1'b0 ;
else if ( send_command_reg )
current_command_valid <= #1 1'b1 ;
 
end
 
reg write_command_byte ;
reg current_command_output_valid ;
always@(
current_command or
command_byte or
write_output_buffer_reg_previous or
current_command_valid or
output_buffer
)
begin
current_command_returns_value = 1'b0 ;
current_command_gets_parameter = 1'b0 ;
current_command_gets_null_terminated_string = 1'b0 ;
current_command_output = 8'h00 ;
write_command_byte = 1'b0 ;
current_command_output_valid = 1'b0 ;
case(current_command)
8'h20:begin
current_command_returns_value = 1'b1 ;
current_command_output = command_byte ;
current_command_output_valid = 1'b1 ;
end
8'h60:begin
current_command_gets_parameter = 1'b1 ;
write_command_byte = write_output_buffer_reg_previous && current_command_valid ;
end
8'hA1:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'h00 ;
current_command_output_valid = 1'b1 ;
end
8'hA4:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'hF1 ;
current_command_output_valid = 1'b1 ;
end
8'hA5:begin
current_command_gets_null_terminated_string = 1'b1 ;
end
8'hA6:begin
end
8'hA7:begin
end
8'hA8:begin
end
8'hA9:begin
current_command_returns_value = 1'b1 ;
current_command_output_valid = 1'b1 ;
`ifdef PS2_AUX
current_command_output = 8'h00 ; // interface OK
`else
current_command_output = 8'h02 ; // clock line stuck high
`endif
end
8'hAA:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'h55 ;
current_command_output_valid = 1'b1 ;
end
8'hAB:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'h00 ;
current_command_output_valid = 1'b1 ;
end
8'hAD:begin
end
8'hAE:begin
end
8'hAF:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'h00 ;
current_command_output_valid = 1'b1 ;
end
8'hC0:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'hFF ;
current_command_output_valid = 1'b1 ;
end
8'hC1:begin
end
8'hC2:begin
end
8'hD0:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'h01 ; // only system reset bit is 1
current_command_output_valid = 1'b1 ;
end
8'hD1:begin
current_command_gets_parameter = 1'b1 ;
end
8'hD2:begin
current_command_returns_value = 1'b1 ;
current_command_gets_parameter = 1'b1 ;
current_command_output = output_buffer ;
current_command_output_valid = write_output_buffer_reg_previous ;
end
8'hD3:begin
current_command_gets_parameter = 1'b1 ;
`ifdef PS2_AUX
current_command_returns_value = 1'b1 ;
current_command_output = output_buffer ;
current_command_output_valid = write_output_buffer_reg_previous ;
`endif
end
8'hD4:begin
current_command_gets_parameter = 1'b1 ;
end
8'hE0:begin
current_command_returns_value = 1'b1 ;
current_command_output = 8'hFF ;
current_command_output_valid = 1'b1 ;
end
endcase
end
 
reg cyc_i_previous ;
reg stb_i_previous ;
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
begin
cyc_i_previous <= #1 1'b0 ;
stb_i_previous <= #1 1'b0 ;
end
else if ( wb_ack_o )
begin
cyc_i_previous <= #1 1'b0 ;
stb_i_previous <= #1 1'b0 ;
end
else
begin
cyc_i_previous <= #1 wb_cyc_i ;
stb_i_previous <= #1 wb_stb_i ;
end
 
end
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
wb_ack_o <= #1 1'b0 ;
else if ( wb_ack_o )
wb_ack_o <= #1 1'b0 ;
else
wb_ack_o <= #1 cyc_i_previous && stb_i_previous ;
end
 
reg [31:0] wb_dat_o ;
wire wb_read = read_input_buffer_reg || read_status_register_reg || read_devide ;
 
wire [15:0] output_data = read_status_register_reg ? {2{status_byte}} : read_devide ? devide_reg : {2{input_buffer}} ;
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
wb_dat_o <= #1 32'h0 ;
else if ( wb_read )
wb_dat_o <= #1 {2{output_data}} ;
end
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
output_buffer_full <= #1 1'b0 ;
else if ( output_buffer_full && tx_kbd_write_ack_i || enable1)
output_buffer_full <= #1 1'b0 ;
else
output_buffer_full <= #1 write_output_buffer_reg && (!current_command_valid || (!current_command_gets_parameter && !current_command_gets_null_terminated_string)) ;
end
 
`ifdef PS2_AUX
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
aux_output_buffer_full <= #1 1'b0 ;
else if ( aux_output_buffer_full && tx_aux_write_ack_i || enable2)
aux_output_buffer_full <= #1 1'b0 ;
else
aux_output_buffer_full <= #1 write_output_buffer_reg && current_command_valid && (current_command == 8'hD4) ;
end
`endif
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
output_buffer <= #1 8'h00 ;
else if ( write_output_buffer_reg )
output_buffer <= #1 wb_dat_i_sampled[15:8];
end
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
devide_reg <= #1 8'h00 ;
else
begin
if ( write_devide_reg0 )
devide_reg[7:0] <= #1 wb_dat_i_sampled[7:0] ;
if ( write_devide_reg1 )
devide_reg[15:8] <= #1 wb_dat_i_sampled[15:8] ;
end
end
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
begin
translate_o <= #1 1'b0 ;
system <= #1 1'b0 ;
interrupt1 <= #1 1'b0 ;
`ifdef PS2_AUX
interrupt2 <= #1 1'b0 ;
`endif
end
else if ( write_command_byte )
begin
translate_o <= #1 output_buffer[6] ;
system <= #1 output_buffer[2] ;
interrupt1 <= #1 output_buffer[0] ;
`ifdef PS2_AUX
interrupt2 <= #1 output_buffer[1] ;
`endif
end
end
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
enable1 <= #1 1'b1 ;
else if ( current_command_valid && (current_command == 8'hAE) )
enable1 <= #1 1'b0 ;
else if ( current_command_valid && (current_command == 8'hAD) )
enable1 <= #1 1'b1 ;
else if ( write_command_byte )
enable1 <= #1 output_buffer[4] ;
 
end
 
`ifdef PS2_AUX
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
enable2 <= #1 1'b1 ;
else if ( current_command_valid && (current_command == 8'hA8) )
enable2 <= #1 1'b0 ;
else if ( current_command_valid && (current_command == 8'hA7) )
enable2 <= #1 1'b1 ;
else if ( write_command_byte )
enable2 <= #1 output_buffer[5] ;
 
end
`endif
 
wire write_input_buffer_from_command = current_command_valid && current_command_returns_value && current_command_output_valid ;
wire write_input_buffer_from_kbd = !input_buffer_full && rx_kbd_data_ready_i && !enable1 && !current_command_valid ;
 
`ifdef PS2_AUX
wire write_input_buffer_from_aux = !input_buffer_full && rx_aux_data_ready_i && !enable2 && !current_command_valid && !write_input_buffer_from_kbd ;
`endif
 
wire load_input_buffer_value =
write_input_buffer_from_command
||
write_input_buffer_from_kbd
`ifdef PS2_AUX
||
write_input_buffer_from_aux
`endif
;
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
input_buffer_full <= #1 1'b0 ;
else if ( read_input_buffer_reg )
input_buffer_full <= #1 1'b0 ;
else if ( load_input_buffer_value )
input_buffer_full <= #1 1'b1 ;
end
 
`ifdef PS2_AUX
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
aux_input_buffer_full <= #1 1'b0 ;
else if ( read_input_buffer_reg )
aux_input_buffer_full <= #1 1'b0 ;
else if ( write_input_buffer_from_aux || (write_input_buffer_from_command && (current_command == 8'hD3)) )
aux_input_buffer_full <= #1 1'b1 ;
end
`endif
 
reg input_buffer_filled_from_command ;
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
input_buffer_filled_from_command <= #1 1'b0 ;
else if ( read_input_buffer_reg )
input_buffer_filled_from_command <= #1 1'b0 ;
else if ( write_input_buffer_from_command )
input_buffer_filled_from_command <= #1 1'b1 ;
end
 
`ifdef PS2_AUX
reg [7:0] value_to_load_in_input_buffer ;
always@
(
write_input_buffer_from_command
or
current_command_output
or
rx_scancode_i
or
write_input_buffer_from_kbd
or
rx_aux_data_i
)
begin
case ({write_input_buffer_from_command, write_input_buffer_from_kbd})
2'b10,
2'b11 : value_to_load_in_input_buffer = current_command_output ;
2'b01 : value_to_load_in_input_buffer = rx_scancode_i ;
2'b00 : value_to_load_in_input_buffer = rx_aux_data_i ;
endcase
end
 
`else
wire [7:0] value_to_load_in_input_buffer = write_input_buffer_from_command ? current_command_output : rx_scancode_i ;
`endif
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
input_buffer <= #1 8'h00 ;
else if ( load_input_buffer_value )
input_buffer <= #1 value_to_load_in_input_buffer ;
end
 
assign rx_kbd_read_o = rx_kbd_data_ready_i &&
( enable1
||
( read_input_buffer_reg
&&
input_buffer_full
&&
!input_buffer_filled_from_command
`ifdef PS2_AUX
&&
!aux_input_buffer_full
`endif
)
);
 
`ifdef PS2_AUX
assign rx_aux_read_o = rx_aux_data_ready_i &&
( enable2 ||
( read_input_buffer_reg
&&
input_buffer_full
&&
aux_input_buffer_full
&&
!input_buffer_filled_from_command
)
);
`endif
 
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
wb_int_o <= #1 1'b0 ;
else if ( read_input_buffer_reg || enable1 || !interrupt1)
wb_int_o <= #1 1'b0 ;
else
wb_int_o <= #1 input_buffer_full
`ifdef PS2_AUX
&&
!aux_input_buffer_full
`endif
;
end
 
`ifdef PS2_AUX
always@(posedge wb_clk_i or posedge wb_rst_i)
begin
if ( wb_rst_i )
wb_intb_o <= #1 1'b0 ;
else if ( read_input_buffer_reg || enable2 || !interrupt2)
wb_intb_o <= #1 1'b0 ;
else
wb_intb_o <= #1 input_buffer_full
&&
aux_input_buffer_full
;
end
`endif
 
endmodule // ps2_wb_if

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.