.MODEL small .STACK 100h .DATA ; EQUATES FALSE EQU 0 TRUE EQU 1 BS_KEY EQU 08H CR EQU 13 LF EQU 10 SPACE EQU 20H INPUT EQU 0FFH SCREEN EQU 9 CURSOR_LEFT EQU 08H STR_TERM EQU 24H DIRECT_IO EQU 6 PERFORM_IO EQU 21H ; DATA BYTES TITLE_MSG DB "*** ACEY DUCEY : ASSEMBLY ***", CR, LF, STR_TERM RULES_LINE1 DB "ACEY DUCEY IS PLAYED IN THE FOLLOWING MANNER:", CR, LF, STR_TERM RULES_LINE2 DB "THE DEALER (COMPUTER) DEALS TWO CARDS FACE UP", CR, LF, STR_TERM RULES_LINE3 DB "YOU HAVE THE OPTION TO BET OR NOT BET DEPENDING", CR, LF, STR_TERM RULES_LINE4 DB "ON WHETHER OR NOT YOU FEEL THE NEXT CARD WILL", CR, LF, STR_TERM RULES_LINE5 DB "HAVE A VALUE BETWEEN THE FIRST TWO.", CR, LF, STR_TERM RULES_LINE6 DB " ", CR, LF, STR_TERM RULES_LINE7 DB "IF YOU DO NOT WANT TO BET, INPUT A 0 (ZERO).", CR, LF, STR_TERM SEE_RULES DB "DO YOU WANT TO SEE THE RULES?", CR, LF, STR_TERM PLAY_AGAIN DB "DO YOU WANT TO PLAY AGAIN?", CR, LF, STR_TERM WALLET_AMOUNT_START DB "YOU NOW HAVE", STR_TERM WALLET_AMOUNT_END DB " DOLLARS.", CR, LF, STR_TERM INVALID DB "PLEASE ENTER 'YES' OR 'NO'.", CR, LF, STR_TERM NEGATIVE DB "PLEASE BET A NON-NEGATIVE AMOUNT.", CR, LF, STR_TERM TOO_MUCH DB "SORRY MY FRIEND, BUT YOU BET TOO MUCH.", CR, LF, STR_TERM YOU_HAVE_1 DB "YOU HAVE ONLY", STR_TERM YOU_HAVE_2 DB " DOLLARS TO BET.", CR, LF, STR_TERM JACK DB "JACK", CR, LF, STR_TERM QUEEN DB "QUEEN", CR, LF, STR_TERM KING DB "KING", CR, LF, STR_TERM ACE DB "ACE", CR, LF, STR_TERM ASK_BET DB "WHAT IS YOUR BET?", CR, LF, STR_TERM YOU_WIN DB "YOU WIN!!!",CR,LF,STR_TERM YOU_LOSE DB "SORRY, YOU LOSE.", CR,LF,STR_TERM YOU_BUST DB "SORRY MY FRIEND, YOU ARE BROKE.",CR,LF,STR_TERM GAME_IS_OVER DB "*** GAME OVER ***", CR, LF, STR_TERM THANKS DB "THANKS FOR PLAYING!", CR, LF, STR_TERM HOPE DB "OK, HOPE YOU HAD FUN.", CR, LF, STR_TERM ANSWER DB LF, 0, LF DUP(0) NO_STRING DB "NO", 0 YES_STRING DB "YES", 0 NEWLINE_STRING DB CR,LF,24H BACKSPACE_STRING DB SPACE, CURSOR_LEFT, STR_TERM RUNNING DB TRUE GAME_OVER DB FALSE BET_IS_GOOD DB FALSE RANDOM_RESULT DB 0 CARD1 DB 0 CARD2 DB 0 CARD3 DB 0 MINIMUM DB 2 MAXIMUM DB 14 SHOW DB 0 BUFFER_LENGTH DB 5 INPUT_BUFFER DB 5 DUP(0) YES_FLAG DB 0 NO_FLAG DB 0 NEG_FLAG DB 0 ; DATA WORDS POS DW 0 BUFFER DW 9 DUP(0) TEMP_BUFFER DW 9 DUP(0) WALLET DW 0 BET DW 0 CARD_TO_DISPLAY DW 0 .CODE SET_AL_Y: MOV AL,'Y' RET SET_AL_N: MOV AL,'N' RET EXIT_PROC_Y_OR_N: CMP YES_FLAG,TRUE JE SET_AL_Y CMP NO_FLAG,TRUE JE SET_AL_N MOV AL,0 RET PROCESS_YES_OR_NO: MOV SI, 0H LEA BX,INPUT_BUFFER MOV YES_FLAG,FALSE MOV NO_FLAG,FALSE PROCESS_Y_OR_N: MOV CL,[BX+SI] CMP CL,STR_TERM JE EXIT_PROC_Y_OR_N CMP SI,0 JE CHECK_Y_OR_N CMP SI,1 JE CHECK_E_OR_O CMP SI,2 JE CHECK_S JMP EXIT_PROC_Y_OR_N CHECK_E_OR_O: CMP CL,'E' JE PROBABLE_YES CMP CL,'O' JE PROBABLE_NO MOV YES_FLAG,FALSE MOV NO_FLAG,FALSE JMP EXIT_PROC_Y_OR_N CHECK_S: CMP CL,'S' JE LIKELY_YES MOV YES_FLAG, FALSE JMP EXIT_PROC_Y_OR_N LIKELY_YES: CMP YES_FLAG,TRUE JE EXIT_PROC_Y_OR_N MOV YES_FLAG,FALSE JMP EXIT_PROC_Y_OR_N CHECK_Y_OR_N: CMP CL,'Y' JE POSSIBLE_YES CMP CL,'N' JE POSSIBLE_NO INC SI JMP PROCESS_Y_OR_N PROBABLE_YES: CMP YES_FLAG, TRUE JE MORE_YES MOV YES_FLAG, FALSE JMP EXIT_PROC_Y_OR_N MORE_YES: INC SI JMP PROCESS_Y_OR_N PROBABLE_NO: CMP NO_FLAG, TRUE JE MORE_NO MOV NO_FLAG, FALSE JMP EXIT_PROC_Y_OR_N MORE_NO: INC SI JMP PROCESS_Y_OR_N POSSIBLE_YES: MOV YES_FLAG, TRUE MOV NO_FLAG, FALSE INC SI JMP PROCESS_Y_OR_N POSSIBLE_NO: MOV YES_FLAG, FALSE MOV NO_FLAG, TRUE INC SI JMP PROCESS_Y_OR_N ACCEPT_CHARACTER_INPUT: XOR SI,SI LEA BX,INPUT_BUFFER PROCESS_INPUT: MOV AH, 01H INT 21h CMP AL, BS_KEY JE BACKSPACED CMP AL, CR JE DONE_PROCESSING_INPUT CMP AL, SPACE JL PROCESS_INPUT CMP AL, 126 JG PROCESS_INPUT MOV [BX+SI],AL INC SI JMP PROCESS_INPUT DONE_PROCESSING_INPUT: RET BACKSPACED: MOV DX,OFFSET BACKSPACE_STRING MOV AH,SCREEN INT PERFORM_IO JMP PROCESS_INPUT ACCEPT_INTEGER_INPUT: READ_INTEGER: XOR SI,SI MOV AX,@data MOV DX,AX LEA BX,INPUT_BUFFER READ_NEXT_INT: MOV AH, 01H INT 21h CMP AL,'-' JNE PROCESS_DIGIT CMP SI,0 JNE DONE_READING MOV [BX+SI],AL INC SI JMP READ_NEXT_INT PROCESS_DIGIT: CMP AL,'0' JL DONE_READING CMP AL,'9' JG DONE_READING MOV [BX+SI],AL INC SI JMP READ_INTEGER DONE_READING: MOV AL,STR_TERM MOV [BX+SI],AL JMP STORE_RESULT STORE_RESULT: MOV POS,SI MOV AL,10 MOV NEG_FLAG,FALSE XOR SI,SI CONVERT_S2I: CMP SI,POS JE EXIT_CONVERT_S2I MOV CX,[BX+SI] CMP CX,'-' JE IS_NEGATIVE SUB CX,49 MUL BET ADD BET,CX INC SI JMP CONVERT_S2I IS_NEGATIVE: MOV NEG_FLAG,TRUE INC SI JMP CONVERT_S2I EXIT_CONVERT_S2I: RET DISPLAY_CARD: CMP AL,10 JLE CONVERT_CARD CMP AL,11 JE DISPLAY_CARD_JACK CMP AL,12 JE DISPLAY_CARD_QUEEN CMP AL,13 JE DISPLAY_CARD_KING CMP AL,14 JE DISPLAY_CARD_ACE RET DISPLAY_CARD_JACK: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET JACK INT PERFORM_IO CALL WRITE_NEWLINE RET DISPLAY_CARD_KING: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET KING INT PERFORM_IO CALL WRITE_NEWLINE RET DISPLAY_CARD_QUEEN: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET QUEEN INT PERFORM_IO CALL WRITE_NEWLINE RET DISPLAY_CARD_ACE: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET ACE INT PERFORM_IO CALL WRITE_NEWLINE RET CONVERT_CARD: MOV CX, 10 MOV AX, CARD_TO_DISPLAY LEA SI, TEMP_BUFFER LEA DI, BUFFER MOV BX,0 CALL CONVERT_TO_STRING MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET BUFFER INT PERFORM_IO RET CONVERT_WALLET: MOV CX, 10 MOV AX, WALLET LEA SI, TEMP_BUFFER LEA DI, BUFFER MOV BX,0 CALL CONVERT_TO_STRING RET CONVERT_TO_STRING: XOR DX, DX DIV CX ADD DL, '0' MOV [SI], DL MOV [DI], DL INC SI INC DI INC BX CMP AX, 0 JNE CONVERT_TO_STRING CALL WRITE_NEWLINE REVERSE_BUFFER: LEA SI, BUFFER LEA DI, TEMP_BUFFER MOV AX, DI DEC AX ADD DI, BX REVERSE_LOOP: CMP AX,DI JE EXIT_REVERSE MOV BL,[DI] MOV [SI],BL INC SI DEC DI JMP REVERSE_LOOP EXIT_REVERSE: MOV BYTE PTR [SI], STR_TERM RET READ_CHAR: READ_WAIT: MOV AH,DIRECT_IO MOV DL,0FFH INT PERFORM_IO TEST AL,AL JZ READ_WAIT RET WRITE_CHAR: MOV AH,DIRECT_IO MOV DL,AL INT PERFORM_IO RET WRITE_NEWLINE: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET NEWLINE_STRING INT PERFORM_IO RET DO_PLAY_AGAIN: CALL INIT_GAME ASK_TO_PLAY_AGAIN: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET PLAY_AGAIN INT PERFORM_IO CALL ACCEPT_CHARACTER_INPUT CALL PROCESS_YES_OR_NO CMP AL,'Y' JE DO_PLAY_AGAIN CMP AL,'N' JE EXIT_ASK CALL WRITE_NEWLINE MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET INVALID INT PERFORM_IO JMP ASK_TO_PLAY_AGAIN ASK_TO_SEE_THE_RULES: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET SEE_RULES INT PERFORM_IO CALL ACCEPT_CHARACTER_INPUT CALL PROCESS_YES_OR_NO CMP AL,'Y' JE DISPLAY_RULES CMP AL,'N' JE EXIT_ASK CALL WRITE_NEWLINE MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET INVALID INT PERFORM_IO JMP ASK_TO_SEE_THE_RULES DISPLAY_RULES: CALL WRITE_NEWLINE MOV AX,@data MOV DS,AX MOV AH,09H MOV DX,OFFSET RULES_LINE1 INT 21H MOV DX,OFFSET RULES_LINE2 INT 21H MOV DX,OFFSET RULES_LINE3 INT 21H MOV DX,OFFSET RULES_LINE4 INT 21H MOV DX,OFFSET RULES_LINE5 INT 21H MOV DX,OFFSET RULES_LINE6 INT 21H MOV DX,OFFSET RULES_LINE7 INT 21H RET EXIT_ASK: CALL WRITE_NEWLINE RET GENERATE_RANDOM_NUMBER: MOV AH, 00H INT 1AH MOV BH, 62 MOV AH, DL CMP AH, BH JA GENERATE_RANDOM_NUMBER MOV BH, 51 MOV AH, DL CMP AH, BH JB GENERATE_RANDOM_NUMBER SUB DL,49 MOV RANDOM_RESULT, DL RET SELECT_CARD1: CALL GENERATE_RANDOM_NUMBER MOV AL,RANDOM_RESULT MOV CARD1,AL CBW MOV CARD_TO_DISPLAY,AX CALL DISPLAY_CARD RET SELECT_CARD2: CALL GENERATE_RANDOM_NUMBER MOV AL,RANDOM_RESULT CMP CARD1,AL JE SELECT_CARD2 MOV CARD2,AL CBW MOV CARD_TO_DISPLAY,AX CALL DISPLAY_CARD RET SELECT_CARD3: CALL GENERATE_RANDOM_NUMBER MOV AL,RANDOM_RESULT CMP CARD1,AL JE SELECT_CARD3 CMP CARD2,AL JE SELECT_CARD3 MOV CARD3,AL CBW MOV CARD_TO_DISPLAY,AX CALL DISPLAY_CARD RET SET_BET_GOOD: MOV BET_IS_GOOD,TRUE RET SET_BET_BAD: MOV BET_IS_GOOD,FALSE RET COMPARE_CARDS: CALL SET_BET_BAD CALL COMPARE_3GT1 RET COMPARE_3GT1: MOV AL,CARD3 MOV BL,CARD1 CMP AL,BL JG COMPARE_3LT2 CALL COMPARE_3GT2 RET COMPARE_3LT2: MOV AL,CARD3 MOV BL,CARD2 CMP AL,BL JNG SET_BET_GOOD RET COMPARE_3GT2: MOV AL,CARD3 MOV BL,CARD2 CMP AL,BL JG SET_BET_GOOD RET ASK_FOR_BET: CALL WRITE_NEWLINE MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET ASK_BET INT PERFORM_IO CALL ACCEPT_INTEGER_INPUT MOV AX,BET CMP AX,0 JL NEGATIVE_BET MOV AX,BET MOV BX,WALLET CMP AX,BX JG EXCESSIVE_BET RET NEGATIVE_BET: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET NEGATIVE INT PERFORM_IO JMP ASK_FOR_BET EXCESSIVE_BET: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET TOO_MUCH INT PERFORM_IO MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET YOU_HAVE_1 INT PERFORM_IO CALL CONVERT_WALLET MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET BUFFER INT PERFORM_IO MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET YOU_HAVE_2 INT PERFORM_IO JMP ASK_FOR_BET CLEAR_CARDS: MOV CARD1,0 MOV CARD2,0 MOV CARD3,0 RET INIT_GAME: MOV GAME_OVER,FALSE MOV WALLET,100 RUNNING_LOOP: CALL GAME_LOOP CMP GAME_OVER,FALSE JNE RUNNING_LOOP RET EXIT_GAME: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET GAME_IS_OVER INT PERFORM_IO CALL ASK_TO_PLAY_AGAIN CMP AL,'Y' JNE EXIT_PROGRAM CALL INIT_GAME EXIT_PROGRAM: MOV AX,@data MOV DS,AX MOV AH,SCREEN LEA DX,THANKS INT PERFORM_IO MOV AX,@data MOV DS,AX MOV AH,SCREEN LEA DX,HOPE INT PERFORM_IO CALL TERMINATE GAME_LOOP: CMP GAME_OVER,TRUE JE EXIT_GAME CALL CONVERT_WALLET MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET WALLET_AMOUNT_START INT PERFORM_IO MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET BUFFER INT PERFORM_IO MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET WALLET_AMOUNT_END INT PERFORM_IO CALL CLEAR_CARDS CALL SELECT_CARD1 CALL SELECT_CARD2 CALL ASK_FOR_BET CMP BET,0 JE ZERO_BET CALL SELECT_CARD3 CALL COMPARE_CARDS CMP BET_IS_GOOD,TRUE JE INCREASE_WALLET JNE DECREASE_WALLET CMP WALLET,0 JLE GONE_BUST JMP GAME_LOOP INCREASE_WALLET: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET YOU_WIN INT PERFORM_IO INC WALLET JMP GAME_LOOP DECREASE_WALLET: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET YOU_LOSE INT PERFORM_IO DEC WALLET JMP GAME_LOOP ZERO_BET: MOV GAME_OVER,TRUE JMP GAME_LOOP GONE_BUST: MOV AX,@data MOV DS,AX MOV AH,SCREEN MOV DX,OFFSET YOU_BUST INT PERFORM_IO MOV GAME_OVER,TRUE JMP GAME_LOOP START: MOV AX,@data MOV DS,AX MOV AH,09H LEA DX,TITLE_MSG INT 21h CALL ASK_TO_SEE_THE_RULES MOV GAME_OVER,FALSE MOV WALLET,100 MOV RUNNING,TRUE CALL RUNNING_LOOP TERMINATE: ; Exit program MOV AH, 4CH INT 21H END START