ปัญหาการประกอบ TASM

1) ฉันมีโค้ด asm นี้ในไฟล์ .asm โดยพื้นฐานแล้วมันกำลังทำอะไรทำนองนี้

BEGIN


X:=2;  
Y:=2+X;
Z:=Y;

IF( Z > X ) THEN  
WRITELN("VALOR DE Z"); 
WRITELN( Z ); 
ELSE 
WRITELN("VALOR DE X"); 
WRITELN( X ); 
END; 

END programa1.

ASM ที่นี่:

   ;/StartHeader
INCLUDE macrose.mac
DOSSEG
.MODEL SMALL
STACK 100h
.DATA
            BUFFER      DB 8 DUP('$')  ;23h
            BUFFERTEMP  DB 8 DUP('$')  ;23h
            BLANCO  DB '#'
            BLANCOS DB '$'
            MENOS   DB '-$'
            COUNT   DW 0
            NEGATIVO    DB 0
            ARREGLO DW 0
            ARREGLO1    DW 0
            ARREGLO2    DW 0
            LISTAPAR    LABEL BYTE
            LONGMAX DB 254
            TOTCAR  DB ?
            INTRODUCIDOS    DB 254 DUP ('$')
                        MULT10  DW 1
                        NUM DW ?
                        X  dw ?
                        Y  dw ?
                        Z  dw ?
            T1 dw ?
            T2 dw ?
                        cadena1 db "VALOR DE Z",'$'
                        cadena2 db "VALOR DE X",'$'
.CODE
.386
BEGIN:
            MOV     AX, @DATA
            MOV     DS, AX
CALL  COMPI
            MOV AX, 4C00H
            INT 21H
COMPI  PROC
    I_ASIGNAR           2, X
    SUMAR               X, 2, T1
    I_ASIGNAR           T1, Y
    I_ASIGNAR           Y, Z
    I_MAYOR MACRO       X, Z, T2
        JF                  T2, P1
    WRITE               cadena1
    ADD                 Z, 30H
    WRITE               Z
        JMP                 Q1
P1: 
    WRITE               cadena2
    ADD                 X, 30H
    WRITE               X
Q1: 
        ret
COMPI  ENDP
END BEGIN

และเมื่อฉันพยายามเรียกใช้ใน cmd dosbox (cmd ใน win 7 จะไม่ทำงาน) ด้วย tasm file.asm ฉันมีข้อผิดพลาดเหล่านี้

คำเตือน codigo.asm() ขั้นตอนการเปิด: COMPI

ร้ายแรง codigo.asm(55) พบการสิ้นสุดไฟล์โดยไม่คาดคิด

ฉันไม่รู้ว่าทำไมเพราะฉันค่อนข้างแน่ใจว่าฉันกำลังปิดขั้นตอนและจุดเริ่มต้น นอกจากนี้บรรทัดสุดท้ายในไฟล์ของฉันคือ 54 และฉันไม่รู้ว่าทำไมถึงบอกฉันว่าปัญหาอยู่ในบรรทัดที่ 55

มาโครเหล่านี้ฉันใช้:

JF  MACRO VALOR1,DESTINO
    MOV AX,VALOR1
    CMP AX,1                   
    JNE  DESTINO

    ENDM

WRITE   MACRO MESSAGE
        PUSH AX ;EXTRA
        MOV AH, 09H
        LEA DX, MESSAGE
        INT 21H
        POP AX  ;EXTRA
    ENDM

I_ASIGNAR MACRO OPERANDO2, OPERANDO1
        PUSH AX
        MOV AX, OPERANDO2
        MOV OPERANDO1, AX
        POP AX
    ENDM

SUMAR   MACRO OPERANDO2, OPERANDO1, RESULTADO
        PUSH AX
                MOV AX, OPERANDO1
        ADD AX, OPERANDO2
        MOV RESULTADO, AX
        POP AX
    ENDM

I_MAYOR MACRO OPERANDO2, OPERANDO1, RESULTADO
    LOCAL LABEL1
    LOCAL SALIR
        PUSH AX
        MOV AX, OPERANDO1
        CMP AX, OPERANDO2
        JLE LABEL1
        MOV RESULTADO, 1
        JMP SALIR
    LABEL1:
        MOV RESULTADO, 0
    SALIR:
        POP AX
    ENDM

2) ฉันมีรหัสนี้ในรูปแบบ asm โดยพื้นฐานแล้วมันแค่ทำสิ่งที่ชอบ:

BEGIN


X:=2;  
Y:=2+X;
Z:=Y;

WRITELN("VALOR DE Z"); 
WRITELN( Z ); 


END programa1.

อัสสัมที่นี่:

;/StartHeader
INCLUDE macrose.mac
DOSSEG
.MODEL SMALL
STACK 100h
.DATA
            BUFFER      DB 8 DUP('$')  ;23h
            BUFFERTEMP  DB 8 DUP('$')  ;23h
            BLANCO  DB '#'
            BLANCOS DB '$'
            MENOS   DB '-$'
            COUNT   DW 0
            NEGATIVO    DB 0
            ARREGLO DW 0
            ARREGLO1    DW 0
            ARREGLO2    DW 0
            LISTAPAR    LABEL BYTE
            LONGMAX DB 254
            TOTCAR  DB ?
            INTRODUCIDOS    DB 254 DUP ('$')
                        MULT10  DW 1
                        NUM DW ?
                        X  dw ?
                        Y  dw ?
                        Z  dw ?
            T1 dw ?
                        cadena1 db "VALOR DE Z",'$'
.CODE
.386
BEGIN:
            MOV     AX, @DATA
            MOV     DS, AX
CALL  COMPI
            MOV AX, 4C00H
            INT 21H
COMPI  PROC
    I_ASIGNAR           2, X
    SUMAR               X, 2, T1
    I_ASIGNAR           T1, Y
    I_ASIGNAR           Y, Z
    WRITE               cadena1
    ADD                 Z, 30H
    WRITE               Z
        ret
COMPI  ENDP
END BEGIN

แต่ฉันมีปัญหาอื่น (แต่ฉันไม่มีข้อผิดพลาดของขั้นตอนการเปิด ทำไม?) ที่กำลังพิมพ์: VALOR DE Z1 VALOR DE Z

-ทำไมฉันถึงพิมพ์ "VALOR DE Z" สองครั้ง? -1 เป็นคำตอบ แต่ควรพิมพ์เฉพาะ VALOR DE Z และ 1 ไม่ใช่สองครั้ง -ฉันใช้มาโครเดียวกับที่ฉันโพสต์ และยังทำงานใน Dosbox 0.74 ด้วย

มีความคิดอะไรบ้าง? ขอบคุณนะคะ

พี.ดี. ฉันอยู่ใน dell inspiron 64 บิต n5150 intel core i7 2670Qm 2.20Ghz 6gb ram เหตุใดรูปแบบรหัสจึงไม่ทำงานในปัญหาที่ 2


person ramro93    schedule 14.12.2015    source แหล่งที่มา
comment
ฉันได้ลองแก้ไขการจัดรูปแบบโค้ดในโค้ดหยดสุดท้ายแล้ว แต่ดูเหมือนจะไม่สามารถทำให้มันติดได้   -  person David Hoelzer    schedule 15.12.2015
comment
ข้อเสนอแนะของฉันคือการลบคำถามที่ 2 เหลือเพียงคำถามที่ 1 จากนั้นถามคำถาม SO แยกต่างหากสำหรับคำถามที่ 2   -  person Michael Petch    schedule 15.12.2015
comment
ฉันคิดว่าปัญหาสำหรับคำถามของคุณ #1 คือคุณมีบรรทัดนี้ I_MAYOR MACRO X, Z, T2 ในขั้นตอน COMPI คำว่า MACRO ไม่น่าจะมีอยู่ ฉันคิดว่าคุณหมายถึง I_MAYOR X, Z, T2 ฉันคิดว่านั่นทำให้ TASM สับสนเนื่องจากคิดว่าคุณกำลังเริ่มมาโครใหม่   -  person Michael Petch    schedule 15.12.2015
comment
ถูกตัอง! ขอบคุณมาก! ฉันจะถามคำถามใหม่สำหรับฉบับที่ 2 ขอบคุณ   -  person ramro93    schedule 15.12.2015
comment
ฉันเดาว่าน่าจะเป็นข้อผิดพลาดในการคัดลอกและวาง (การพิมพ์) ในขณะที่คุณกำลังเขียนโค้ด หากเป็นกรณีนี้ ฉันจะลงคะแนนให้ปิดคำถาม #1 เพราะมันเป็นเพียงการพิมพ์ผิดจริงๆ   -  person Michael Petch    schedule 15.12.2015
comment
สำหรับคำถาม # 2 คุณไม่สามารถใช้ใน 21h/ah=09h เพื่อพิมพ์ค่าจำนวนเต็มโดยตรง คุณต้องแปลงจำนวนเต็มเป็นสตริงแล้วเรียก int 21h/ah=09h บนบัฟเฟอร์สตริงด้วยค่าที่แปลงแล้ว โดยจะพิมพ์ข้อมูลโดยเริ่มต้นที่ตำแหน่งของตัวแปร Z ตัวละครตลกๆ ที่คุณอาจแสดงบนคอนโซลคือค่า Ascii สำหรับคำใน Z จากนั้นจึงพิมพ์ T1 (ขณะมองหา $) จากนั้นดำเนินการต่อจนกระทั่งพบ การยกเลิก $ ซึ่งเกิดขึ้นที่ส่วนท้ายของสตริง cadena1 เมื่อพบ $ แล้วมันก็หยุด ดังนั้นมันจะปรากฏ cadena1 พิมพ์สองครั้ง   -  person Michael Petch    schedule 15.12.2015
comment
ขอบคุณมาก! คำถามสุดท้าย ฉันจะแปลงจำนวนเต็มเป็นสตริงโดยใช้ stringbuffer ได้อย่างไร ขอขอบคุณความช่วยเหลือ   -  person ramro93    schedule 15.12.2015
comment
อัลกอริธึมปกติคือนำค่าจำนวนเต็มมาหารด้วย 10 ส่วนที่เหลือสามารถเพิ่มลงใน ASCII '0' เพื่อแปลงตัวเลขเป็นอักขระที่สามารถพิมพ์ได้ และจัดเก็บไว้ในบัฟเฟอร์สตริง คุณหารด้วย 10 ไปเรื่อยๆ จนกว่าเงินปันผลจะเป็น 0 คุณต้องกังวลกับการกลับหลัก เนื่องจากมันจะถูกประมวลผลในลำดับที่กลับกัน คุณสามารถหาตัวอย่างเรื่องนี้ได้ทางออนไลน์หากคุณดู   -  person Michael Petch    schedule 15.12.2015
comment
เข้าใจแล้ว! ขอบคุณมาก!   -  person ramro93    schedule 15.12.2015


คำตอบ (1)


ฉันค่อนข้างแน่ใจว่า MASM ต้องการ COMPI ENDP แต่ TASM ต้องการเพียง ENDP นอกจากนี้ คุณมีคำว่า MACRO ในข้อความสั่งใดข้อความหนึ่งของคุณ:

COMPI  PROC
    I_ASIGNAR           2, X
    SUMAR               X, 2, T1
    I_ASIGNAR           T1, Y
    I_ASIGNAR           Y, Z
    I_MAYOR MACRO       X, Z, T2   ; <<<---  Remove "MACRO"
        JF                  T2, P1
    WRITE               cadena1
    ADD                 Z, 30H
    WRITE               Z
        JMP                 Q1
P1: 
    WRITE               cadena2
    ADD                 X, 30H
    WRITE               X
Q1: 
        ret
COMPI ENDP               

การดำเนินการนี้ควรแก้ไขปัญหาของคุณในคำถาม #1

person David Hoelzer    schedule 15.12.2015