[comp.os.msdos.programmer] Programming the Mouse

gene@uokmax.uucp (Gene E. Johannsen) (07/31/90)

	I am writing a program that I want to use the mouse with.  I don't
have a reference work to the mouse so I am using a list of interrupts.  Below
is a small program I writing to learn how to use the mouse.  All it will do is
set up and turn on the mouse and then print an '*' when I press the left
button.  It prints the '*' but freezes immediately afterwards:

.MODEL	SMALL

.CODE

;-----------------------------
;Initializes a Hardware mouse
;-----------------------------
	mov ax,0009h	;
	mov bx,0001h	;define text cursor
	mov cx,0000h	;
	mov dx,0008h	;
	int 33h		;
	
	mov ax,000ch	;
	mov cx,0002h	;define interrupt subroutine parameters
	es:		;
	lea dx,BUTTON	;
	int 33h		;
	
	mov ax,0001h	;show mouse cursor
	int 33h		;

	mov ah,08h	;pause until a key is pressed
	int 21h		;

	int 20h		;exit program


;------------------------------------------------------
;BUTTON
;Prints an '*' when the left button is pressed.
;------------------------------------------------------


BUTTON		PROC	FAR
	push ax		;This is where the problem comes.  It prints 
	push dx		;the '*' okay, but then it freezes.
	mov ah,02h	
	mov dl,2ah
	int 21h
	pop dx
	pop ax
	ret
BUTTON		ENDP

	END

gene@uokmax.ecn.uoknor.edu

readdm@walt.cc.utexas.edu (David M. Read) (07/31/90)

In article [abridged] gene@uokmax.uucp (Gene E. Johannsen) writes:
!>
!>	I am writing a program that I want to use the mouse with.  I don't
!>have a reference work to the mouse so I am using a list of interrupts.  Below
!>is a small program I writing to learn how to use the mouse.  All it will do is
!>set up and turn on the mouse and then print an '*' when I press the left
!>button.  It prints the '*' but freezes immediately afterwards:
!>
!>.MODEL	SMALL
!>
!>.CODE
!>
!>  [...]
!>
!>BUTTON		PROC	FAR
!>	push ax		;This is where the problem comes.  It prints 
!>	push dx		;the '*' okay, but then it freezes.
!>	mov ah,02h	
!>	mov dl,2ah
!>	int 21h
!>	pop dx
!>	pop ax
!>	ret
        ^^^
!>BUTTON		ENDP
!>
!>	END
>
I may be wrong here, but shouldn't this be an 'iret' instruction?  After
all, the routine *is* an interrupt service routine, called by a hardware
interrupt...If you return with a regular 'ret' call, none of the registers
are popped off the stack and restored to their state before the interrupt,
and the CPU doesn't know where to pick up, so it *should* freeze!

-Dave

Ralf.Brown@B.GP.CS.CMU.EDU (07/31/90)

In article <34725@ut-emx.UUCP>, readdm@walt.cc.utexas.edu (David M. Read) wrote:
}In article [abridged] gene@uokmax.uucp (Gene E. Johannsen) writes:
}!>
}!>      I am writing a program that I want to use the mouse with.  I don't
}!>have a reference work to the mouse so I am using a list of interrupts.  Below
}!>is a small program I writing to learn how to use the mouse.  All it will do is
}!>set up and turn on the mouse and then print an '*' when I press the left
}!>button.  It prints the '*' but freezes immediately afterwards:
}!>
}!>  [...]
}!>
}!>BUTTON                PROC    FAR
}!>  [...]
}!>      ret
}        ^^^
}!>BUTTON                ENDP
}!>
}!>      END
}>
}I may be wrong here, but shouldn't this be an 'iret' instruction?  After
}all, the routine *is* an interrupt service routine, called by a hardware
}interrupt...If you return with a regular 'ret' call, none of the registers
}are popped off the stack and restored to their state before the interrupt,
}and the CPU doesn't know where to pick up, so it *should* freeze!

No, because the "interrupt handler" is actually a FAR routine called by the
real mouse interrupt handler in the mouse.sys or mouse.com software.  The real
problem is that Gene is calling INT 21h from an interrupt handler, which is
a no-no unless stringent precautions are taken to avoid re-entering DOS.
--
UUCP: {ucbvax,harvard}!cs.cmu.edu!ralf -=- 412-268-3053 (school) -=- FAX: ask
ARPA: ralf@cs.cmu.edu  BIT: ralf%cs.cmu.edu@CMUCCVMA  FIDO: 1:129/3.1
Disclaimer?    |   I was gratified to be able to answer promptly, and I did.
What's that?   |   I said I didn't know.  --Mark Twain

johnk@telxon.uucp (John E. Kabat Jr.) (07/31/90)

Of course it won't work  u r calling dos from inside an interrupt
routine.  Try using the bios calls or write directly to the screen.
U are not normally able to coll dos from inside an interrupt routine
with out playing a log to funny games.

John E. Kabat Jr.    <|> ...!uunet!telxon!johnk <|> johnk@telxon.uucp.uu.net
Telxon Corporation   <|> 
Akron, Ohio, 44313   <|> 
(216) 867-3700 (3554)<|> 



John E. Kabat Jr.    <|> ...!uunet!telxon!johnk <|> johnk@telxon.uucp.uu.net
Telxon Corporation   <|> 
Akron, Ohio, 44313   <|> 
(216) 867-3700 (3554)<|> 

everett@hpcvra.CV.HP.COM (Everett Kaser) (08/01/90)

/ gene@uokmax.uucp (Gene E. Johannsen) writes...
>	I am writing a program that I want to use the mouse with.  I don't
>have a reference work to the mouse so I am using a list of interrupts.  Below
>is a small program I writing to learn how to use the mouse.  All it will do is
>set up and turn on the mouse and then print an '*' when I press the left
>button.  It prints the '*' but freezes immediately afterwards:

>BUTTON		PROC	FAR
>	push ax		;This is where the problem comes.  It prints 
>	push dx		;the '*' okay, but then it freezes.
>	mov ah,02h	
>	mov dl,2ah
>	int 21h
>	pop dx
>	pop ax
>	ret
>BUTTON		ENDP

I believe that your problem is the call to DOS (INT 21h) inside your mouse
event handler routine.  Since the mouse generates a hardware interrupt, which
controls CPU execution to be vectored to the mouse driver, which then calls
your routine, you cannot call DOS, only manipulate your own code/data space,
make calls to INT 33h (the mouse driver), directly manipulate the display
(dangerous), etc.  Since in your main program you've called DOS to get a key,
when you call DOS from the mouse event handler (which was called from a hard-
ware ISR), you're re-entering DOS.  DOS was not designed to be re-entrant and
you screw up their stacks and flags and stuff.

Everett Kaser                   Hewlett-Packard Company
...hplabs!hp-pcd!everett        work: (503) 750-3569   Corvallis, Oregon
everett%hpcvra@hplabs.hp.com    home: (503) 928-5259   Albany, Oregon

gene@uokmax.uucp (Gene E. Johannsen) (08/01/90)

In article <34725@ut-emx.UUCP> readdm@walt.cc.utexas.edu (David M. Read) writes:
>In article [abridged] gene@uokmax.uucp (Gene E. Johannsen) writes:
>!>
>!>	I am writing a program that I want to use the mouse with.  I don't
>!>have a reference work to the mouse so I am using a list of interrupts.  Below
>!>is a small program I writing to learn how to use the mouse.  All it will do is
>!>set up and turn on the mouse and then print an '*' when I press the left
>!>button.  It prints the '*' but freezes immediately afterwards:
>!>
>!>.MODEL	SMALL
>!>
>!>.CODE
>!>
>!>  [...]
>!>
>!>BUTTON		PROC	FAR
>!>	push ax		;This is where the problem comes.  It prints 
>!>	push dx		;the '*' okay, but then it freezes.
>!>	mov ah,02h	
>!>	mov dl,2ah
>!>	int 21h
>!>	pop dx
>!>	pop ax
>!>	ret
>        ^^^
>!>BUTTON		ENDP
>!>
>!>	END
>>
>I may be wrong here, but shouldn't this be an 'iret' instruction?  After
>all, the routine *is* an interrupt service routine, called by a hardware
>interrupt...If you return with a regular 'ret' call, none of the registers
>are popped off the stack and restored to their state before the interrupt,
>and the CPU doesn't know where to pick up, so it *should* freeze!
>
>-Dave


I thought the same thing, but I tried 'iret' and it didn't work any better.
Anyway, I found my problem.  It is the 'int 21h' that freezes it.  I honestly
don't know why.

gene

L.Parkes@comp.vuw.ac.nz (Lloyd Parkes) (08/01/90)

In article <34725@ut-emx.UUCP> readdm@walt.cc.utexas.edu (David M. Read) writes:

   !>	ret
	^^^
   !>BUTTON		ENDP
   !>
   !>	END
   >
   I may be wrong here, but shouldn't this be an 'iret' instruction?  After
   all, the routine *is* an interrupt service routine, called by a hardware

No it isn't. Mouse event handlers are called by the the mouse driver.
The mouse driver uses far calls.

					Lloyd

--
------------------------------------------------------------------------
Lloyd Parkes		|	   Bix Licks Stick's Tricks
lloyd@comp.vuw.ac.nz	|    Bix Barton Master of the Rum and Uncanny
------------------------------------------------------------------------

broehl@watserv1.waterloo.edu (Bernie Roehl) (08/02/90)

In article <1990Jul31.193800.18227@uokmax.uucp> gene@uokmax.uucp (Gene E. Johannsen) writes:
>Anyway, I found my problem.  It is the 'int 21h' that freezes it.  I honestly
>don't know why.

It's because DOS is not re-entrant.  You may be in the midst of a DOS call
when a mouse interrupt comes along; you call DOS again from your handler,
and since DOS has only one internal stack you overwrite what was there
previously.  Your call completes, you get your *, then the handler returns
to a clobbered stack and your system goes to Sudbury.
-- 
	Bernie Roehl, University of Waterloo Electrical Engineering Dept
	Mail: broehl@watserv1.waterloo.edu OR broehl@watserv1.UWaterloo.ca
	BangPath: {allegra,decvax,utzoo,clyde}!watmath!watserv1!broehl
	Voice:  (519) 885-1211 x 2607 [work]

gene@uokmax.uucp (Gene E. Johannsen) (08/03/90)

Thank you all for responding and telling me the problem with my program
(DOS is not re-entrant).  Now I have some questions:

	1) I wrote a program to put an '*' on the screen where I had my
	   cursor.  I did the standard conversion, ie. row*80+column, but
	   then found that I had to divide this value by 4.  Why?
	2) I am now trying to program the mouse using graphics.  If someone
	   could direct me to a good source for Mouse and/or VGA graphics
	   information I would be grateful.

thanks

Gene