home *** CD-ROM | disk | FTP | other *** search
/ Power Programming / powerprogramming1994.iso / progtool / microcrn / issue_40.arc / KBDTEST.ARC / KBDTEST.C next >
Text File  |  1988-01-11  |  7KB  |  163 lines

  1. /* Code from 86World column in Micro Cornucopia Issue #40 */
  2.  
  3. /* KBDTEST.C - a progam to demonstrate interrupt 9 (the keyboard hardware
  4.                interrupt) and test for proper operation of all keys on an
  5.                IBM compatible keyboard.
  6.  
  7.     METHOD:   The keyboard interrupt service vector is saved and replaced
  8.               with a pointer to our own routine which simply prints a
  9.               little message somewhere on the screen according to which
  10.               key is pressed. By doing this, the screen can give a graphic
  11.               display of which keys the computer thinks are pressed at any
  12.               given time.
  13.  
  14.               If there is a difference between what is shown on the screen
  15.               and what is pushed down on the keyboard, then the keyboard
  16.               very likely has some design flaws, either in hardware or in
  17.               the firmware on the keyboard MPU.
  18.  
  19.     COMPILING:Use the file kbdtest.prj as your project file, and MAKE
  20.               SURE YOU USE A LARGE DATA MODEL!! The program works under
  21.               compact and large, but it doesn't work under tiny, small,
  22.               or medium. I haven't tried huge. Be sure to compile video.c
  23.               with the same memory model.
  24.  
  25.               Required Files: KBDTEST.C, KBDTEST.PRJ, VIDEO.C, VIDEO.H,
  26.                               MCMVSMEM.OBJ, normal C libraries, etc.
  27.  
  28.     NOTES:    Feel free to use any part of this program anywhere you like,
  29.               with NO restrictions. Just remember me kindly.
  30.  
  31.               originally written in Pascal, Feb. 16, 1987
  32.               translated from original into C, Dec 13, 1987
  33.  
  34.                                             Laine Stump, Dec 13, 1987
  35.                                                                         */
  36. #include <dos.h>
  37. #include <stdarg.h>   /* needed for va_arg in video.h */
  38. #include "video.h"
  39.  
  40. #define ESCLIMIT 25   /* # of consec. ESC presses to mean "exit" */
  41. #define KEYLIMIT 83   /* higher for models w/F11 & F12 keys */
  42.  
  43. struct
  44.   {
  45.   char message[6];
  46.   unsigned char col, row;
  47.   } keydisp[KEYLIMIT] = {
  48.     {"Es",18,9},   {"1!",21,9},    {"2@",24,9},  {"3#",27,9},  {"4$",30,9},
  49.     {"5%",33,9},   {"6^",36,9},    {"7&",39,9},  {"8*",42,9},  {"9(",45,9},
  50.     {"0)",48,9},   {"-_",51,9},    {"=+",54,9},  {"<───",57,9},{"Tab",18,11},
  51.     {"Qq",22,11},  {"Ww",25,11},   {"Ee",28,11}, {"Rr",31,11}, {"Tt",34,11},
  52.     {"Yy",37,11},  {"Uu",40,11},   {"Ii",43,11}, {"Oo",46,11}, {"Pp",49,11},
  53.     {"{[",52,11},  {"}]",55,11},   {"<┘",59,12}, {"Ctrl",18,13},{"Aa",23,13},
  54.     {"Ss",26,13},  {"Dd",29,13},   {"Ff",32,13}, {"Gg",35,13}, {"Hh",38,13},
  55.     {"Jj",41,13},  {"Kk",44,13},   {"Ll",47,13}, {":;",50,13}, {"\"'",53,13},
  56.     {"~`",56,13},  {"LS",18,15},   {"|\\",21,15},{"Zz",24,15}, {"Xx",27,15},
  57.     {"Cc",30,15},  {"Vv",33,15},   {"Bb",36,15}, {"Nn",39,15}, {"Mm",42,15},
  58.     {"<,",45,15},  {">.",48,15},   {"?/",51,15}, {"RS",55,15}, {"PS",59,15},
  59.     {"Alt",19,17}, {"Space",34,17}, {"Caps",54,17},{"F1",9,9}, {"F2",12,9},
  60.     {"F3",9,11},   {"F4",12,11},   {"F5",9,13},  {"F6",12,13}, {"F7",9,15},
  61.     {"F8",12,15},  {"F9",9,17},    {"F0",12,17}, {"Num",63,9}, {"Scrl",69,9},
  62.     {"Hm",62,11},  {" ^",65,11},   {"Pu",68,11}, {" -",71,11}, {"< ",62,13},
  63.     {" 5",65,13},  {" >",68,13},   {" +",71,15}, {"En",62,15}, {" v",65,15},
  64.     {"Pd",68,15},  {"Ins",60,17},  {"Del",66,17}
  65.     };
  66.  
  67. /* static globals */
  68. int escctr;
  69. void interrupt (*int9save)();  /* a place to save address of old */
  70.                                /* interrupt handler */
  71.  
  72. /* the routine that will be executed for every keypress */
  73. void interrupt int9service()
  74. /* a basic outline: read kbd data port
  75.                     act on the key
  76.                     strobe acknowledge of kbd control port
  77.                     signal end of interrupt to int controller
  78.                     return
  79. */
  80.     {
  81.     unsigned char scancode;
  82.  
  83.     /* should enable interrupts here, but I don't feel like
  84.        getting out the command line version of the compiler
  85.        for just one line of assembly (maybe it's already done??) */
  86.  
  87.     scancode = inportb(0x60);    /* get input from keyboard */
  88.     if ((scancode & 0x7F) == 1)  /* check for ESC (scan code 1) */
  89.         {
  90.         if (scancode > 0x7F)
  91.             escctr = 0;
  92.         else
  93.             escctr++;
  94.           }
  95.     /* display or undisplay a key */
  96.     if (scancode > 0x7F)
  97.         in(NORMAL);
  98.     else
  99.         in(REVERSE);
  100.     scancode &= 0x7F;
  101.     if ((scancode > 0) && (scancode <= KEYLIMIT))
  102.         {
  103.         scancode--; /* convert position to offset */
  104.         at(keydisp[scancode].row,keydisp[scancode].col);
  105.         cprintf("%s",keydisp[scancode].message);
  106.         }
  107.     else
  108.         {
  109.         at(20,39);
  110.         cprintf("%2X",(int) scancode);
  111.         }
  112.     /* signal EOI to kbd & controller */
  113.     outportb(0x61,inportb(0x61) | 0x80);
  114.     outportb(0x61,inportb(0x61) & 0x7F);
  115.     outportb(0x20,0x20);
  116.     }   /* int9service */
  117.  
  118. void printkbd(void)
  119. /* put up a graphical representation of an IBM XT keyboard */
  120. {
  121. at(1,32); in(REVERSE); cprintf(" KBDTEST v1.1 ");
  122. in(NORMAL);
  123. at(8,8);
  124. cprintf("┌──┬──┐  ┌──┬──┬──┬──┬──┬──┬──┬──┬──┬──┬──┬──┬──┬────┬─────┬─────┐");
  125. at(9, 8);
  126. cprintf("│F1│F2│  │Es│1!│2@│3#│4$│5%│6^│7&│8*│9(│0)│-_│=+│<───│ Num │ Scrl│");
  127. at(10,8);
  128. cprintf("├──┼──┤  ├──┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴─┬──┼──┬──┼──┬──┤");
  129. at(11,8);
  130. cprintf("│F3│F4│  │Tab│Qq│Ww│Ee│Rr│Tt│Yy│Uu│Ii│Oo│Pp│{[│}] │  │Hm│ ^│Pu│ -│");
  131. at(12,8);
  132. cprintf("├──┼──┤  ├───┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬──┤<┘├──┼──┼──┼──┤");
  133. at(13,8);
  134. cprintf("│F5│F6│  │Ctrl│Aa│Ss│Dd│Ff│Gg│Hh│Jj│Kk│Ll│:;│\"'│~`│  │< │ 5│ >│  │");
  135. at(14,8);
  136. cprintf("├──┼──┤  ├──┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴┬─┴──┼──┼──┼──┼──┤  │");
  137. at(15,8);
  138. cprintf("│F7│F8│  │LS│|\\│Zz│Xx│Cc│Vv│Bb│Nn│Mm│<,│>.│?/│ RS │PS│En│ v│Pd│ +│");
  139. at(16,8);
  140. cprintf("├──┼──┤  ├──┴─┬┴──┴──┴──┴──┴──┴──┴──┴──┴──┴─┬┴────┼──┴──┼──┴──┤  │");
  141. at(17,8);
  142. cprintf("│F9│F0│  │ Alt│           Space             │ Caps│ Ins │ Del │  │");
  143. at(18,8);
  144. cprintf("└──┴──┘  └────┴─────────────────────────────┴─────┴─────┴─────┴──┘");
  145.  
  146. at(22,23); in(REVERSE); cprintf(" hold down ESC for 3 sec. to Exit ");
  147. }   /* printkbd */
  148.  
  149. /*-------------------------*/
  150. main()
  151.     {
  152.     initvideo();
  153.     printkbd();
  154.  
  155.     escctr = 0;
  156.     int9save = getvect(9);
  157.     setvect(9,int9service);
  158.     while (escctr < ESCLIMIT) /* wait until the signal to end */
  159.         ;
  160.     setvect(9,int9save);       /* restore old service so we don't have */
  161.     in(NORMAL); clearscreen(); /* to reach for the BRS (Big Red Switch) */
  162.     }   /* main */
  163.