龙芯下汇编语言编程(1)

来源:互联网 发布:轩辕世界神兽数据 编辑:程序博客网 时间:2024/05/02 04:54

作者: comcat 发表日期: 2007-03-22 11:20          http://comcat.blog.openrays.org/blog.php?do=showone&tid=310

 

1. Hello World

从经典的Hello World开始:

.text #表示将后面的代码编译后置于目标文件的.text段
.globl main #声明main为全局变量。该变量名会置于符号表中
.ent main #告诉汇编器main函数在此开始,调试用

main: #标号,表示main函数的始地址,有实际意义
lui $4, %hi(cmd) #Load Upper Immediate
addiu $4, $4, %lo(cmd) #execve的第一个参数置于a0, 为字符串/bin/echo的首地址

lui $5, %hi(argv) #%hi, %lo为汇编器定义的宏,分别求地址的高16和低16位
addiu $5, $5, %lo(argv) #execve的第二个参数置于a1, 为字符指针数组的首地址

move $6, $0 #第三个参数a2为0 (NULL)
li $2, 4011 #将execve系统调用号置入v0寄存器
syscall #系统调用

move $2, $0 #main的返回值0, 置于v0
jr $31 #main返回

.end main #告诉汇编器main在此结束,调试用


.data #以下内容位于目标文件的数据段

cmd:
.asciiz "/bin/echo"

msg:
.asciiz "Hello world!"

argv:
.word cmd # /bin/echo的首地址
.word msg # Hello world!的首地址
.word 0x0 # NULL


存为helloworld.s,gcc helloworld.s -o hw 编译之,执行结果:

Hello world!


2. 带立即数的指令

汇编或机器语言中,称指令中的常数为立即数(Immediate)

上面的例子我们看到这些指令:lui, li, addiu

lui: Load Upper Immediate, 加载立即数到寄存器的高16位

lui t0, 0xaa55 # t0 = 0xaa55 0000
addiu t0, t1, 64 # t0 = t1 + 64,为无符号相加

带立即数的指令,指令编码格式属于I-型,回忆下其格式: 6, 5, 5, 16 预留给立即数的空间是16位,因此指令中的立即数范围,无符号为0~2^16-1, 有符号为-2^15~2^15-1

如果超过范围,可以先用 li 将立即数置入寄存器,然后使用add运算


3. li (Load Immediate)

li (Load Immediate) 没有16位的限制,因为它不是单一的一条指令,而是由汇编器定义的一个“复合”指令,一般称其为宏指令。

常见情况下,li的展开:

li t0, -5 -----> addiu t0, zero, -5

li t0, 0x8000 -----> ori t0, t0, 0x8000

li t0, 0x12345 -----> lui t0, 0x1
ori t0, t0, 0x2345

4. 龙芯下,系统调用的约定

v0: 用于置系统调用号
a0~a3: 置前四个参数,后面的参数用栈传
syscall 系统调用触发指令
返回值依旧使用v0接收


原创粉丝点击