home *** CD-ROM | disk | FTP | other *** search
/ The CDPD Public Domain Collection for CDTV 1 / CDPD_Vol1.bin / pd / 176-200 / 197 / stevie / tos.c < prev    next >
C/C++ Source or Header  |  1992-06-23  |  6KB  |  313 lines

  1. /*
  2.  * System-dependent routines for the Atari ST. 
  3.  */
  4.  
  5. #include "stevie.h"
  6.  
  7. #include <osbind.h>
  8.  
  9. /*
  10.  * The following buffer is used to work around a bug in TOS. It appears that
  11.  * unread console input can cause a crash, but only if console output is
  12.  * going on. The solution is to always grab any unread input before putting
  13.  * out a character. The following buffer holds any characters read in this
  14.  * fashion. The problem can be easily produced because STEVIE can't yet keep
  15.  * up with the normal auto-repeat rate in insert mode. 
  16.  */
  17. #define    IBUFSZ    128
  18.  
  19. static long     inbuf[IBUFSZ];    /* buffer for unread input */
  20. static long    *inptr = inbuf;    /* where to put next character */
  21.  
  22. /*
  23.  * inchar() - get a character from the keyboard 
  24.  *
  25.  * Certain special keys are mapped to values above 0x80. These mappings are
  26.  * defined in keymap.h. If the key has a non-zero ascii value, it is simply
  27.  * returned. Otherwise it may be a special key we want to map. 
  28.  *
  29.  * The ST has a bug involving keyboard input that seems to occur when typing
  30.  * quickly, especially typing capital letters. Sometimes a value of
  31.  * 0x02540000 is read. This doesn't correspond to anything on the keyboard,
  32.  * according to my documentation. My solution is to loop when any unknown key
  33.  * is seen. Normally, the bell is rung to indicate the error. If the "bug"
  34.  * value is seen, we ignore it completely. 
  35.  */
  36. int
  37. inchar()
  38. {
  39.     for (;;) {
  40.     long            c, *p;
  41.  
  42.     /*
  43.      * Get the next input character, either from the input buffer or
  44.      * directly from TOS. 
  45.      */
  46.     if (inptr != inbuf) {    /* input in the buffer, use it */
  47.         c = inbuf[0];
  48.         /*
  49.          * Shift everything else in the buffer down. This would be
  50.          * cleaner if we used a circular buffer, but it really isn't
  51.          * worth it. 
  52.          */
  53.         inptr--;
  54.         for (p = inbuf; p < inptr; p++)
  55.         *p = *(p + 1);
  56.     } else
  57.         c = Crawcin();
  58.  
  59.     if ((c & 0xff) != 0)
  60.         return ((int) c);
  61.  
  62.     switch ((int) (c >> 16) & 0xff) {
  63.  
  64.       case 0x62:
  65.         return K_HELP;
  66.       case 0x61:
  67.         return K_UNDO;
  68.       case 0x52:
  69.         return K_INSERT;
  70.       case 0x47:
  71.         return K_HOME;
  72.       case 0x48:
  73.         return K_UARROW;
  74.       case 0x50:
  75.         return K_DARROW;
  76.       case 0x4b:
  77.         return K_LARROW;
  78.       case 0x4d:
  79.         return K_RARROW;
  80.       case 0x29:
  81.         return K_CGRAVE;    /* control grave accent */
  82.         /*
  83.          * Occurs due to a bug in TOS. 
  84.          */
  85.       case 0x54:
  86.         break;
  87.         /*
  88.          * Add the function keys here later if we put in support for
  89.          * macros. 
  90.          */
  91.       default:
  92.         beep();
  93.         break;
  94.     }
  95.     }
  96. }
  97. /*
  98.  * get_inchars - snarf away any pending console input 
  99.  *
  100.  * If the buffer overflows, we discard what's left and ring the bell. 
  101.  */
  102. static void
  103. get_inchars()
  104. {
  105.     while (Cconis()) {
  106.     if (inptr >= &inbuf[IBUFSZ]) {    /* no room in buffer? */
  107.         Crawcin();        /* discard the input */
  108.         beep();        /* and sound the alarm */
  109.     } else
  110.         *inptr++ = Crawcin();
  111.     }
  112. }
  113.  
  114. void
  115. outchar(c)
  116.     char            c;
  117. {
  118.     get_inchars();
  119.     Cconout(c);
  120. }
  121.  
  122. void
  123. outstr(s)
  124.     char           *s;
  125. {
  126.     get_inchars();
  127.     Cconws(s);
  128. }
  129.  
  130. #define    BGND    0
  131. #define    TEXT    3
  132.  
  133. /*
  134.  * vbeep() - visual bell 
  135.  */
  136. static void
  137. vbeep()
  138. {
  139.     int             text, bgnd;    /* text and background colors */
  140.     long            l;
  141.  
  142.     text = Setcolor(TEXT, -1);
  143.     bgnd = Setcolor(BGND, -1);
  144.  
  145.     Setcolor(TEXT, bgnd);    /* swap colors */
  146.     Setcolor(BGND, text);
  147.  
  148.     for (l = 0; l < 5000; l++);    /* short pause */
  149.  
  150.     Setcolor(TEXT, text);    /* restore colors */
  151.     Setcolor(BGND, bgnd);
  152. }
  153.  
  154. void
  155. beep()
  156. {
  157.     if (RedrawingDisabled)
  158.     return;
  159.  
  160.     if (P(P_VB))
  161.     vbeep();
  162.     else
  163.     outchar('\007');
  164. }
  165.  
  166. /*
  167.  * remove(file) - remove a file 
  168.  */
  169. void
  170. remove(file)
  171.     char           *file;
  172. {
  173.     Fdelete(file);
  174. }
  175.  
  176. /*
  177.  * rename(of, nf) - rename existing file 'of' to 'nf' 
  178.  */
  179. void
  180. rename(of, nf)
  181.     char           *of, *nf;
  182. {
  183.     Fdelete(nf);        /* if 'nf' exists, remove it */
  184.     Frename(0, of, nf);
  185. }
  186.  
  187. void
  188. windinit()
  189. {
  190.     if (Getrez() == 0)
  191.     Columns = 40;        /* low resolution */
  192.     else
  193.     Columns = 80;        /* medium or high */
  194.  
  195.     P(P_LI) = Rows = 25;
  196.  
  197.     Cursconf(1, NULL);
  198. }
  199.  
  200. void
  201. windexit(r)
  202.     int             r;
  203. {
  204.     exit(r);
  205. }
  206.  
  207. void
  208. windgoto(r, c)
  209.     int             r, c;
  210. {
  211.     outstr("\033Y");
  212.     outchar(r + 040);
  213.     outchar(c + 040);
  214. }
  215.  
  216. #ifndef MWC
  217. /*
  218.  * System calls or library routines missing in TOS. 
  219.  */
  220.  
  221. void
  222. sleep(n)
  223.     int             n;
  224. {
  225.     int             k;
  226.  
  227.     k = Tgettime();
  228.     while (Tgettime() <= k + n);
  229. }
  230. #endif
  231.  
  232. void
  233. delay()
  234. {
  235.     long            n;
  236.  
  237.     for (n = 0; n < 8000; n++);
  238. }
  239.  
  240. #ifndef MWC
  241. int
  242. system(cmd)
  243.     char           *cmd;
  244. {
  245.     char            arg[1];
  246.  
  247.     arg[0] = (char) 0;        /* no arguments passed to the shell */
  248.  
  249.     if (Pexec(0, cmd, arg, 0L) < 0)
  250.     return -1;
  251.     else
  252.     return 0;
  253. }
  254. #endif
  255.  
  256. #ifdef    MEGAMAX
  257. char           *
  258. strchr(s, c)
  259.     char           *s;
  260.     int             c;
  261. {
  262.     do {
  263.     if (*s == c)
  264.         return (s);
  265.     } while (*s++);
  266.     return (NULL);
  267. }
  268. #endif
  269.  
  270. #ifdef    FOPENB
  271.  
  272. FILE           *
  273. fopenb(fname, mode)
  274.     char           *fname;
  275.     char           *mode;
  276. {
  277.     char            modestr[10];
  278.  
  279.     sprintf(modestr, "b%s", mode);
  280.  
  281.     return fopen(fname, modestr);
  282. }
  283.  
  284. #endif
  285.  
  286. #ifndef MWC
  287. /*
  288.  * getenv() - get a string from the environment 
  289.  *
  290.  * Both Alcyon and Megamax are missing getenv(). This routine works for both
  291.  * compilers and with the Beckemeyer and Gulam shells. With gulam, the
  292.  * env_style variable should be set to either "mw" or "gu". 
  293.  */
  294. char           *
  295. getenv(name)
  296.     char           *name;
  297. {
  298.     extern long     _base;
  299.     char           *envp, *p;
  300.  
  301.     envp = *((char **) (_base + 0x2c));
  302.  
  303.     for (; *envp; envp += strlen(envp) + 1) {
  304.     if (strncmp(envp, name, strlen(name)) == 0) {
  305.         p = envp + strlen(name);
  306.         if (*p++ == '=')
  307.         return p;
  308.     }
  309.     }
  310.     return (char *) 0;
  311. }
  312. #endif
  313.