16BIT RISC PROCESSOR
Hola Amigos
I have designed a 16bit RISC processor designed with Xilinx iSim ans iSim simulator. RISC stands for Reduced Instruction Set Computer which is small microprocessor designed to favour small tasks and compute instructions with less time for the execution process.
Common RISC processors that you would see around are ARM, MIPS, IBM Pc.
Why was RISC introduced ?
As compared with CISC (Complex Instruction Set Computer) which takes a complex time to execute the instructions was reducing the performance of computing where the speed was drowning when CPU contacts the data memory. Hence another alternative was set in motion and that was RISC architecture.
Coming down to my 16bit processor.
ALU Code-
**************************************************************************************
module ALU(ain,bin,func,result,z);
input [7:0]ain;
input [7:0]bin;
output reg[7:0]result;
reg carry,temp=0;
input [3:0]func;
output reg z;
//wire [7:0]result;
//assign n = result[7];
always @(ain or bin)begin
if(func==4’b0000)begin
{temp,result} = ain + bin;
carry = temp;
if(result==0)
z=1;
end
else if(func==4’b0001)begin
{temp,result} = ain – bin;
carry = temp;
if(result==0)
z=1;
end
else if(func==4’b0010)begin
{temp,result} = ain + 1;
carry = temp;
if(result==0)
z=1;
end
else if(func==4’b0011)begin
{temp,result} = ain – 1;
carry = temp;
if(result==0)
z=1;
end
else if(func==4’b0100)begin
result = ain | bin;
carry = 0;
if(result==0)
z=1;end //OR
else if(func==4’b0101)begin
result = ain & bin;
carry = 0;
if(result==0)
z=1;end //AND
else if(func==4’b0110)begin
result = ain^bin;
carry = 0;
if(result==0)
z=1;end //XOR
else if(func==4’b0111)begin
result[0] = ~(ain[0]&bin[0]);
result[1] = ~(ain[1]&bin[1]);
result[2] = ~(ain[2]&bin[2]);
result[3] = ~(ain[3]&bin[3]);
result[4] = ~(ain[4]&bin[4]);
result[5] = ~(ain[5]&bin[5]);
result[6] = ~(ain[6]&bin[6]);
result[7] = ~(ain[7]&bin[7]);
carry = 0;
if(result==0)
z=1;end //NAND
else if(func==4’b1000)begin
result[0] = ~ain[0];
result[1] = ~ain[1];
result[2] = ~ain[2];
result[3] = ~ain[3];
result[4] = ~ain[4];
result[5] = ~ain[5];
result[6] = ~ain[6];
result[7] = ~ain[7];
carry = 0;
if(result==0)
z=1;end //NOT
else begin
result = 4’bxxxx;
carry = 0;
end //Default
if(result==0)
z = 1’b1;
else
z = 0;
end
endmodule
Instruction Memory
**************************************************************************************
module instruction(address,clk,opcode,jump,jiz,addA,addB,write_add,iformat,im_select);
input [15:0]address;
input clk,im_select;
output reg[3:0]opcode;
output reg[11:0] jump;
output reg[7:0] jiz;
output reg[3:0] addA;
output reg[3:0] addB;
output reg[3:0] write_add;
output reg[3:0] iformat;
reg [3:0]dest;
reg [15:0]instruction;
reg [15:0] imem[0:15];
initial begin
imem[2]<=16'b0000_0000_0000_0101;
imem[1]<=16'b0001_0010_0011_0011;
imem[3]<=16'b0010_0100_0010_0011;
imem[0]<=16'b0010_0000_0000_0101;
imem[4]<=16'b0010_0111_0010_0011;
imem[5]<=16'b0011_0010_0011_0010;
imem[6]<=16'b0110_0001_0001_0011;
imem[7]<=16'b0001_0110_0001_0011;
imem[8]<=16'b0110_0001_0011_0001;
end
always @(im_select)begin
if(im_select==1)begin
dest=write_add;
instruction = imem[address];
opcode = instruction[15:12];
jump = instruction[11:0];
jiz = instruction[7:0];
addA = instruction[11:8];
addB = instruction[7:4];
write_add = instruction[3:0];
iformat = instruction[3:0];
end
end
endmodule
Register File
**************************************************************************************
module Register(reg_wrt,readA,clk,readB,dest,data,readA_out,readB_out);
input reg_wrt;
input [3:0]readA,readB,dest;
input [7:0]data;
input clk;
reg [7:0] Register [0:15];
initial begin
Register[0]=0;//R0 alwayscontains zero
Register[1]=2; //Random values stored
Register[2]=4;
Register[3]=6;
Register[4]=8;
Register[5]=10; // You can change any value within this initial block
Register[6]=12;
Register[7]=14;
end
output reg [7:0]readA_out,readB_out;
always @(posedge clk)begin
readA_out <= Register[readA];
readB_out <= Register[readB];
if(reg_wrt==1)
Register[dest]=data;
end
endmodule
RAM (Datamemory)
**************************************************************************************
module RAM(address,clk,data_in,data_out,re,wr);
input [7:0]address;
input [7:0]data_in;
input clk,re,wr;
output [7:0]data_out;
reg[7:0] mem [0:30];
reg[7:0] data;
assign data_out = data;
initial
mem[16]=25;
always @(posedge clk)begin
if(wr)begin
mem[address] = data_in;
end
end
always @(address or re)begin
if(re)begin
data = mem[address];
end
end
endmodule
Program Counter
**************************************************************************************
module PC(in,clk,out,pc_sel,reset);
input [15:0]in;
input clk,reset,pc_sel;
output reg[15:0]out;
initial
out = 0;
always @(posedge clk)begin
if(reset==1)
out <= 16'bx;
else if(pc_sel==1 && in<50)
out <= in+1;
else if(pc_sel==0)
out <= in;
end
endmodule
input [1:0]sel2;
output reg[1:0]Mux2;
15 GPRs in Register File
R0 always contains zero. Modify it as you want but not recommended.
Instructions are represented by 2 bytes.
LOAD and STORE moves data to and forth from register to RAM and vice versa
Patch 1.0.0 released – Download
1. JIZ instruction has been added.
Opcode 1111 if Register has content as zero then it will jump to the given address
If you face any problem with code reply immediately




Can you share the ISA for above architecture? Are you following MIPS?
LikeLike
Yes I amBut I have excluded shift left 2 because it is required when we jump by 4 to next pc_address to remove last 2 zeros. But here we don't need it. I have modified and verified it.
LikeLike
I used it and got A grade from my teacher however I am a bit confused. Why have you avoided alucontrol instead used opcode directly from control unit ?Are you goin to add more instructions ?:)
LikeLike
Congo !!Well alucontrol was somehow taking a clock cycle and was making my processor a delay with 1 CC.Yes there are 2 more patches coming soon. 🙂
LikeLike
hi,shashi sumanI use your all code to simulation,but it can't run wave , a lot of signaldisplay \”Z\” (Hign resistance) , Have your code wrong ? or imcomplete ?
LikeLike
hi,shashi suman,I use your all code to simulation , but it can't run wave,a lot of signal display \”Z\”(high resistance) , have your code wrong? or incomplete ?
LikeLike
Hello Tony, the code is complete, You must simulate the top level module, This will only show the wave of clk and reset, however other waves can be added using the navigation to all modules from the navigator at left side in Xilinx Simulator.
LikeLike
hi , I have a question , your sel2 only 1 bit ,but sel2 control mux have 3 state (00 01 10) ?
LikeLike
Correct Bro ! I have changed it. Thanks for reviewing.The sel 10 state gets used only in JMP format so it was a relief.Also ran prime and Fibonacci on this code.
LikeLike
Your code is poorly documented!!!!Try to make it readable next time.
LikeLike
which module remain at top level ?and provide sequence of module and how to connect all module in quartus II software
LikeLike
The risc module is the top module with only clock and reset pins. Sorry for late reply
LikeLike
Yeah Will do my best
LikeLike
okay no problem , after successful compilation clock and reset pins are there then how to check final output ? and what kind of output should be there?
LikeLike
If you are using Xilinx then in the simulation windows check the left paneIt will show all modules.All you have to do is add any port of the module to the wave window by dragging or right click and add.
LikeLike
Regarding What kind of output should be there?Well you have to provide the right instruction and the program will do operation according to the opcode and it will be stored in the destination register whih you will have to drag in the window to see the stored value
LikeLike
i am using quartus II software any idea about that?
LikeLike
And Thank you
LikeLike
Your code is for 16 bit processor. Is this code is similar for 32 bit?
LikeLike
Yep, Just change the data width carefully
LikeLike
This comment has been removed by the author.
LikeLike
Should we write test bench for each module separately or only one test bench for whole module??
LikeLike
Nops…it has to be only for the outer most module
LikeLike
hai bro can iknown the complete test bench for this code
LikeLike
It is already present in the code itself.
LikeLike
Can you please make a veido about how to add all modules to the simulator
LikeLike
Follow this post. It might help you a lot I guesshttps://www.hellocodings.com/2018/12/how-to-simulate-verilog-code-in-xilinx.html?m=1
LikeLike
How can we inputs to each module??When I simulate the top module I will get high impedance states in opcode,all sel
LikeLike
Hi,Iam not gettige output using this code
LikeLike
You will have to instantiate modules. This is happening in datapath module which connects all modules
LikeLike
How have you connected all modules ?
LikeLike
I am not getting a and b values which have to read from register values
LikeLike
Lend me some time.I will re simulate and find any bug
LikeLike
Bro is your code is Pipelining risc processor?
LikeLike
Bro we are not getting RTL SCHEMATIC
LikeLike
No
LikeLike
What error are you getting ?I am getting my RTL with the same above code
LikeLike
when we are generating RTL schematic of datapath…it shows error that….multi source in Unit on signal ; this signal is connected to multiple drivers.
LikeLike
Two Sources are trying to throw output through a signle wire
LikeLike
Hi Everyone, I have edited and cleaned the code. I will repost with single cycle code as well as pipelined code with complete explanation.Thanks for your patience with my blog.
LikeLike
This comment has been removed by the author.
LikeLike
Releasing New Code Tomorrow !!
LikeLike
Please upload the pipeline code
LikeLike