Последовательности символов, входящих в строку и расположенных в алфавитном или обратном алфавитному порядках - Assembler

Формулировка задачи:

Вывести на экран последовательности символов, входящих в строку и расположенных в алфавитном или обратном алфавитному порядках. Длина минимальной такой последовательности – 3 символа. Каждую имеющуюся последовательность выводить на экран с новой строки. Мой код в спойлере. Ошибка заключается в том, что в обратном алфавитном порядке выводит немного неправильно. Помогите исправить.
.DATA
String_1        db      40 dup(20h)
String_2        db      40 dup(20h)
Index_H         dw      0000h
Buffer          dw      0000h
Index_L         dw      0000h        
In_Put          db      "Vvedite stroku, sostojawuu iz bukv v kolichesve ot 30 do 40 sivolov:",0Dh,0Ah,"$"
Symbol_Bad_s    db      0Dh,0Ah,"Vvedenno malo simvolov$"
Clear           db      62  dup(20h),"$"  
Enter           db      0Dh,0Ah,"$"
V_p             db      0Dh,0Ah,"V Prjamom porjadke:","$"
O_p             db      0Dh,0Ah,"V Obratnom porjadke:","$"
N_p             db      0Dh,0Ah,"Elementy udovl. poisku otsutstvujut","$"
Konec           db      0Dh,0Ah,"Konec. Click ENTER","$"    
Count           dw      0000h        
.STACK  256
.CODE
start:
    mov     AX,@DATA
    mov     DS,AX
    mov     ES,AX
    mov     DI,offset   String_1    
    mov     DX,offset In_Put
    mov     AH,09h                                                                          
    int     21h  
    mov     CX,40      
InPut_Data:  
    xor     AH,AH                      ; Chtenie nagatoj klavishi
    int     16h    
    cmp     AL,0Dh                     ; Natat li ENTER?
    jz      Symbol_Bad      
; Proverka diapozona    
    cmp     AL,7Bh
    lahf    
    not     AH
    xchg    AH,DH
    cmp     AL,61h
    lahf    
    or      AH,DH
    sahf
    jns     Indi                       ; Esli vvedennyje dannye in[a..z]
    cmp     AL,5Bh
    lahf    
    not     AH
    xchg    AH,DH
    cmp     AL,41h
    lahf    
    or      AH,DH
    sahf
    jns     Indi                       ; Esli vvedennyje dannye in[A..Z]    
; Vyvod oshibki na ekran
Symbol_Bad_PP:
    push    CX
    mov     AH,03h                     ; Nahojdenie pozicii kursora
    int     10h
    push    DX
    mov     DX,offset Symbol_Bad_s     ; vyvod stroki oshibki
    mov     AH,09h    
    int     21h
exit:    
    xor     AH,AH                      ; [AH=00h\ INT 16h] ==> ctenie najatpj klavishi  
    int     16h
    cmp     AL,0Dh                     ; Zaderjka do najatija Enter
    jnz     exit                      
    mov     AH,02h                     ; Peremeshenie kursora na nachalo stroki
    mov     DX,0200h
    int     10h    
    mov     DX,offset Clear            ; Ochistka stroki oshibki
    mov     AH,09h    
    int     21h
    pop     DX                         ; Peremeshenie kursora na konec vvedennoj stroki
    mov     AH,02h
    int     10h
    pop     CX
    inc     AH
    jmp     Symbol_Bad
Indi:    
    mov     AH,0Eh                     ; Vyvod vvedennoj stroki na ekran (Teletayp)
    int     10h
    stosb                              ; Zagruzka v stroku vvedennogo simvola
    inc     Count
Symbol_Bad:
    cmp     Count,30
    jle     InPut_Data
    cmp     Count, 40
    jz      Next
    cmp     AL,0Dh
    jnz     InPut_Data        
next:    
    mov     SI,offset String_1
    mov     DI,offset String_2
    mov     CX,Count
Write:    
    lodsb
    cmp     AL,61h
    jae     small                           ; big_Let ==> small_Let
    add     AL,20h
small:          
    stosb
    loop    Write
    mov     SI,offset   String_2            ; Zagruzka adresa pervogo simvola
    mov     DI,offset   String_2+1          ; Zagruzka adresa vtorogo simvola
    mov     CX,Count  
    cld    
    mov     DX,offset V_p
    mov     AH,09h    
    int     21h      
loads:
    lodsb   ;AL,[SI]                        ; Poisk posledovatelnosni iz 2 simvolov v alfov. porjadke
    inc     AL
    scasb   ;[DI+1];AL
    loopnz  loads
    xor     CX,0
    jz      exit_
    mov     Index_L,SI                      ; Sohranenie pervogo elementa v alfov. porjadke
re_loads:                                   ; poisk poslednego elementa v alfov porjadke
    lodsb
    inc     AL
    scasb
    loopz   re_loads
    mov     Index_H,SI                      ; Sohranenie adresa poslednego elementa
    mov     Buffer,SI
    sub     SI,Index_L
    cmp     SI,2                            ; kol-vo simvolov v alfov. porjadke
    jb      prov                            ; Proverka (ne menee 3 simvolov)
    mov     DX,offset Enter
    mov     AH,09h    
    int     21h
    push    CX
    inc     SI                            
    mov     CX,SI
    mov     AH,0Eh
    mov     SI,Index_L
    sub     SI,41
write_skrin:    
    lodsb                                    ; vyvedenie simvolov
    int     10h
    loop    write_skrin
    pop     CX
prov:
    mov     SI,Index_H  
    xor     CX,0
    jnz     loads  
exit_:      
    xor     Index_L,0
    jnz     indicir
    mov     DX,offset N_p                    ; esli net elementov, udovletvor. poisku
    mov     AH,09h    
    int     21h
indicir:      
    mov     Index_H,0                        ; Obnulenie Index_H
    mov     SI,offset   String_2-1           ; Zagruzka adresa poslednego elementa
    add     SI,Count
    mov     DI,SI
    dec     DI  
    mov     CX,Count
    std  
   
   
   
; V obratnom porjadke:    
    mov     DX,offset O_p
    mov     AH,09h    
    int     21h  
   
loads_:
    lodsb   ;AL,[SI]
    inc     AL
    scasb   ;[DI+1];AL
    loopnz   loads_
    xor     CX,0
    jz      exit__
    mov     Index_H,SI
    inc     Index_H  
re_loads_:    
    lodsb
    inc     AL
    scasb
    loopz   re_loads_
    mov     Index_L,SI
    mov     Buffer,SI
    mov     SI,Index_H  
    sub     SI,Index_L
    cmp     SI,3
    jb      prov_
    mov     DX,offset Enter
    mov     AH,09h    
    int     21h
    push    CX
    mov     CX,SI
    mov     AH,0Eh
    mov     SI,Index_H
    sub     Si,40
write_skrin_:    
    lodsb
    int     10h
    loop    write_skrin_
    pop     CX
prov_:
    mov     SI,Buffer  
    xor     CX,0
    jnz     loads_  
exit__:
    xor     Index_H,0
    jnz     indicir_      
    mov     DX,offset N_p
    mov     AH,09h    
    int     21h
indicir_:
    mov     DX,offset Konec
    mov     AH,09h    
    int     21h
_exit:    
    xor     AH,AH                    
    int     16h
    cmp     AL,0Dh
    jnz     _exit  
    mov     AX,4C00h
    int     21h
       
end start
ends

Код к задаче: «Последовательности символов, входящих в строку и расположенных в алфавитном или обратном алфавитному порядках - Assembler»

textual
.model small
.data
    InpBuff db  30, 0, 30 dup ('$')
    Kol db  "Введите строку: ",'$'
    Vpyam   db  "По возрастанию: ","$"  
    vobr    db  "По убыванию: ","$"
 
.stack  256
 
newstr  macro
    call    DispCrLf
    endm
dosstr  macro   aStr:REQ
    mov dx, offset aStr
    call    DispDt
    endm
 
.code
start   PROC    NEAR
    mov ax, @data
    mov ds, ax
    mov es, ax      
 
    dosstr  Kol
    newstr
    lea dx, InpBuff
    mov ah, 0ah
    int 21h
    newstr
   
    dosstr  vpyam
    newstr
 
    xor cx, cx
    mov si, offset InpBuff+2
    mov di, offset IsDirSeq
    mov cl, [si-1]
    call    SearchSequence
 
    dosstr  vobr
    newstr
 
    mov di, offset IsRevSeq
    call    SearchSequence
@@exit:
    mov ax, 4c00h ; exit to operating system.
    int 21h        
start   ENDP
;---------------------------
SearchSequence  PROC    NEAR
; OnEnter:
;   DS:SI-> string where look for sequence
;   CX=StrLength
;   CS:DI-> seearch sequence subrouting
; OnExit:
;   AX=seqence length
    push    ax
    push    cx
    push    si
@@loop:
    call    di
    test    ax, ax
    jz  @@end_of_str
    cmp ax, 3
    jb  @@2next
    call    OutStrLen
    call    DispCrLf
@@2next:
    add si, ax
    sub cx, ax
    jnz @@loop
@@end_of_str:
    pop si
    pop cx
    pop ax
    ret
SearchSequence  ENDP
;---------------------------
IsDirSeq    PROC    NEAR
; OnEnter:
;   DS:SI-> string where look for sequence
;   CX=StrLength
; OnExit:
;   AX=seqence length
;
    push    cx
    push    dx  ; seq cnt
    push    si
    xor dx, dx
    jcxz    @@exit
    cld
    inc dx
    lodsb
    dec cx
    jz  @@exit
@@loop:
    inc al
    mov ah, al
    lodsb
    cmp al, ah
    jne @@exit
    inc dx
    dec cx
    jnz @@loop
@@exit:
    mov ax, dx
    pop si
    pop dx
    pop cx
    ret
IsDirSeq    ENDP
;---------------------------
IsRevSeq    PROC    NEAR
; OnEnter:
;   DS:SI-> string where look for sequence
;   CX=StrLength
; OnExit:
;   AX=seqence length
;
    push    cx
    push    dx  ; seq cnt
    push    si
    xor dx, dx
    jcxz    @@exit
    cld
    inc dx
    lodsb
    dec cx
    jz  @@exit
@@loop:
    dec al
    mov ah, al
    lodsb
    cmp al, ah
    jne @@exit
    inc dx
    dec cx
    jnz @@loop
@@exit:
    mov ax, dx
    pop si
    pop dx
    pop cx
    ret
IsRevSeq    ENDP
;---------------------------
OutStrLen   PROC    NEAR
; OnEnter:
;   DS:SI -> str to display
;   AX -> str length
    push    ax
    push    cx
    push    dx
    push    si
 
    mov cx, ax
    cld
    jcxz    @@exit
@@loop:
    lodsb
    mov ah, 2
    mov dl, al
    int 21h
    loop    @@loop
 
@@exit:
    pop si
    pop dx
    pop cx
    pop ax
    ret
OutStrLen   ENDP
;---------------------------
DispCrLf    PROC    NEAR
    push    ax
    push    dx
    mov dl, 0dh
    mov ah, 2
    int 21h
    mov dl, 0ah
    mov ah, 2
    int 21h
    pop dx
    pop ax
    ret
DispCrLf    ENDP
;---------------------------
DispDt  PROC    NEAR
    push    ax
    mov ah, 9
    int 21h
    pop ax
    ret
DispDt  ENDP
;---------------------------
    end start

11   голосов, оценка 4.364 из 5


СОХРАНИТЬ ССЫЛКУ