Need help to run 16 bit program in MAsm32.

Started by ashokpatil, October 13, 2006, 06:48:08 AM

Previous topic - Next topic

ashokpatil

Hello friends:
I am used to writing assembly in 16 bit. But, I have downloaded MASM32 on my computer. I have modified the program below to work under MASM32. It compiles successfully, but when i run it, the program crahses.  When i change the model to small, the compiler does not see the variables.  The program takes input from the user and displays it at the center of the screen.
When i try compiling it, i get the error message, "can not acess label through segment registers" for each of the isntruction which tries to access a variable.
If i change the model to flat, it compiles fine, but the program crashes when i try to run.

Could anyone help please?
Thank you.


; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

;                 Build this with the "Project" menu using
;                       "Console Assemble and Link"

; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

;TITLE   A08CTRNM (EXE)  Accept names from keyboard,
;                center them on screen, sound bell

       .386                                 ; create 32 bit code
    .model small, stdcall                 ; 32 bit memory model
    option casemap :none                    ; case sensitive

    include \masm32\include\windows.inc     ; always first
    include \masm32\macros\macros.asm       ; MASM support macros

  ; -----------------------------------------------------------------
  ; include files that have MASM format prototypes for function calls
  ; -----------------------------------------------------------------
    include \masm32\include\masm32.inc
    include \masm32\include\gdi32.inc
    include \masm32\include\user32.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\debug.inc


  ; ------------------------------------------------
  ; Library files that have definitions for function
  ; exports and tested reliable prebuilt code.
  ; ------------------------------------------------
    includelib \masm32\lib\masm32.lib
    includelib \masm32\lib\gdi32.lib
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    includelib \masm32\lib\debug.lib

     .DATA
PARLIST   LABEL  BYTE         ;Name parameter list:
MAXNLEN   DB     20            ;  maximum length of name
ACTULEN   DB     ?            ;  no. of characters entered
KBNAME   DB     21 DUP(' ')      ;  entered name
PROMPT   DB     'Name? ', '$'
;-------------------------------------------------------

    .STACK 64 
    .code                       ; Tell MASM where the code starts
   

; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

start:                          ; The CODE entry point to the program

        call main
        exit

main proc     
           CALL   Q10CLEAR      ;Clear screen
A20:
      MOV     DX,0000         ;Set cursor to 00,00
      CALL   Q20CURSOR
      CALL   B10INPUT      ;Provide for input of name
      CALL   Q10CLEAR      ;Clear screen
      CMP     ACTULEN,00      ;Name entered?
      JE     A30         ;  no, exit
      CALL   C10CENTER      ;Set bell and '$' and center
      CALL   D10DISPLY      ;Display name
      JMP     A20         ;Repeat
A30:
        ret
main endp
;           Display prompt and accept input of name:
;            --------------------------------------
B10INPUT   PROC   NEAR
      PUSH     AX            ;Preserve used
      PUSH     DX            ;  registers
      MOV     AH,09H         ;Request display
      LEA     DX,PROMPT      ;  of user prompt
      INT     21H
      MOV     AH,0AH         ;Request keyboard
      LEA     DX,PARLIST      ;  input
      INT     21H
      POP     DX            ;Restore
      POP     AX            ;  registers
      RET
B10INPUT   ENDP
;            Set bell and '$' delimiter and
;              set cursor at center of screen:
;            --------------------------------
C10CENTER   PROC   NEAR         ;Uses BX and DX
      MOVZX  BX,ACTULEN      ;Replace 0DH with 07H
      MOV     KBNAME[BX],07
      MOV     KBNAME[BX+1],'$'   ;Set display delimiter
      MOV     DL,ACTULEN      ;Locate center column:
      SHR     DL,1         ;  divide length by 2,
      NEG     DL            ;  reverse sign,
      ADD     DL,40         ;  add 40
      MOV     DH,12         ;Center row
      CALL   Q20CURSOR      ;Set cursor
      RET
C10CENTER   ENDP
;           Display centered name:
;           ---------------------
D10DISPLY   PROC   NEAR         ;Uses AH and DX
      MOV     AH,09H
      LEA     DX,KBNAME      ;Display name
      INT     21H
      RET
D10DISPLY   ENDP
;           Clear screen and set attribute:
;            -----------------------------
Q10CLEAR   PROC   NEAR
      PUSHA            ;Preserve general registers
      MOV     AX,0600H      ;Request scroll screen
      MOV     BH,30         ;Color attribute
      MOV     CX,0000         ;From 00,00
      MOV     DX,184FH      ;  to 24,79
      POPA               ;Restore general registers
      INT     10H
      RET
Q10CLEAR   ENDP
;           Set cursor row, column:
;            ---------------------
                     ;DX set on entry
Q20CURSOR   PROC   NEAR         ;Uses AH and BH
      MOV     AH,02H         ;Request set cursor
      MOV     BH,00         ;Page #0
      INT     10H
      RET
Q20CURSOR   ENDP


; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

end start                       ; Tell MASM where the program ends

      

japheth

Hi,

1. issue

>       .386
>    .model small, stdcall

this is a no-no if you want to create a real-mode program, instead write:

>       .286
>    .model small, stdcall
>       .386                                 ; create 32 bit code


2. remove all those masm32 includes and libs, they cannot help you in 16-bit.

3. a stack of 64 byte is very small, should be increased (512 is good)
4. you might better set up DS on startup, for example:

    mov ax,@data
    mov ds,ax
    call main


sinsi

Re: Q10CLEAR
Q10CLEAR   PROC   NEAR
      PUSHA            ;Preserve general registers
      MOV     AX,0600H      ;Request scroll screen
      MOV     BH,30         ;Color attribute
      MOV     CX,0000         ;From 00,00
      MOV     DX,184FH      ;  to 24,79
      POPA               ;Restore general registers
      INT     10H
      RET
Q10CLEAR   ENDP

You save all registers (PUSHA) on entry, then fill registers for your INT 10H call, but then restore registers (POPA) before your INT 10H call, trashing your just-filled registers...

Write your normal 16-bit .ASM, then produce the .OBJ by using "ML /c A08CTRNM.ASM", then produce the .EXE using a 16-bit linker (search the forum for "link16")
Light travels faster than sound, that's why some people seem bright until you hear them.

ashokpatil

#3
Thank you sinsi and japheth for your help:

I am going to try to find link16 on the forum, meantime, i fixed the bug in Q10clear procedure and made other changes as suggested by japheth:
Still i am getting the following erros.

Assembling: C:\masm32\ashok\A08CTRNM.asm
C:\masm32\ashok\A08CTRNM.asm(32) : error A2006: undefined symbol : DGROUP
C:\masm32\ashok\A08CTRNM.asm(47) : error A2074: cannot access label through segment registers
C:\masm32\ashok\A08CTRNM.asm(74) : error A2074: cannot access label through segment registers
C:\masm32\ashok\A08CTRNM.asm(75) : error A2074: cannot access label through segment registers
C:\masm32\ashok\A08CTRNM.asm(76) : error A2074: cannot access label through segment registers
C:\masm32\ashok\A08CTRNM.asm(77) : error A2074: cannot access label through segment registers

I know that i have made some silly mistake somewhere, can't figure out what it is.  I think the data section is not being properly initialized.

Your help is really appreaciated.
Thank you.
Ashok
now the program looks as follows:

;TITLE A08CTRNM (EXE)  Accept names from keyboard,
; center them on screen, sound bell

       .286                                ; create 32 bit code
    .model small, stdcall                  ; 32 bit memory model
    option casemap :none                    ; case sensitive
    .386

     .DATA
PARLIST LABEL  BYTE ;Name parameter list:
MAXNLEN DB   20 ;  maximum length of name
ACTULEN DB   ? ;  no. of characters entered
KBNAME DB   21 DUP(' ') ;  entered name
PROMPT DB   'Name? ', '$'
;-------------------------------------------------------

    .STACK 512
    .code                       ; Tell MASM where the code starts
   

; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

start:                          ; The CODE entry point to the program

       mov ax,@data
       mov ds,ax
       MOV   ES,AX

        call main
        MOV   AX,4C00H ;End processing
  INT   21H

main proc near     
      CALL   Q10CLEAR ;Clear screen
A20:
MOV   DX,0000 ;Set cursor to 00,00
CALL   Q20CURSOR
CALL   B10INPUT ;Provide for input of name
CALL   Q10CLEAR ;Clear screen
CMP   ACTULEN,00 ;Name entered?
JE   A30 ;  no, exit
CALL   C10CENTER ;Set bell and '$' and center
CALL   D10DISPLY ;Display name
JMP   A20 ;Repeat
A30:
     ret
main endp
;   Display prompt and accept input of name:
;    --------------------------------------
B10INPUT PROC   NEAR
PUSH   AX ;Preserve used
PUSH   DX ;  registers
MOV   AH,09H ;Request display
LEA   DX,PROMPT ;  of user prompt
INT   21H
MOV   AH,0AH ;Request keyboard
LEA   DX,PARLIST ;  input
INT   21H
POP   DX ;Restore
POP   AX ;  registers
RET
B10INPUT ENDP
;    Set bell and '$' delimiter and
;      set cursor at center of screen:
;    --------------------------------
C10CENTER PROC   NEAR ;Uses BX and DX
MOVZX  BX,ACTULEN ;Replace 0DH with 07H
MOV   KBNAME[BX],07
MOV   KBNAME[BX+1],'$' ;Set display delimiter
MOV   DL,ACTULEN ;Locate center column:
SHR   DL,1 ;  divide length by 2,
NEG   DL ;  reverse sign,
ADD   DL,40 ;  add 40
MOV   DH,12 ;Center row
CALL   Q20CURSOR ;Set cursor
RET
C10CENTER ENDP
;   Display centered name:
;   ---------------------
D10DISPLY PROC   NEAR ;Uses AH and DX
MOV   AH,09H
LEA   DX,KBNAME ;Display name
INT   21H
RET
D10DISPLY ENDP
;   Clear screen and set attribute:
;    -----------------------------
Q10CLEAR PROC   NEAR
PUSHA ;Preserve general registers
MOV   AX,0600H ;Request scroll screen
MOV   BH,30 ;Color attribute
MOV   CX,0000 ;From 00,00
MOV   DX,184FH ;  to 24,79
INT   10H
                                POPA ;Restore general registers
RET
Q10CLEAR ENDP
;   Set cursor row, column:
;    ---------------------
;DX set on entry
Q20CURSOR PROC   NEAR ;Uses AH and BH
MOV   AH,02H ;Request set cursor
MOV   BH,00 ;Page #0
INT   10H
RET
Q20CURSOR ENDP


; «««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

end start                       ; Tell MASM where the program ends


EDIT: Added code tags to make the code easier to view and copy.

      

sinsi

I only get those errors using ML version 7 and ML version 8.
Using ML version 6 and LINK16 assembles, links and runs OK.
Light travels faster than sound, that's why some people seem bright until you hear them.

japheth


ML 7 and 8 require another parameter:

ml -c -omf A08CTRNM.asm


sinsi

Ah, they default to /coff (at last). Merci for the info japheth :U.
Light travels faster than sound, that's why some people seem bright until you hear them.

ashokpatil

Thank you friends. I got it. I downloaded the 16 bit linker, renamed it as link16.exe and

compiled the source code with mc /c filename.asm
link16 filename.obj

IT WORKED!!.
Thanks to both JAPHETH and SINSI