/[gxemul]/trunk/src/devices/dev_pckbc.c
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Diff of /trunk/src/devices/dev_pckbc.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 29 by dpavlin, Mon Oct 8 16:19:56 2007 UTC revision 30 by dpavlin, Mon Oct 8 16:20:40 2007 UTC
# Line 25  Line 25 
25   *  SUCH DAMAGE.   *  SUCH DAMAGE.
26   *     *  
27   *   *
28   *  $Id: dev_pckbc.c,v 1.65 2006/03/04 12:38:48 debug Exp $   *  $Id: dev_pckbc.c,v 1.69 2006/07/25 18:58:02 debug Exp $
29   *     *  
30   *  Standard 8042 PC keyboard controller (and a 8242WB PS2 keyboard/mouse   *  Standard 8042 PC keyboard controller (and a 8242WB PS2 keyboard/mouse
31   *  controller), including the 8048 keyboard chip.   *  controller), including the 8048 keyboard chip.
32   *   *
33     *  Quick source of good info: http://my.execpc.com/~geezer/osd/kbd/kbd.txt
34   *   *
35   *  TODO: Finish the rewrite for 8242.   *
36     *  TODOs:
37     *      Finish the rewrite for 8242.
38   */   */
39    
40  #include <stdio.h>  #include <stdio.h>
# Line 98  struct pckbc_data { Line 101  struct pckbc_data {
101  #define STATE_LDCMDBYTE                 1  #define STATE_LDCMDBYTE                 1
102  #define STATE_RDCMDBYTE                 2  #define STATE_RDCMDBYTE                 2
103  #define STATE_WAITING_FOR_TRANSLTABLE   3  #define STATE_WAITING_FOR_TRANSLTABLE   3
104  #define STATE_WAITING_FOR_F3            4  #define STATE_WAITING_FOR_RATE          4
105  #define STATE_WAITING_FOR_FC            5  #define STATE_WAITING_FOR_ONEKEY_MB     5
106  #define STATE_WAITING_FOR_AUX           6  #define STATE_WAITING_FOR_AUX           6
107  #define STATE_WAITING_FOR_AUX_OUT       7  #define STATE_WAITING_FOR_AUX_OUT       7
108  #define STATE_LDOUTPUT                  8  #define STATE_LDOUTPUT                  8
# Line 457  void dev_pckbc_tick(struct cpu *cpu, voi Line 460  void dev_pckbc_tick(struct cpu *cpu, voi
460          for (port_nr=0; port_nr<2; port_nr++) {          for (port_nr=0; port_nr<2; port_nr++) {
461                  /*  Cause receive interrupt, if there's something in the                  /*  Cause receive interrupt, if there's something in the
462                      receive buffer: (Otherwise deassert the interrupt.)  */                      receive buffer: (Otherwise deassert the interrupt.)  */
463                    int irq = port_nr==0? d->keyboard_irqnr : d->mouse_irqnr;
464    
465                  if (d->head[port_nr] != d->tail[port_nr] && ints_enabled) {                  if (d->head[port_nr] != d->tail[port_nr] && ints_enabled) {
466                          debug("[ pckbc: interrupt port %i ]\n", port_nr);                          debug("[ pckbc: interrupt port %i ]\n", port_nr);
467                          cpu_interrupt(cpu, port_nr==0? d->keyboard_irqnr                          cpu_interrupt(cpu, irq);
                             : d->mouse_irqnr);  
468                          d->currently_asserted[port_nr] = 1;                          d->currently_asserted[port_nr] = 1;
469                  } else {                  } else {
470                          if (d->currently_asserted[port_nr])                          if (d->currently_asserted[port_nr])
471                                  cpu_interrupt_ack(cpu, port_nr==0?                                  cpu_interrupt_ack(cpu, irq);
                                     d->keyboard_irqnr : d->mouse_irqnr);  
472                          d->currently_asserted[port_nr] = 0;                          d->currently_asserted[port_nr] = 0;
473                  }                  }
474          }          }
# Line 500  static void dev_pckbc_command(struct pck Line 503  static void dev_pckbc_command(struct pck
503                  return;                  return;
504          }          }
505    
506          if (d->state == STATE_WAITING_FOR_F3) {          if (d->state == STATE_WAITING_FOR_RATE) {
507                  debug("[ pckbc: (port %i) received '0xf3' data: "                  debug("[ pckbc: (port %i) received Typematic Rate data: "
508                      "0x%02x ]\n", port_nr, cmd);                      "0x%02x ]\n", port_nr, cmd);
509                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
510                  d->state = STATE_NORMAL;                  d->state = STATE_NORMAL;
511                  return;                  return;
512          }          }
513    
514          if (d->state == STATE_WAITING_FOR_FC) {          if (d->state == STATE_WAITING_FOR_ONEKEY_MB) {
515                  debug("[ pckbc: (port %i) received '0xfc' data: "                  debug("[ pckbc: (port %i) received One-key make/break data: "
516                      "0x%02x ]\n", port_nr, cmd);                      "0x%02x ]\n", port_nr, cmd);
517                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
518                  d->state = STATE_NORMAL;                  d->state = STATE_NORMAL;
# Line 535  static void dev_pckbc_command(struct pck Line 538  static void dev_pckbc_command(struct pck
538          }          }
539    
540          switch (cmd) {          switch (cmd) {
541    
542          case 0x00:          case 0x00:
543                    /*
544                     *  TODO: What does this do? This is possibly due to an
545                     *  error in the handling of some other command code.
546                     */
547                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
548                  break;                  break;
549    
550          case KBC_MODEIND:       /*  Set LEDs  */          case KBC_MODEIND:       /*  Set LEDs  */
551                  /*  Just ACK, no LEDs are actually set.  */                  /*  Just ACK, no LEDs are actually set.  */
552                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
553                  break;                  break;
554    
555          case KBC_SETTABLE:          case KBC_SETTABLE:
556                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
557                  d->state = STATE_WAITING_FOR_TRANSLTABLE;                  d->state = STATE_WAITING_FOR_TRANSLTABLE;
558                  break;                  break;
559    
560          case KBC_ENABLE:          case KBC_ENABLE:
561                  d->keyscanning_enabled = 1;                  d->keyscanning_enabled = 1;
562                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
563                  break;                  break;
564    
565          case KBC_DISABLE:          case KBC_DISABLE:
566                  d->keyscanning_enabled = 0;                  d->keyscanning_enabled = 0;
567                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
568                  break;                  break;
569    
570          case KBC_SETDEFAULT:          case KBC_SETDEFAULT:
571                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
572                  break;                  break;
573          case 0xf3:  
574            case KBC_GETID:
575                    /*  Get keyboard ID.  NOTE/TODO: Ugly hardcoded answer.  */
576                    pckbc_add_code(d, KBR_ACK, port_nr);
577                    pckbc_add_code(d, 0xab, port_nr);
578                    pckbc_add_code(d, 0x41, port_nr);
579                    break;
580    
581            case KBC_TYPEMATIC:
582                    /*  Set typematic (auto-repeat) delay/speed:  */
583                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
584                  d->state = STATE_WAITING_FOR_F3;                  d->state = STATE_WAITING_FOR_RATE;
585                  break;                  break;
586          case 0xfa:      /*  Just ack?  */  
587            case KBC_ALLKEYS_TMB:
588                    /*  "Make all keys typematic/make/break"  */
589                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
590                  break;                  break;
591          case 0xfc:  
592            case KBC_ONEKEY_MB:
593                    /*  "Make one key typematic/make/break"  */
594                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
595                  d->state = STATE_WAITING_FOR_FC;                  d->state = STATE_WAITING_FOR_ONEKEY_MB;
596                  break;                  break;
597    
598          case KBC_RESET:          case KBC_RESET:
599                  pckbc_add_code(d, KBR_ACK, port_nr);                  pckbc_add_code(d, KBR_ACK, port_nr);
600                  pckbc_add_code(d, KBR_RSTDONE, port_nr);                  pckbc_add_code(d, KBR_RSTDONE, port_nr);
601                    /*
602                     *  Disable interrupts during reset, or Linux 2.6
603                     *  prints warnings about spurious interrupts.
604                     */
605                    d->rx_int_enable = 0;
606                  break;                  break;
607    
608          default:          default:
609                  fatal("[ pckbc: (port %i) UNIMPLEMENTED 8048 command"                  fatal("[ pckbc: (port %i) UNIMPLEMENTED 8048 command"
610                      " 0x%02x ]\n", port_nr, cmd);                      " 0x%02x ]\n", port_nr, cmd);
611                    exit(1);
612          }          }
613  }  }
614    
615    
 /*  
  *  dev_pckbc_access():  
  */  
616  DEVICE_ACCESS(pckbc)  DEVICE_ACCESS(pckbc)
617  {  {
618          uint64_t idata = 0, odata = 0;          uint64_t idata = 0, odata = 0;

Legend:
Removed from v.29  
changed lines
  Added in v.30

  ViewVC Help
Powered by ViewVC 1.1.26