Free PS/2 mouse code

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
SANiK

Free PS/2 mouse code

Post by SANiK »

Code: Select all

//Mouse.inc by SANiK
//License: Use as you wish, except to cause damage
byte mouse_cycle=0;     //unsigned char
sbyte mouse_byte[3];    //signed char
sbyte mouse_x=0;         //signed char
sbyte mouse_y=0;         //signed char

//Mouse functions
void mouse_handler(struct regs *a_r) //struct regs *a_r (not used but just there)
{
  switch(mouse_cycle)
  {
    case 0:
      mouse_byte[0]=inportb(0x60);
      mouse_cycle++;
      break;
    case 1:
      mouse_byte[1]=inportb(0x60);
      mouse_cycle++;
      break;
    case 2:
      mouse_byte[2]=inportb(0x60);
      mouse_x=mouse_byte[1];
      mouse_y=mouse_byte[2];
      mouse_cycle=0;
      break;
  }
}

inline void mouse_wait(byte a_type) //unsigned char
{
  dword _time_out=100000; //unsigned int
  if(a_type==0)
  {
    while(_time_out--) //Data
    {
      if((inportb(0x64) & 1)==1)
      {
        return;
      }
    }
    return;
  }
  else
  {
    while(_time_out--) //Signal
    {
      if((inportb(0x64) & 2)==0)
      {
        return;
      }
    }
    return;
  }
}

inline void mouse_write(byte a_write) //unsigned char
{
  //Wait to be able to send a command
  mouse_wait(1);
  //Tell the mouse we are sending a command
  outportb(0x64, 0xD4);
  //Wait for the final part
  mouse_wait(1);
  //Finally write
  outportb(0x60, a_write);
}

byte mouse_read()
{
  //Get's response from mouse
  mouse_wait(0); 
  return inportb(0x60);
}

void mouse_install()
{
  byte _status;  //unsigned char
 
  //Enable the auxiliary mouse device
  mouse_wait(1);
  outportb(0x64, 0xA8);
  
  //Enable the interrupts
  mouse_wait(1);
  outportb(0x64, 0x20);
  mouse_wait(0);
  _status=(inportb(0x60) | 2);
  mouse_wait(1);
  outportb(0x64, 0x60);
  mouse_wait(1);
  outportb(0x60, _status);
  
  //Tell the mouse to use default settings
  mouse_write(0xF6);
  mouse_read();  //Acknowledge
  
  //Enable the mouse
  mouse_write(0xF4);
  mouse_read();  //Acknowledge

  //Setup the mouse handler
  irq_install_handler(12, mouse_handler);
}
Eat up!
It's been tested in Boch's, VMWare, and on real hardware and it works on all 3 platforms.
Due to the lack of PS/2 mouse documention, I offer this code as documention itself meaning there are no royalties and crap like that.

Credits:
Warmaster199/Hopeless for having me write the driver in the first place =P
Froggey and Journey for testing the countless lines of code.

Just having everyone reach equillibrium...

------
*edit*
------
http://www.osdever.net/forums/viewtopic.php?t=1395
VESA pmode detection routine. Easy and nothing trivial there.
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Free PS/2 mouse code

Post by Pype.Clicker »

someone around here has suggested some PS2 code could be non-working because inb/outb macros were not including waits. Do your inb/outb have something special or do they simply perform "in DX,AL" and "out AL,DX" as we should expect them to do ?

tnx for the code, by the way. I was just searching for some quick-to-integrate PS2 mouse code for Clicker :-)
mystran

Re:Free PS/2 mouse code

Post by mystran »

It was me that suggested it, and it was totally random thought to a "this does not work"-type question; I've noticed that while Bochs/VMWare might not care about delays, not having them when doing IO to some devices on real machine can cause all kinds of interesting problems.

I don't really know much about PS/2 programming, and I don't actually have any idea if PS/2 mice are affected by the issue, although I remember writing a driver once when I was still programming for DOS, which more or less means pre-1995. ;)

edit: Oh, and it was Sanik who asked for what might be wrong. :)
SANiK

Re:Free PS/2 mouse code

Post by SANiK »

mystran, yeah, I had fixed it.

I went through like 30 different initiation methods before I got one that works.
Ooh, and thanks about the "quick-to-integrate PS2 mouse code."
I try to stick to the 'self-sufficient' coding style in which each component (One C file) relies as little as possible on other pieces.

The reason most of the tutorials and documents I tryed didn't work was that they simply forgot to or used:
1) Add a time out for the mouse
2) Didn't wait to acknowledge the returned command from the mouse
3) Wrong in/out addresses or commands

There should be a driver-dev forum on here =P (Just kidding though, that would be asking for too much)
Many osdevers overlook the very people who would write drivers for them.
User avatar
Candy
Member
Member
Posts: 3882
Joined: Tue Oct 17, 2006 11:33 pm
Location: Eindhoven

Re:Free PS/2 mouse code

Post by Candy »

Pype.Clicker wrote: ...have something special or do they simply perform "in DX,AL" and "out AL,DX" as we should expect them to do ?
I'd make that "out DX, AL".
B.E

Re:Free PS/2 mouse code

Post by B.E »

Candy wrote:
Pype.Clicker wrote: ...have something special or do they simply perform "in DX,AL" and "out AL,DX" as we should expect them to do ?
I'd make that "out DX, AL".
It depends on what compiler you use, for example TASM and MASM use destination, source while NASM uses source, destination
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Free PS/2 mouse code

Post by Pype.Clicker »

sorry for messing things up. I must have used GCC inline assembly for too long ... NASM, MASM and TASM both use the intel-suggested order of "out DX,AL", of course ... The underlying question was whether there were additionnal wait states etc.

Tnx for the code again: whyme_t has started integrating it in clicker ;)
distantvoices
Member
Member
Posts: 1600
Joined: Wed Oct 18, 2006 11:59 am
Location: Vienna/Austria
Contact:

Re:Free PS/2 mouse code

Post by distantvoices »

can we expect clicker to have a funky cursor moving around when the mouse is touched - soon? ];->
... the osdever formerly known as beyond infinity ...
BlueillusionOS iso image
User avatar
Pype.Clicker
Member
Member
Posts: 5964
Joined: Wed Oct 18, 2006 2:31 am
Location: In a galaxy, far, far away
Contact:

Re:Free PS/2 mouse code

Post by Pype.Clicker »

hehe ... i guess yes ... Say, BI, don't you wish to be hired by the Clicker team and port your VM86/VBE code on another birthing platform ?
distantvoices
Member
Member
Posts: 1600
Joined: Wed Oct 18, 2006 11:59 am
Location: Vienna/Austria
Contact:

Re:Free PS/2 mouse code

Post by distantvoices »

No problem. I gonna give it a shot, but no promises or deadlines. *gg*

I have a GUI to complete and a File System Service to flesh out too(file remove is pretty incomplete - no blocks freed, no inode freed, dir entry remains intact, only te vfs entry gets lost) - and the BlueIllusion Text editor waits to be completed and tested. *gg*

[ot]
The past four weeks I have spent with
debug sessions darker than night just to find out that my reverse page mappings got overwritten due to unintended multiple hand out of already dealt out pages (merde) - so time to bork out for the Memory Manager.
[/ot]
... the osdever formerly known as beyond infinity ...
BlueillusionOS iso image
SANiK

Re:Free PS/2 mouse code

Post by SANiK »

I think I missed a function, which would be the mouse_detect() function. The only way I think one can do it is actually checking if the mouse returns a 0xFA in the mouse_read function.
Did anybody find any documention on this?
Perica
Member
Member
Posts: 454
Joined: Sat Nov 25, 2006 12:50 am

Re:Free PS/2 mouse code

Post by Perica »

..
Last edited by Perica on Tue Dec 05, 2006 9:41 pm, edited 1 time in total.
SANiK

Re:Free PS/2 mouse code

Post by SANiK »

Well, all the waits I've seen are loops which repeatedly keep polling the mouse till it's done.

You could add a 'hlt' in there to slow down the processer and to cool off the PC, but it is required to keep polling the mouse. That step seems to be needed. Although, as for the constant looping, one can make a time table of how many Hz it takes the mouse to complete certain operations.
Perica
Member
Member
Posts: 454
Joined: Sat Nov 25, 2006 12:50 am

Re:Free PS/2 mouse code

Post by Perica »

..
Last edited by Perica on Tue Dec 05, 2006 9:41 pm, edited 1 time in total.
User avatar
Brendan
Member
Member
Posts: 8561
Joined: Sat Jan 15, 2005 12:00 am
Location: At his keyboard!
Contact:

Re:Free PS/2 mouse code

Post by Brendan »

Hi,
Perica wrote:About the port input/output waits, what kind of wait would be sufficient (a [tt]nop[/tt], maybe?)?
Some history. Some computers where buggy and didn't delay the CPU long enough when IO ports where accessed. On these buggy computers you need a delay between IO instructions to the same chip/device to give that chip/device time to react. An example here would be changing the PIT chip from lowbyte/highbyte to highbyte only, and then immediately trying to read the count - if the PIT chip hasn't had enough time to react to the first IO write it could still be in lowbyte/highbyte mode when you read the count, so that the lowbyte is read rather than the highbyte.

To prevent this a delay between the IO port accesses is needed on the buggy computers. This delay can be done by accessing an unrelated IO port, or with a near jump.

Fortunately the buggy computers were early 80386 and 80286, and these IO port delays are not needed for anything more modern.

For a much better description of the problem, see section 7.9.4 of "pctim003.txt" (at http://www.contactor.se/~daniel/links/Pctim003.txt).


Cheers,

Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
Post Reply