码迷,mamicode.com
首页 > 其他好文 > 详细

OpenRisc-67-OR的汇编

时间:2014-04-29 13:33:22      阅读:474      评论:0      收藏:0      [点我收藏+]

标签:des   blog   http   使用   文件   io   

引言

之前我们写过OR的裸机程序,写过基于OR的linux设备驱动程序,也反汇编过OR的机器码。

本小节,我们将通过一个简单的实验,对OR的汇编(指令集)做一个简单的梳理和测试。


1,基本思想

要想了解OR的指令集,其实只要查查OpenRISC architecture manual就可以了,但是不是最好的熟悉方式,也没有必要将其所有指令集记下来。我认为,通过一个实际的工程或者例子,从中了解OR的指令集是比较好的一种方式。

那么,通过什么例子呢?

一般RISC的指令集包括,运算指令,分支指令,和访存指令,三类。所以我们这个实验最好能用到这三类指令,碰巧,我最近在测试DDR控制器,所以我们下面将通过一个读写内存的例子来熟悉OR的指令集。


2,实验步骤

2.1实验准备

在开始编码之前,我们首先需要考虑如下几个问题:

a,如何对汇编源程序(.S文件)进行编译,生成机器码。

b,如何加载机器码使OR的指令总线能读到。

c,如何查看机器码的执行过程和结果。


根据前面,我们积累下来的经验,可知,利用bootrom进行RTL仿真,可以很好的解决上面三个问题。并且都是自动化的。



2.2 实验步骤

在了解并解决了上面几个问题之后,剩下的就是具体的操作了。

a,修改soc-design/orpsocv2/sw/bootrom目录下的board.h


#ifndef _BOARD_H_
#define _BOARD_H_

//#define IN_CLK  	      50000000 // Hz
#define IN_CLK  	      66666667 // Hz
#define PRELOAD_RAM  
#define BOOTROM_MEM_TEST   
//
// ROM bootloader
//
// Uncomment the appropriate bootloader define. This will effect the bootrom.S
// file, which is compiled and converted into Verilog for inclusion at 
// synthesis time. See bootloader/bootloader.S for details on each option.
#ifndef PRELOAD_RAM
#define BOOTROM_SPI_FLASH
//#define BOOTROM_GOTO_RESET
//#define BOOTROM_LOOP_AT_ZERO
//#define BOOTROM_LOOP_IN_ROM
#else
	#ifdef BOOTROM_MEM_TEST
		#define BOOTROM_MEM_TEST1
	#else
		#define BOOTROM_GOTO_RESET
	#endif
#endif

// Address bootloader should start from in FLASH
// Last 256KB of 2MB flash - offset 0x1c0000 (2MB-256KB)
#define BOOTROM_ADDR_BYTE2 0x1c
#define BOOTROM_ADDR_BYTE1 0x00
#define BOOTROM_ADDR_BYTE0 0x00
// Causes SPI bootloader to loop if SPI didn‘t give correct size of image
#define SPI_RETRY_IF_INSANE_SIZEWORD

//
// Defines for each core (memory map base, OR1200 interrupt line number, etc.)
//
#define SDRAM_BASE                 0x0

#define GPIO_0_BASE         0x91000000

#define UART0_BASE  	    0x90000000
#define UART0_IRQ                    2
#define UART0_BAUD_RATE 	115200


#define SPI0_BASE           0xb0000000
#define SPI0_IRQ                     6

#define I2C_0_BASE          0xa0000000
#define I2C_0_IRQ                   10

#define I2C_1_BASE          0xa1000000
#define I2C_1_IRQ                   11

#define ETH0_BASE            0x92000000
#define ETH0_IRQ                      4

#define ETH_MACADDR0	           0x00
#define ETH_MACADDR1	           0x12
#define ETH_MACADDR2  	           0x34
#define ETH_MACADDR3	           0x56
#define ETH_MACADDR4  	           0x78
#define ETH_MACADDR5	           0x9a

//
// OR1200 tick timer period define
//
#define TICKS_PER_SEC   100

//
// CFI flash controller base
//
#define CFI_CTRL_BASE 0xf0000000

//
// UART driver configuration
// 
#define UART_NUM_CORES 1
#define UART_BASE_ADDRESSES_CSV	UART0_BASE
#define UART_BAUD_RATES_CSV UART0_BAUD_RATE


// 
// i2c_master_slave core driver configuration
//

#define I2C_MASTER_SLAVE_NUM_CORES 2

#define I2C_MASTER_SLAVE_BASE_ADDRESSES_CSV			I2C_0_BASE, I2C_1_BASE


#endif




b,修改soc-design/orpsocv2/sw/bootrom目录下的bootrom.S

这个文件,是需要我们自己手动编写OR的汇编了。

需要注意的有几点。

首先,如何让仿真自动退出:使用“l.nop 1”这条指令,具体原因可参考or1200_monitor.v文件中的相关内容。

其次,如何判断读写内存的成功与失败,分别使用“l.nop 4”和“l.nop 3”。

最后,这些汇编,都很容易理解,唯一需要注意的是OR支持延迟槽。

下面是具体代码清单:


//////////////////////////////////////////////////////////////////////
///                                                               //// 
/// bootrom      Rill 2014-04-28                                  ////
///                                                               ////
/// Assembly programs to be embedded inside system to aid boot    ////
///                                                               ////
///                                                               ////
//////////////////////////////////////////////////////////////////////

// Defines for which bootrom app to use are in board.h - TODO: use the
// processed orspoc-defines.v file for this define. It makes more sense
// as this software ends up as gates.
	
#include "board.h"


#ifdef BOOTROM_MEM_TEST1
	
#define RAM_LOAD_BASE 0x100000
#define RESET_ADDR 0x100
#define RAM_LOAD_VALUE 0x5555
#define RAM_LOAD_SIZE 0xc

boot_init:	
	l.movhi r0, 0  /*0*/
	l.movhi r1, RAM_LOAD_BASE /*1*/

mem_write:
	l.movhi r6, 0 /*2*/ /* counter*/
	l.ori r7, r0, RAM_LOAD_SIZE /*3*/
	//l.movhi	r7, RAM_LOAD_SIZE
	l.movhi r8, 0 /*4*/ /* load addr index*/
write:	
	l.ori	r3,r0, RAM_LOAD_VALUE    /*5*/    /* Read a byte into r3 */
	l.add	r8, r1, r6    /*6*/   /* Calculate store address */
	l.sw	0(r8), r3     /*7*/   /* Write byte to memory */
	l.addi	r6, r6, 4     /*8*/   /* Increment counter */
	l.sfeq 	r6, r7 		/*9*/  /* Check if we‘ve finished loading the words */
	l.bnf 	write       /*10*/  /* Continue copying if not last word */
	l.nop			/*11*/

mem_read:
	l.movhi r6, 0
	l.ori r7, r0, RAM_LOAD_SIZE
	l.movhi r8, 0
read:
	l.add	r8, r1, r6
	l.lwz	r3, 0(r8)
	l.j	check
	l.nop
read2:
	l.addi	r6, r6, 4
	l.sfeq 	r6, r7
	l.bnf 	read
	l.nop
	l.j	success
	l.nop

check:
	l.ori	r5,r0, RAM_LOAD_VALUE
	l.sfeq 	r3, r5
	l.bnf 	error
	l.nop
	l.j	read2
	l.nop

error:
	l.nop 	3
	l.j error	
	l.nop	1

success:
	l.nop	4
	l.j	success	
	l.nop	1

#endif




c,创建C语言裸机测试目录和程序

由于我们想利用ORPSoC现成的测试环境,所以我们还需要编写一个假的,只是为了满足原有的测试环境的目录和文件。

在soc-design/orpsocv2/board/xilinx/ml501/sw/tests目录下创建目录和文件:


mkdir mem
cd mem
touch mem.c
cp ../../Makefile .



编辑mem.c:


/*
* Rill
* april/28/2014
*/

int main()
{
	while(1);//we run instructions in bootrom ONLY.
	return 0;
}


由于我们只运行bootrom.S中的指令,所以mem.c里面写什么语句不重要。


d,测试与验证

完成编码之后,我们就可以运行我们刚才写的汇编程序了,方法我们之前已经介绍过多次了,这里重复如下:

在 soc-design/orpsocv2/board/xilinx/ml501/sim/run目录下执行如下:


make rtl-test TEST=mem VCD=1


很快,我们就可以仿真结束,然后,我们就可以查看仿真日志文件和仿真波形。

从中可以看出,对内存的读写都是正确的。

or1200_monitor输出的日志文件:mem-general.log


58598000.0 ps: l.nop 4 putc (U)
58718000.0 ps: l.nop exit (00005555)

mamicode.com,码迷



vcd波形文件:


mamicode.com,码迷



3,小结

对于cpu来说,对所有外设(uart,i2c,vga......)的控制都可以通过load/store来完成,和读写内存的实质是完全相同的,所以,通过上面的汇编,我们只要改变一下读写地址修改成对应外设的地址,我们就可以实现对该设备的控制了。

当然,编写出优秀的汇编程序也不是一件太容易的事情,这就需要详细阅读OR的架构手册,掌握GPR和SPR的使用方法。甚至,我们还要查看or32-elf-asm来了解更准确的OR的指令集。



OpenRisc-67-OR的汇编,码迷,mamicode.com

OpenRisc-67-OR的汇编

标签:des   blog   http   使用   文件   io   

原文地址:http://blog.csdn.net/rill_zhen/article/details/24661175

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!