使用quartus 2的MIPS处理器的计数器程序(汇编机器代码)

时间:2013-10-27 18:12:06

标签: assembly mips intel-fpga machine-language

我已经为一个计数器写了一个机器级代码,该代码应该递增到15然后递减到10,一旦达到15,然后重置为0,一旦达到10。

我已经在.mif文件中编写了这个程序。我使用了2个.mif文件,一个用于指令存储器,另一个用于数据存储器。

我觉得我没有正确编写跳转指令,因为我无法弄清楚如何编写跳转指令。

以下代码是指令存储器代码

enter code here





--
-- Instruction Memory Initialization File
--
-- Instrucion Format:
--
-- R-Type: <6-bit Opcode>,<5-bit rs>,<5-bit rt>,<5-bit rd>,<5-bit shamt>,<6-bit funct>
--    bits   (31-26)       (25-21)     (20-16)    (15-11)     (10-6)       (5-0)
--
-- I-Type: <6-bit Opcode>,<5-bit rs>,<5-bit rt>,<16-bit Address> 
--   bits     (31-26)      (25-21)   (20-16)     (15-0)


--File format:
-- Hex Address 3 hex nibbles (12 bits) : bit31 ...... bit0;

WIDTH=32;
DEPTH=1024;

ADDRESS_RADIX=HEX;
DATA_RADIX=BIN;

CONTENT BEGIN
--Hex Address :   bit31..........................bit0;
--   |             |                              |
    000       :    10001100000000000000000000000000;
--                 |____||___||___||______________|
--                   |     |    |          |
--                   lw, rs=0, rt=0,   offset=0 
-- This is the first instruction that get's executed
-- in mips_ss CPU in DE0-Nano.
-- This is a lw instructioni. It loads r0 with data from
-- data memory location 0. Data memory location 0 is 
-- preloaded with 0 , see DRAM.mif.
--
    001       :    10001100000000010000000000000100;
--                 |____||___||___||______________|
--                   |     |    |          |
--                   lw, rs=0, rt=1,   offset=4 
-- This is a lw instructioni. It loads r1 with data from
-- data memory location 4. Data memory location 4 is 
-- preloaded with 0, see DRAM.mif.
--
    002       :    10001100000000100000000000001000;
--                 |____||___||___||______________|
--                   |     |    |          |
--                   lw, rs=0, rt=2,   offset=8 
-- This is a lw instructioni. It loads r2 with data from
-- data memory location 8. Data memory location 8 is 
-- preloaded with 1, see DRAM.mif.
    003       :    10001100000000110000000000001100;
--                 |____||___||___||______________|
--                   |     |    |          |
--                   lw, rs=0, rt=3,   offset=12 
-- This is a lw instructioni. It loads r3 with data from
-- data memory location 8. Data memory location 8 is 
-- preloaded with 10, see DRAM.mif.
    004       :    10001100000001000000000000010000;
--                 |____||___||___||______________|
--                   |     |    |          |
--                   lw, rs=0, rt=4,   offset=16 
-- This is a lw instructioni. It loads r4 with data from
-- data memory location 8. Data memory location 8 is 
-- preloaded with 15, see DRAM.mif.
--
    005       :    00010000100000000000000000000000;
--                 |____||___||___||______________|
--                   |     |    |         |             
--                  beq,rs=4,rt=0,  offset exit loop(addr:008)

    006       :    00000000010000000000000000100000;
--                 |____||___||___||___||___||____|
--                   |     |    |    |    |    |         
--                 R-type,rs=2,rt=0,rd=0,---,f=add 
-- Add instructions (r-type, opcode=0, funct=100000) 
-- add       => rd = rs + rt
-- Therefore => r0 = r2 + r0

    007       :    00001000000000000000000000000101;
--                 |____||________________________|
--                   |               |             
--                 jump, Target address:address(005) 
-- Decrementing to 10
    008       :    00010000011000000000000000000000;
--                 |____||___||___||______________|
--                   |     |    |         |             
--                  beq,rs=3,rt=0,  offset to exit loop(addr:00B)

    009       :    00000000010000010010100000100010;
--                 |____||___||___||___||___||____|
--                   |     |    |    |    |    |         
--                 R-type,rs=2,rt=1,rd=5,---,f=sub 
-- sub instructions (r-type, opcode=0, funct=100010) 
-- add       => rd = rs - rt
-- Therefore => r4 = r1 - r2
    00A       :    00001000000000000000000000001000;
--                 |____||________________________|
--                   |               |             
--                 jump, Target address:address(addr:008)
-- Reloading when r0 == 10
    00B       :    10001100000000000000000000000000;
--                 |____||___||___||______________|
--                   |     |    |          |
--                   lw, rs=0, rt=0,   offset=0 
-- This is a lw instructioni. It loads r0 with data from
-- data memory location 4. Data memory location 0 is 
-- preloaded with 0, see DRAM.mif.

    00C       :    00001000000000000000000000000101;
--                 |____||________________________|
--                   |               |             
--                 jump, Target address:address(addr:005)

END;

[/代码]

下面的下一个是数据存储器mif文件

[代码]

-- Data Memory Initialization File
--

--File format:
-- Hex Address 3 hex nibbles (12 bits) : bit31 ...... bit0;

WIDTH=32;
DEPTH=1024;

ADDRESS_RADIX=HEX;
DATA_RADIX=BIN;

CONTENT BEGIN
    000       :    00000000000000000000000000000000;
    001       :    00000000000000000000000000000000;
-- 1
    002       :    00000000000000000000000000000001;
-- 10
    003       :    00000000000000000000000000001010;
-- 15
    004       :    00000000000000000000000000001111;
END;

该计划未按预期运作。它递增10然后随机递减。

请帮助。我想我没有正确编写Jump指令格式。

1 个答案:

答案 0 :(得分:0)

首先,在使用FPGA时,您还应该考虑CPU无法正常工作,尤其是在修改CPU的HDL代码时。

但是,如果您的CPU是MIPS CPU,则程序会出现以下错误:

  • 什么是“lw r0,0(r0)”指令(地址0和0xB)?在真正的MIPS芯片上,这些指令将访问地址0处的存储器,但之后什么都不做,因为在真正的MIPS芯片上,r0是只读的(它始终为0)。如果您的基于FPGA的实现应该真正实现r0作为寄存器,则不能使用“lw r0,0(r0)”来初始化r0,因为r0可能包含另一个值而不是0.在这种情况下,您必须使用类似“sub r0,r0”的内容,r0“以确保r0的值为0。
  • 地址6处的“添加r0,r0,r2”肯定不会达到预期效果 - r0硬连线为0或实现为真实寄存器。
  • 您似乎忘记了“延迟槽”:MIPS处理器执行一个周期延迟的跳转或分支指令。示例:即使地址5处的“beq”指令是分支,也会执行地址6处的“add”指令。不允许将跳转指令放入“延迟槽”(在另一个跳转指令之后放置跳转指令) - 在地址7和8中都违反了这两个指令都包含跳转指令。您还必须在地址0xC跳转后添加NOP指令(例如“add r0,r0,r0”)。初学者最好在每次跳转和分支指令后添加NOP指令,这样就可以忘记延迟时隙。
  • 您确定地址5和8中的“beq”指令是否正确编码?它们似乎跳转到地址7和0xA(或6和9 ??)而不是8和0xB。