汇编:实验10三题

Posted 小杰666

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了汇编:实验10三题相关的知识,希望对你有一定的参考价值。

1、显示字符串

题目:

汇编源码:

; 实验10.1
; 屏幕指定位置显示指定颜色的字符串

assume cs:code
data segment
    db 'Welcome to masm!',0
data ends

stack segment
    dw 8 dup (0)
stack ends

code segment
start:
    mov dh,8        ; 行号 0-24
    mov dl,3        ; 列号 0-79
    mov cl,2        ; 颜色 绿色
    mov ax,data
    mov ds,ax
    mov si,0        ; ds:si指向字符串开头
    mov ax,stack
    mov ss,ax
    mov sp,10h      ; 函数相关栈
    push cx
    push dx
    call show_str

    mov ax,4c00h
    int 21h

; 参数为 行号dh 列号dl 颜色cl
show_str:
    ; 寄存器保存
    push bp
    mov bp,sp
    push di
    push si
    push ax
    push es
    
    ; 显存起始地址段地址
    mov ax,0b800h 
    mov es,ax

    ; 显存中字符的开始地址
    mov al,160      ; 每行字节数
    mul byte ptr [bp+5]
    mov dl,[bp+4]
    mov dh,0
    add ax,dx
    add ax,dx
    mov di,ax

fill:
    mov cl,[si]     ; 字符
    mov ch,0
    jcxz ok
    mov ch,[bp+6]   ; 颜色
    mov es:[di],cx
    add di,2
    inc si
    jmp fill
ok:
    ; 寄存器恢复
    pop es
    pop ax
    pop si
    pop di
    pop bp
    ret

code ends
end start

编译执行结果:

2、解决除法溢出问题

题目:

汇编源码:

; 实验10.2
; 解决除法的商的溢出问题
; 公式:X/N = int(H/N)*65536 + [rem(H/N)*65536+L]/N
; 公式是二项式,第一项得出整个除法的商的高16位,65536不用真的乘
; 第二项得出整个除法的商的低16位,而余数是整个除法的余数
; 题目中除数0a,整个除法余数是0,不好验证,这里使用除数0b
assume cs:code
stack segment
    dw 8 dup (0)
stack ends

code segment
start:
    mov ax,stack
    mov ss,ax
    mov sp,10h

    mov ax,4240h        ; 被除数低16
    mov dx,000fh        ; 被除数高16
    mov cx,0bh          ; 除数
    push cx
    push dx
    push ax
    call divdw
    
    mov ax,4c00h
    int 21h

divdw:
    push bp
    mov bp,sp
    push bx

    ; int(H/N)
    mov dx,0
    mov ax,[bp+6]
    div word ptr [bp+8]
    mov bx,ax           ; 商的高16位,dx里是余数,不用动

    ; [rem(H/N)*65536+L]/N
    ; rem(H/N)*65536 表示余数放在高16位,刚好是dx
    ; +L 则为被除数低16位,放到ax里,作为新除法被除数的低16位
    mov ax,[bp+4]
    div word ptr [bp+8]
    mov cx,dx       ; cx为余数
    mov dx,bx       ; dx为商的高16位,ax为商的低16位

    pop bx
    pop bp
    ret

code ends
end start
; 以上,在win2k的dos下用debug执行exe会无效指令,退出dos。可以用dosbox执行。

执行结果:

3、数值显示

题目:

汇编源码:

; 将数据以十进制形式显示
assume cs:code

data segment
    db 10 dup (0)
data ends

stack segment
    dw 8 dup (0)
stack ends

swap segment
    dw 10 dup (0)
swap ends

code segment
start:
    mov ax,12666
    mov bx,data
    mov ds,bx
    mov si,0
    mov bx,stack
    mov ss,bx
    mov sp,10h
    call dtoc

    mov bx,swap
    push ss
    mov ss,bx
    push sp
    mov sp,20
    call turn
    pop sp
    pop ss

    mov dh,8
    mov dl,3
    mov cl,2
    push cx
    push dx
    call show_str

    mov ax,4c00h
    int 21h

dtoc:
    push cx
    push si
    push bx
s:
    mov dx,0        ; 被除数dx:ax
    mov bx,10
    div bx
    mov cx,ax       ; 商ax
    add dx,30h      ; 余数+30h
    mov [si],dl
    jcxz oks
    mov ax,cx
    inc cx
    inc si
    jmp s
oks:
    pop bx
    pop si
    pop cx
    ret

; 参数为 行号dh 列号dl 颜色cl
show_str:
    ; 寄存器保存
    push bp
    mov bp,sp
    push di
    push si
    push ax
    push es
    
    ; 显存起始地址段地址
    mov ax,0b800h 
    mov es,ax

    ; 显存中字符的开始地址
    mov al,160      ; 每行字节数
    mul byte ptr [bp+5]
    mov dl,[bp+4]
    mov dh,0
    add ax,dx
    add ax,dx
    mov di,ax

fill:
    mov cl,[si]     ; 字符
    mov ch,0
    jcxz okf
    mov ch,[bp+6]   ; 颜色
    mov es:[di],cx
    add di,2
    inc si
    jmp fill
    
okf:
    ; 寄存器恢复
    pop es
    pop ax
    pop si
    pop di
    pop bp
    ret

; 字符串顺序翻转
turn:
    push ax
    push cx
    push si

turn_s:
    mov cl,[si]
    mov ch,0
    jcxz oks2
    push cx
    inc si
    mov cx,2
    jmp turn_s

oks2:
    mov cx,si
    mov si,0
ok_s:
    pop ax
    mov [si],al
    inc si
    loop ok_s

    pop si
    pop cx
    pop ax
    ret

code ends
end start
; 以上,在win2k的dos下用debug执行exe会无效指令,退出dos。可以用dosbox执行

执行结果:

以上是关于汇编:实验10三题的主要内容,如果未能解决你的问题,请参考以下文章

汇编:实验13三题

实验五

《软件测试》课程实验2第三题

2017-2018-2 20179225 《网络攻防与实践》 第10周作业

汇编实验3

王爽 汇编 实验10.1