【问题标题】:How to convert C++ program to Mips assembly language in MARs assembler?如何在 MAR 汇编器中将 C++ 程序转换为 Mips 汇编语言?
【发布时间】:2012-10-22 21:14:12
【问题描述】:

将C++程序转换为mips汇编语言

    #include <iostream>
    using namespace std;

    int main() {

int a = 1; 
int b = 1; 
    int array[a];
   while ( a < 10)
    {   
     array[a] = b + a;
 cout << array[a] << endl; // print elements in array //check values in array
        a +=1;
    }
      system("pause");  
    return 0;
    }

Mips 汇编语言程序

    .data
     str: .ascii "abcdef"
     array: .space 20
    .text
    main: 
     li $s0, 1 # a = 1
     li $s2, 1 # b = 1         
     loop:
     la  $t1, array
     slti $t0, $s0, 3   # t0<- 1 if a < 3
     beq $t0, $zero, exit
     sll $t0, $s0, 2    # t1<- 4*a
     add $t1, $t1, $t0  # new base addr
     add $t2, $s2, $s0  # t2<- a+b   
     sw  $t1, 0($t2)    # D[a]=a+b
     addi $s0, $s0, 1   # a = a +1
     j loop             # goes to loop: label 
     exit:
     li $v0, 10 # v0<- (exit)
     syscall 

我试过用lw, sw, lb, sb把寄存器$t2的值放到数组中,但是在Mars编译器中单步运行程序时还是会报错

更新了 Mips 汇编语言程序

     .data
     str: .ascii "abcdef"
     .align 2
     array: .space 40
     .text
     main: 
     li $s0, 1 # a = 1
     li $s2, 1 # b = 1
     loop:
     la  $t1, array
     slti $t0, $s0, 3   # t0<- 1 if a < 3
     beq $t0, $zero, exit
     sll $t0, $s0, 2   # t1<- 4*a
     addu $t2, $t1, $t0 # new base addr
     add $s1, $s0, $s2 # s1<- a+b
     sw  $s1, 0($t2)   # D[a]=a+b

     li  $v0, 1        # load appropriate system call code into register $v0;
               # code for printing integer is 1
     lw $a0, 0($t0)
     addiu $t0, $t0, 4
     syscall           # call operating system to perform print operation

     addi $s0, $s0, 1  # a = a +1
     j loop            # goes to loop: label          
     exit:
     li $v0, 10 # v0<- (exit)
     syscall

我运行这个程序,我得到这个错误:“地址超出范围 0x00000004” 我想打印我的数组的值来检查它是否正确。

【问题讨论】:

    标签: assembly mips mips32


    【解决方案1】:

    您的代码中有几个错误。 关于数组中项的存储,必须将数组的基地址与索引相加(乘以4)才能得到要存储的项的地址。

    假设$s0 持有a,$s2 持有b,要存储D[a] = a + b,您将:

    la $t1, array
    sll $t0, $s0, 2
    addu $t2, $t1, $t0  # $t2 is &D[a]
    add $s1, $s0, $s2    # $s1 = a + b
    sw $s1, 0($t2)  # D[A] = a + b
    

    请注意,您没有保留足够的内存来保存数组 D 中的 10 个项目,假设 int 是 32 位宽,那么每个项目是 4 个字节长,因此您应该保留 40 个字节...

    您还应该确保数组在单词边界处正确对齐。为此,您可以指示汇编器使用 .align 2 指令为您进行对齐,例如:

    .align 2
    array: .space 40
    

    【讨论】:

    • 谢谢,但我认为“addiu”命令用于:寄存器、寄存器、整数?当我使用“addiu”时出现此错误:“$t0”:操作数的类型不正确。此外,当我将“add”或“addu”命令替换为“addiu”时,我收到以下错误:“0x00400024 处的运行时异常:存储地址未在字边界 0x1001000a 上对齐”
    • @user1757759:是的,应该是addu(添加无符号)。关于您收到的错误,我添加了一些有关它的信息。您必须使用 .align 指令对齐数组
    • 还有一个问题,如何打印数组中的值以像在 c++ preogram 中那样进行检查? li $v0, 1 la $a0, array syscall
    • @user1757759:您必须遍历读取每个整数的数组才能打印它们。假设$t0 指向当前项目的地址,你会做li $v0, 1 lw $a0, $t0(0) syscall 然后addiu $t0, $t0, 4 将指针$t0 移动到下一个元素
    • 你正在执行 'lw $a0, 0($t0)' 这是错误的,因为 $t0 包含值 4
    【解决方案2】:
    intN;
    cout<<"Enter the array size: ";
    cin>>N; //size must be less than MAX_SIZE
    
    int one[MAX_SIZE]; 
    int two[MAX_SIZE]; 
    cout<<"Ente the elements of array one:"<<endl;
    for(inti = 0; i<N;i++)
        cin>>one[i];
    
    cout<<"Ente the elements of array two:"<<endl;
    for(inti = 0; i<N;i++)
        cin>>two[i];
    
    int result = compare(one,two,N);
    
    if(result == 0)
        cout<<"Array one is Equal to array two"<<endl;
    elseif(result==-1)
        cout<<"Array one is less than array two"<<endl;
    elseif(result==1)
        cout<<"Array one is greater than array two"<<endl;
    

    【讨论】:

    • 嗨 @user4749717,欢迎来到 StackOverflow。 OP 希望他们的“C++ 程序被转换为 mips 汇编语言”,但你已经回答了一些 C++ 代码,这不是所寻求的。如果您有答案,请重新阅读问题并相应地更新您的答案。
    猜你喜欢
    • 2021-08-22
    • 2019-08-03
    • 2013-11-21
    • 1970-01-01
    • 2014-08-16
    • 1970-01-01
    • 2020-07-28
    • 2016-12-22
    • 1970-01-01
    相关资源
    最近更新 更多