home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 5 Edit / 05-Edit.zip / jove414s.zip / os2kbd.c < prev    next >
C/C++ Source or Header  |  1991-07-08  |  5KB  |  195 lines

  1. #include "jove.h"
  2. #include <signal.h>
  3. #include <errno.h>
  4. #include <fcntl.h>
  5. #include <process.h>
  6.  
  7. #ifdef OS2
  8. #define INCL_BASE
  9. #include <os2.h>
  10. unsigned long kbd_ram_sem;    /* define a RAM semaphore to */
  11.  /* control kbd process */
  12.  
  13. #define SIGKBD SIGUSR1        /* kbd special signal */
  14. struct _iobuf {
  15.     char _FAR_ *_ptr;
  16.     int _cnt;
  17.     char _FAR_ *_base;
  18.     char _flag;
  19.     char _file;
  20. };
  21. typedef struct _iobuf FILE;
  22. /* declare _iob[] array */
  23.  
  24. #ifndef _STDIO_DEFINED
  25. #ifdef _DLL
  26. extern FILE _FAR_ _cdecl _iob[];
  27. #else
  28. extern FILE _near _cdecl _iob[];
  29. #endif
  30. #endif
  31.  
  32.  
  33. /* define file position type */
  34.  
  35. #ifndef _FPOS_T_DEFINED
  36. typedef long fpos_t;
  37. #define _FPOS_T_DEFINED
  38. #endif
  39.  
  40. /* standard file pointers */
  41.  
  42. #define stdin  (&_iob[0])
  43. #define stderr (&_iob[2])
  44. #define stdaux (&_iob[3])
  45. #define stdprn (&_iob[4])
  46.  
  47. int kbhit (void);
  48. int getpid (void);
  49. int read (int handle, void *buffer, unsigned int count);
  50. int write (int handle, void *buffer, unsigned int count);
  51.  
  52. #endif                /* OS2 */
  53.  
  54. /* prototypes */
  55. static SIGRESULT hold_read (int dummy);
  56. static SIGRESULT strt_read (int dummy);
  57. static void _fastcall kbd_reset (void);
  58.  
  59. #ifdef BSD_SIGS
  60. #define pause()    sigpause(0L)
  61. #endif
  62.  
  63. #define CR 13
  64. #define LF 10
  65. #define ESC 0x1B
  66. #define CNTL_X 0x18
  67. #define CNTL_U 0x15
  68. #define CHAR_WAIT_TIME 500L
  69. #define SHORT_INT      50L
  70.  
  71. struct header {
  72.     int pid, nbytes;
  73.     char buf[10];
  74. };
  75.  
  76. #define HEADER_SIZE    (2 * sizeof (int))
  77.  
  78. /* JOVE sends SIGKBD whenever it wants the kbd process (this program)
  79.    to stop competing for input from the keyboard.  JOVE does this when
  80.    JOVE realizes that there are no more interactive processes running.
  81.    The reason we go through all this trouble is that JOVE slows down
  82.    a lot when it's getting its keyboard input via a pipe. */
  83.  
  84. /*************************************/
  85. static SIGRESULT hold_read (int dummy)
  86. /*************************************/
  87.  /* DUMMY passed in when invoked by a signal; of no interest */
  88. {
  89.     kbd_reset ();
  90.     signal (SIGKBD, strt_read);
  91. /* set semaphore to high and then wait until next SIGKBD call */
  92.     DosSemSet (&kbd_ram_sem);
  93.     DosSemRequest (&kbd_ram_sem, -1L);
  94.     SIGRETURN;
  95. }
  96.  
  97. /**************************************/
  98. static SIGRESULT strt_read (int dummy)
  99. /**************************************/
  100. {
  101.     KBDKEYINFO KeyInfo;
  102.     short        kbd_code = 0;
  103.     unsigned char    buffer[10];
  104.     int        n_read = 0, n_written;
  105.     unsigned char    c, scan_code;
  106.     struct header    header;
  107.     unsigned short    wait_for_char;
  108.     long        time_to_wait;
  109.     HSEM        hSem;
  110.     HTIMER        TimeHandle;
  111.  
  112.  
  113. /* reintialize header */
  114.     header.pid = getpid ();
  115.     signal (SIGKBD, hold_read);
  116.     kbd_reset ();
  117.     header.nbytes = 0;
  118.     while (1) {
  119.     while ((kbhit() != 0) && kbd_code == 0) {
  120.         kbd_code = KbdCharIn (&KeyInfo, IO_NOWAIT, 0);
  121.         c = KeyInfo.chChar;
  122.         scan_code = KeyInfo.chScan;
  123.         if (c <= 0xFF && c != 0xE0) {
  124.               header.buf[n_read++] = c;
  125.           } else {
  126.               header.buf[n_read++] = 0xff;
  127.               header.buf[n_read++] = scan_code;
  128.         }
  129. /* wait extra time if first charater needs second to make sense */
  130.     wait_for_char = ((n_read == 1) &&
  131.              (c == ESC || c == CNTL_X || c == CNTL_U));
  132.     if (wait_for_char){
  133.         time_to_wait = CHAR_WAIT_TIME;
  134.         while (time_to_wait >= 0) {
  135.             DosSleep (SHORT_INT);
  136.             if (kbhit ()) break;
  137.             time_to_wait -= SHORT_INT;
  138.         }
  139.     }
  140.  
  141.     }
  142.     if (n_read != 0) {
  143.         header.nbytes = n_read;
  144.         DosWrite (1, (void *) &header, HEADER_SIZE + n_read, &n_written);
  145.         n_read = 0;
  146.     }
  147.     DosSleep (50L);
  148.     kbd_reset ();
  149.     
  150.     }
  151.     SIGRETURN;
  152. }
  153.  
  154. /*******************************/
  155. int main (int argc, char **argv)
  156. /*******************************/
  157. {
  158.     struct header header;
  159.     int pid;
  160.     int trans_mode;
  161.     int fd;
  162.  
  163.  
  164. //translation mode of stdin / out / err
  165.     trans_mode = (setmode(0, O_BINARY) == O_BINARY);
  166.     trans_mode = (setmode(1, O_BINARY) == O_BINARY);
  167.     trans_mode = (setmode(2, O_BINARY) == O_BINARY);
  168.  
  169.     signal(SIGINT, SIG_IGN);
  170.     pid = getpid();
  171.     header.pid = pid;
  172.  
  173.     hold_read(0);
  174.     return 0;
  175. }
  176.  
  177. /*************************************/
  178. static void _fastcall kbd_reset (void)
  179. /*************************************/
  180. /* reset keyboard before starting any kbd input */
  181. {
  182.     KBDINFO kbdInfo;
  183.  
  184.     kbdInfo.cb = 0x000A;
  185.     KbdGetStatus(&kbdInfo, 0);
  186.     kbdInfo.fsMask &= ~0x0001;    /* not echo on        */
  187.     kbdInfo.fsMask |= 0x0002;    /* echo off        */
  188.     kbdInfo.fsMask &= ~0x0008;    /* cooked mode off    */
  189.     kbdInfo.fsMask |= 0x0004;    /* raw mode        */
  190.     kbdInfo.fsMask &= ~0x0100;    /* shift report    off    */
  191.     //kbdInfo.fsMask = (KEYBOARD_ECHO_OFF | KEYBOARD_ASCII_MODE);
  192.     KbdSetStatus(&kbdInfo, 0);
  193.     return;
  194. }
  195.