assembly emu8086组装中的“摄魂师”游戏

yb3bgrhw  于 2023-02-08  发布在  其他
关注(0)|答案(1)|浏览(126)

我有一个问题,我的代码。它总是说它有双重声明的代码,我不知道如何修复它。无论我合并段或离开他们像这样说同样的事情。(我也不是真的知道很多关于这个程序。我们在学校做的,所以就是这样。)
这是密码

; Mastermind game in assembly language for the 8086

; Declare data segment
data segment
    code db 4 dup (0) ; Random 4-digit code
    guess db 4 dup (0) ; Player's current guess
    feedback db 10 dup (0) ; Feedback for each attempt
    attempts db 0 ; Number of attempts
    digits db '0123456789', 0 ; Valid digits
data ends

; Declare code segment
code segment
start:
    ; Initialize the code
    call generate_code

    ; Loop for 10 attempts
    mov bx, 10
    repeat:
        ; Get the player's guess
        call get_guess

        ; Check the guess against the code
        call check_guess

        ; Give feedback to the player
        call give_feedback

        ; Check if the player won
        call check_win

        ; Decrement the number of attempts
        dec bx
        jnz repeat

    ; The player lost
    call print_lose
    jmp exit

; Generates a random 4-digit code
generate_code:
    ; Initialize the random number generator
    mov ax, 0
    mov cx, 0x1234
    mov dx, 0x5678
    call rand

    ; Generate 4 random digits
    mov cx, 4
    generate_digit:
        ; Get a random digit
        mov ax, 10
        call rand
        mov al, dl

        ; Store the digit in the code
        mov [code + cx - 1], al

        ; Decrement the counter
        dec cx
        jnz generate_digit

    ; Return
    ret

; Gets the player's guess
get_guess:
    ; Prompt the player
    call print_prompt
    call read_guess

    ; Validate the guess
    call validate_guess

    ; Return
    ret

; Reads the player's guess from the input
read_guess:
    ; Read 4 characters
    mov cx, 4
    read_character:
        ; Read a character
        call getchar

        ; Store the character in the guess
        mov [guess + cx - 1], al

        ; Decrement the counter
        dec cx
        jnz read_character

    ; Return
    ret

; Validates the player's guess
validate_guess:
    ; Check that each character is a valid digit
    mov cx, 4
    validate_character:
        ; Get the current character
        mov al, [guess + cx - 1]

        ; Check if the character is a valid digit
        mov bx, digits
        call strchr
        cmp ax, -1
        jz invalid

        ; Decrement the counter
        dec cx
        jnz validate_character

    ; Return
    ret
code ends
ibrsph3r

ibrsph3r1#

它总是说它有代码的双重声明
您将标识符 code 用于两个不同的用途。
code db 4 dup (0)中是一个自定义变量的名称,在code segment中是一个程序段的名称,一般来说,“stuff”需要唯一标识。
我建议您为变量选择另一个名称,例如 MyCode

进一步回顾

mov [code + cx - 1], al
mov [guess + cx - 1], al
mov al, [guess + cx - 1]

generate_coderead_guessvalidate_guess 中,使用CX作为地址组件的指令无效。在8086上,只能使用BX、SI、DI和BP通过寄存器寻址内存。
我建议在这些循环中用SI替换CX:

generate_code:
    mov  ax, 0
    mov  cx, 0x1234
    mov  dx, 0x5678
    call rand
    mov  si, 4                       <<<
  generate_digit:
    mov  ax, 10
    call rand
    mov  al, dl
    mov  [MyCode + si - 1], al       <<<
    dec  si                          <<<
    jnz  generate_digit
    ret

read_guess:
    mov  si, 4                       <<<
  read_character:
    call getchar
    mov  [guess + si - 1], al        <<<
    dec  si                          <<<
    jnz  read_character
    ret

validate_guess:
    mov  si, 4                       <<<
  validate_character:
    mov  al, [guess + si - 1]        <<<
    mov  bx, digits                        ???
    call strchr
    cmp  ax, -1
    jz   invalid
    dec  si                          <<<
    jnz  validate_character
    ret

潜伏的问题

你的主程序循环依赖于BX寄存器作为计数器。然而其中一个子程序正在修改BX的值以供自己使用。这将不可避免地发生冲突!
你可以在栈上保留BX的值,如下例所示:

mov  bx, 10
repeat:
  push bx               ; (1)
  call get_guess
  call check_guess
  call give_feedback
  call check_win
  pop  bx               ; (1)
  dec  bx
  jnz  repeat

相关问题