Assembly MIPS使用位移位运算符以二进制形式打印十进制
我在这里和网上的其他地方读过很多关于这个话题的帖子。关于位移位的伟大主题(不一定与汇编有关,但通常的主题是:我已经在这里复制和粘贴了OP中的代码:并进行了回复者建议的更改,并且无论我做什么,我都会继续生成一个零字符串 我理解什么是位移位以及它是如何工作的。向右移位除以“n”将数字除以2^n,向左移位将数字乘以2^n 上周我有一个实验室,它的第三部分是提供一个程序,该程序将接受用户输入,打印出二进制版本,然后是十六进制版本。一旦完成,该程序将打印出字符串中心的某些位,并生成二进制和十六进制版本嗯 我最初的想法是获取字符串,并将其与0x01一起打印结果“1”或“0”,然后将其右移“1”。这包含在一个循环中,并将继续进行,直到我的计数器满足“32”要求并使用它。但我非常困惑它为什么会打印所有“0”。我尝试了其他版本,例如:Assembly MIPS使用位移位运算符以二进制形式打印十进制,assembly,mips,bit,bit-shift,Assembly,Mips,Bit,Bit Shift,我在这里和网上的其他地方读过很多关于这个话题的帖子。关于位移位的伟大主题(不一定与汇编有关,但通常的主题是:我已经在这里复制和粘贴了OP中的代码:并进行了回复者建议的更改,并且无论我做什么,我都会继续生成一个零字符串 我理解什么是位移位以及它是如何工作的。向右移位除以“n”将数字除以2^n,向左移位将数字乘以2^n 上周我有一个实验室,它的第三部分是提供一个程序,该程序将接受用户输入,打印出二进制版本,然后是十六进制版本。一旦完成,该程序将打印出字符串中心的某些位,并生成二进制和十六进制版本嗯
- 将用户输入向左移动31,然后对每个位执行循环,但在循环中它向右移动(以弥补位的相反顺序)-失败-再次全部为零
- 做与上面相反的事情-再次失败,全部为零
(NOT CODE OBVIOUSLY)
User input is: 25 <-- store at $t0
Binary rep is: 0000 0000 0000 0000 0000 0000 0001 1001 # 25 in $t0
LOOP:
AND with 0x01: 0000 0000 0000 0000 0000 0000 0000 0001 #saved to $t1
Produces: 0000 0000 0000 0000 0000 0000 0000 0001 #saved to $t2
Print to Console: 1 #send contents of $t2 to syscall
Shift $t0 Right 1: 0000 0000 0000 0000 0000 0000 0000 1100 #
j LOOP (until the beq branch was met and I left the loop)
这是一种与基本方法稍有不同的方法。它将二进制输出和十六进制输出视为通用输出函数的参数。位屏蔽/位移位类似,但掩码和位宽度是可变的
# Read integer A from user and store it into a register
# Display the integer in binary
# Display the integer in Hex
# set Register $a0 to contain only bits 12,13,14,15 of $a0
# Display the integer in binary contained in $a0
# Display the integer in hex contained in $a0
.data
userInput: .asciiz "Please enter your integer: "
binaryInput: .asciiz "Here is the input in binary: "
nl: .asciiz "\n"
hexInput: .asciiz "Here is the input in hexadecimal: "
binaryOutput: .asciiz "Here is the output in binary: "
hexOutput: .asciiz "Here is the output in hexadecimal: "
hexDigit: .asciiz "0123456789ABCDEF"
obuf: .space 100
obufe:
.text
.globl main
main:
# ask end-user to submit an integer value
li $v0,4
la $a0,userInput
syscall
# read user-input
li $v0,5
syscall
move $s0,$v0
# output original in binary
la $a0,binaryInput
li $a1,32
jal prtbin
# output original in hex
la $a0,hexInput
li $a1,32
jal prthex
# isolate bits 12,13,14,15
srl $s0,$s0,12
andi $s0,$s0,0x0F
# output isolated in binary
la $a0,binaryOutput
li $a1,4
jal prtbin
# output isolated in hex
la $a0,hexOutput
li $a1,4
jal prthex
# exit the program
li $v0,10
syscall
# prtbin -- print in binary
#
# arguments:
# a0 -- output string
# a1 -- number of bits to output
prtbin:
li $a2,1 # bit width of number base digit
j prtany
# prthex -- print in hex
#
# arguments:
# a0 -- output string
# a1 -- number of bits to output
prthex:
li $a2,4 # bit width of number base digit
j prtany
# prtany -- print in given number base
#
# arguments:
# a0 -- output string
# a1 -- number of bits to output
# a2 -- bit width of number base digit
# s0 -- number to print
#
# registers:
# t0 -- current digit value
# t5 -- current remaining number value
# t6 -- output pointer
# t7 -- mask for digit
prtany:
li $t7,1
sllv $t7,$t7,$a2 # get mask + 1
subu $t7,$t7,1 # get mask for digit
la $t6,obufe # point one past end of buffer
subu $t6,$t6,1 # point to last char in buffer
sb $zero,0($t6) # store string EOS
move $t5,$s0 # get number
prtany_loop:
and $t0,$t5,$t7 # isolate digit
lb $t0,hexDigit($t0) # get ascii digit
subu $t6,$t6,1 # move output pointer one left
sb $t0,0($t6) # store into output buffer
srlv $t5,$t5,$a2 # slide next number digit into lower bits
sub $a1,$a1,$a2 # bump down remaining bit count
bgtz $a1,prtany_loop # more to do? if yes, loop
# output string
li $v0,4
syscall
# output the number
move $a0,$t6 # point to ascii digit string start
syscall
# output newline
la $a0,nl
syscall
jr $ra # return
这是一种与基本方法稍有不同的方法。它将二进制输出和十六进制输出视为通用输出函数的参数。位屏蔽/位移位类似,但掩码和位宽度是可变的
# Read integer A from user and store it into a register
# Display the integer in binary
# Display the integer in Hex
# set Register $a0 to contain only bits 12,13,14,15 of $a0
# Display the integer in binary contained in $a0
# Display the integer in hex contained in $a0
.data
userInput: .asciiz "Please enter your integer: "
binaryInput: .asciiz "Here is the input in binary: "
nl: .asciiz "\n"
hexInput: .asciiz "Here is the input in hexadecimal: "
binaryOutput: .asciiz "Here is the output in binary: "
hexOutput: .asciiz "Here is the output in hexadecimal: "
hexDigit: .asciiz "0123456789ABCDEF"
obuf: .space 100
obufe:
.text
.globl main
main:
# ask end-user to submit an integer value
li $v0,4
la $a0,userInput
syscall
# read user-input
li $v0,5
syscall
move $s0,$v0
# output original in binary
la $a0,binaryInput
li $a1,32
jal prtbin
# output original in hex
la $a0,hexInput
li $a1,32
jal prthex
# isolate bits 12,13,14,15
srl $s0,$s0,12
andi $s0,$s0,0x0F
# output isolated in binary
la $a0,binaryOutput
li $a1,4
jal prtbin
# output isolated in hex
la $a0,hexOutput
li $a1,4
jal prthex
# exit the program
li $v0,10
syscall
# prtbin -- print in binary
#
# arguments:
# a0 -- output string
# a1 -- number of bits to output
prtbin:
li $a2,1 # bit width of number base digit
j prtany
# prthex -- print in hex
#
# arguments:
# a0 -- output string
# a1 -- number of bits to output
prthex:
li $a2,4 # bit width of number base digit
j prtany
# prtany -- print in given number base
#
# arguments:
# a0 -- output string
# a1 -- number of bits to output
# a2 -- bit width of number base digit
# s0 -- number to print
#
# registers:
# t0 -- current digit value
# t5 -- current remaining number value
# t6 -- output pointer
# t7 -- mask for digit
prtany:
li $t7,1
sllv $t7,$t7,$a2 # get mask + 1
subu $t7,$t7,1 # get mask for digit
la $t6,obufe # point one past end of buffer
subu $t6,$t6,1 # point to last char in buffer
sb $zero,0($t6) # store string EOS
move $t5,$s0 # get number
prtany_loop:
and $t0,$t5,$t7 # isolate digit
lb $t0,hexDigit($t0) # get ascii digit
subu $t6,$t6,1 # move output pointer one left
sb $t0,0($t6) # store into output buffer
srlv $t5,$t5,$a2 # slide next number digit into lower bits
sub $a1,$a1,$a2 # bump down remaining bit count
bgtz $a1,prtany_loop # more to do? if yes, loop
# output string
li $v0,4
syscall
# output the number
move $a0,$t6 # point to ascii digit string start
syscall
# output newline
la $a0,nl
syscall
jr $ra # return
用户输入为25的断言-这是作为输入输入并作为字符串输入的,还是作为实际值传递给您的函数?如果作为字符串传递,您需要首先对其进行一些转换,以将其从字符串转换为整数。接下来,print函数要用字符串还是数字?我猜是字符串,在这种情况下您需要d将“0”添加到二进制值中,以便正确打印。
la$a0,($s2)
真的很奇怪。la
应该像一个li
,但数字的上半部分是0x1001。我很惊讶这个偶数组合起来了,我想知道它组合成了什么。@MichaelDorgan嗯,好问题!整数是用户输入,我在代码中读作li$v0,5
。在循环的第3行
我正在打印整数值。我以为这会起作用?删除sll
(这只会丢弃大部分位),删除la$a0,($s2)
(我不知道这会导致什么结果,但可能不是正确的做法),将和I
的结果写入$a0
,也许这样做了,但我没有测试它当然会让一个非零数进入该循环?用户输入是25的断言-这是作为输入输入并作为字符串输入的,还是作为实际值传递给函数的?如果作为字符串传递,您需要首先对其进行一些转换,将其从字符串转换为整数。接下来,打印函数需要字符串还是数字?我是猜测字符串,在这种情况下,您需要将“0”添加到二进制值中,以便正确打印。la$a0,($s2)
真的很奇怪。la
应该像一个li
,但数字的上半部分是0x1001。我很惊讶这个偶数组合起来了,我想知道它组合成了什么。@MichaelDorgan嗯,好问题!整数是用户输入,我在代码中读作li$v0,5
。在循环的第3行
我正在打印整数值。我以为这会起作用?删除sll
(这只会丢弃大部分位),删除la$a0,($s2)
(我不知道这会导致什么结果,但可能不是正确的做法),将和I
的结果写到$a0
,也许这样做了,但我当然没有测试过它。那么一个非零的数字会进入循环吗?谢谢Craig Estey!我已经运行了几次,它似乎工作得很好。我需要在有机会的时候剖析你的代码,因为我们刚刚了解了你正在做的跳跃就在一天前,我还学习了如何传递论点。subu
对我来说也是一门新的课程。但这对我来说是一门关于这些主题的优秀速成课程。哈罗德,如果你最初给我的帮助,我会给你更多的分数。不幸的是,我所能做的就是把你的答案投到我最初的帖子上。对不起,伙计,我真的很抱歉感谢您抽出时间查看我的开始代码,并指出我出错的某些方面。谢谢Craig Estey!我已经运行了几次,它似乎工作得很好。我需要在有机会时剖析您的代码,因为我们刚刚了解了您一天前所做的跳跃,以及如何通过argumen谢谢你。subu
对我来说也是新的。但这对我来说是一个很好的关于这些主题的速成课程。哈罗德,如果你最初给我的帮助,我会给你更多的分数。不幸的是,我所能做的就是更新你对我最初帖子的回复。对不起,伙计,但我真的很感谢你抽出时间查看我的帖子开始编写代码并指出我出错的某些方面。