代码改变世界

汇编:将以0结尾的字符串转换为大写并输出

2012-06-18 16:03  youxin  阅读(683)  评论(0编辑  收藏  举报

  编程:将'welcome-to-masm! 转成大写并输出。

要注意判断是否为小写字母,不为字母(-)就不要转换了。

assume cs:code
data segment
    db 'welcome-to-masm!',0
    
data ends
code segment
start:
     mov ax,data
     mov ds,ax
     mov si,0 ;ds:si 指向字符串
     
     call captital
     
     mov dh,12
     mov dl,0
     mov cl,2
     call show_str
    
    mov ax,4c00h
    int 21h
    

;dh 行号 dl 列号 cl颜色 
;字符串显示位置 ds:si
show_str:
     push ax
     push bx
     push cx
     push dx
     push es
     
     ;dh=(dh-1)*160
      sub dh,1
      mov al,160
      mul dh  ;商放在 ax
      mov bx,ax
      
      ;dl=(dl-1)*2
      sub dl,1
      mov al,2
      mul dl 
      add bx,ax ;必须最终为 所在首位置
      
      mov ax,0b800h
      mov es,ax
      mov di,bx
      
   s: mov al,ds:[si]
      cmp al,0
      je show_str_end
      mov es:[bx],al
      mov es:[bx+1],cl
      inc si
      add bx,2
      jmp s
      
show_str_end: pop es
         pop dx
         pop cx
         pop bx
         pop ax
         ret
         
       
captital:
         push cx
         push si 
       
    s1:  
       
          cmp [si],0
          je sret
          ;判断是否为字母,若为字母则转换
          cmp [si],'a'
          jb s2
          cmp [si],'z'
          ja s2
          
          and BYTE ptr [si],11011111b
   s2:    inc si
          jmp short s1
          
          comment /* 这个也可以 用jcxz
          mov cl,[si]
          mov ch,0
          jcxz sret
          and BYTE ptr [si],11011111b
  inc si
          jmp short s1
          */
        
      sret:
          
          pop si
          pop cx
          
          ret
                 
code ends
end start    

 

其中,

  cmp [si],'a'
   jb s2
   cmp [si],'z'
   ja s2
用于判断是否为小写字母。

但是上面的程序输出的依旧是小写字母,为什么???

在于cmp [si],'a' 没有指定传送的大小,虽然’a'占了一个字符,但编译器不知道。应加上
byte ptr ,
改为:
cmp byte ptr [si],'a'
   jb s2
   cmp byte ptr [si],'z'
   ja s2

用int7ch中断显示如下:
assume cs:code
data segment
    db 'welcome-to-masm!',0
    
data ends
code segment
start:

     mov ax,cs
     mov ds,ax
     mov si,offset show_str
     mov ax,0
     mov es,ax
     mov di,200h
     mov cx,offset show_str_end_pos-offset show_str
     cld 
     rep movsb
     

     mov ax,0
     mov es,ax
     mov WORD ptr es:[7ch*4],200h
     mov WORD ptr es:[7ch*4+2],0
     
     
     
     mov ax,data
     mov ds,ax
     mov si,0 ;ds:si 指向字符串
     
     call captital
     
     mov dh,12
     mov dl,0
     mov cl,2
     int 7ch
      
    
    mov ax,4c00h
    int 21h
    

;dh 行号 dl 列号 cl颜色 
;字符串显示位置 ds:si
show_str:
     push ax
     push bx
     push cx
     push dx
     push es
     
     ;dh=(dh-1)*160
      sub dh,1
      mov al,160
      mul dh  ;商放在 ax
      mov bx,ax
      
      ;dl=(dl-1)*2
      sub dl,1
      mov al,2
      mul dl 
      add bx,ax ;必须最终为 所在首位置
      
      mov ax,0b800h
      mov es,ax
      mov di,bx
      
   s: mov al,ds:[si]
      cmp al,0
      je show_str_end
      mov es:[bx],al
      mov es:[bx+1],cl
      inc si
      add bx,2
      jmp s
      
show_str_end: pop es
         pop dx
         pop cx
         pop bx
         pop ax
         
         iret
         
show_str_end_pos: nop

         
       
captital:
         push ax
         push cx
         push si 
       
    s1:  
       
           cmp  [si],0
          ;mov al,[si]
          je sret
          ;判断是否为字母,若为字母则转换
          cmp byte ptr [si],'a'
          jb s2
          cmp BYTE ptr [si],'z'
          ja s2
          and BYTE ptr [si],11011111b
          
   s2:    inc si
          jmp short s1
          
          comment /* 这个也可以 用jcxz
          mov cl,[si]
          mov ch,0
          jcxz sret
          and BYTE ptr [si],11011111b
          inc si
          jmp short s1
          */
        
      sret:
          
          pop si
          pop cx
          pop ax
          ret
                 
code ends
end start