home *** CD-ROM | disk | FTP | other *** search
/ GEMini Atari / GEMini_Atari_CD-ROM_Walnut_Creek_December_1993.iso / files / gnu / libsrc87 / read.c < prev    next >
Encoding:
C/C++ Source or Header  |  1993-07-30  |  5.9 KB  |  335 lines

  1. /*
  2.  *        Cross Development System for Atari ST 
  3.  *     Copyright (c) 1988, Memorial University of Newfoundland
  4.  *
  5.  * See ChangeLog for further history  ++jrb
  6.  *
  7.  * 1.5        ERS    modified for benefit of 16 bit compilers
  8.  * 1.4        ERS
  9.  *     Changed BIOS calls into GEMDOS calls.
  10.  *
  11.  * 1.3        jrd
  12.  *
  13.  * Revision 1.2  88/02/03  22:56:30  m68k
  14.  * Added unix like tty driver stuff
  15.  * 
  16.  * Revision 1.1  88/01/29  17:31:39  m68k
  17.  * Initial revision
  18.  * 
  19.  */
  20. #include    <osbind.h>
  21. #include    <ioctl.h>
  22. #include    <signal.h>
  23. #include    <tchars.h>
  24. #include    <unistd.h>
  25. #include    <device.h>
  26. #include    <limits.h>
  27. #include     <errno.h>
  28. #include    "lib.h"
  29. #ifndef _COMPILER_H
  30. #include <compiler.h>
  31. #endif
  32.  
  33. #define    iswhite(c)    ((c) == ' ' || (c) == '\t')
  34. #define    isvisable(c)    ((unsigned char)(c) >= ' ')
  35. #define    echochar(fd, c)    if (__ttymode & ECHO) (void) _echochar(fd, c); else
  36. #define    delchar(fd, n)    if (__ttymode & ECHO) _delchar(fd, n); else
  37.  
  38. extern int    errno;
  39. extern int    __col_pos;    /* defined in write.c */
  40. static int    start_col;
  41. static char    *thebuf;
  42.  
  43. static int _echochar __PROTO((int fd, int c));
  44. static void _delchar __PROTO((int fd, int n));
  45. static int str_length __PROTO((char *p, int n));
  46.  
  47. extern unsigned int console_read_byte(int);
  48. extern void console_write_byte(int, int);
  49. extern int console_input_status(int);
  50.  
  51. #ifdef __MSHORT__
  52. int
  53. read(fd, buf, nbytes)
  54.     int    fd;
  55.     void    *buf;
  56.     unsigned int    nbytes;
  57. {
  58.       return (int)(_read(fd, buf, (unsigned long) nbytes));
  59. }
  60.  
  61. #else
  62.  
  63. asm(".stabs \"_read\",5,0,0,__read"); /* dept of clean tricks */
  64.  
  65. #endif
  66.  
  67. long
  68. _read(fd, buf, n)
  69.         int     fd;
  70.         void    *buf;
  71.         unsigned long    n;
  72.   {
  73.     long        rval, nbytes;
  74.     long            cnt = 0;
  75.     char        *p = buf;
  76.     struct _device    *dev;
  77.  
  78.     if(n > ((unsigned long)LONG_MAX))
  79.     {
  80.         errno = EBADARG;
  81.         return -1L;
  82.     }
  83.  
  84.     nbytes = (long)n;
  85.     if ((dev = _dev_fd(fd)) && dev->read)
  86.         return (*dev->read)(fd, buf, nbytes);
  87.  
  88.     if (!isatty(fd))
  89.         { /* really cant do much about the signdness of nbytes here */
  90.         if ((rval = Fread(fd, nbytes, buf)) < 0) 
  91.             {
  92.             errno = -rval;
  93.             rval = -1;
  94.             }
  95.         return rval;
  96.         }
  97.     thebuf = buf;
  98.     start_col = __col_pos;
  99.     while (1) {
  100.         *p = console_read_byte(fd);
  101.         if (__ttymode & RAW) 
  102.             {
  103.             if (__ttymode & ECHO) 
  104.                 {
  105.                 console_write_byte(fd, *p);
  106.                 if (*p == '\r')
  107.                     __col_pos = 0;
  108.                 else if (isvisable(*p))
  109.                     __col_pos++;
  110.                 }
  111.             if (++cnt >= nbytes || !console_input_status(fd))
  112.                 return cnt;
  113.             p++;
  114.             continue;
  115.             }
  116.         if ((__ttymode & CRMOD) && *p == '\r')
  117.             *p = '\n';
  118.         if (*p == __tchars[TC_INTRC]) 
  119.             {
  120.             /* Do the bsd thing here, i.e. flush buffers
  121.              * and continue to read after the interupt
  122.              */
  123.             echochar(fd, *p);
  124.             p = buf;
  125.             cnt = 0;
  126.             raise(SIGINT);
  127.             } 
  128.             else 
  129.         if (*p == __tchars[TC_QUITC]) 
  130.             {
  131.             echochar(fd, *p);
  132.             p = buf;
  133.             cnt = 0;
  134.             raise(SIGQUIT);
  135.             }
  136.         if (__ttymode & CBREAK) 
  137.             {
  138.             if (*p == __tchars[TC_LNEXTC])
  139.                 *p = console_read_byte(fd);
  140.             if (__ttymode & ECHO) 
  141.                 {
  142.                 if (*p == '\n' && (__ttymode & CRMOD)) 
  143.                     {
  144.                     console_write_byte(fd, '\n');
  145.                     console_write_byte(fd, '\r');
  146.                     __col_pos = 0;
  147.                     } 
  148.                     else
  149.                     (void) _echochar(fd, *p);
  150.                 }
  151.             ++cnt;
  152.  
  153.             if (!console_input_status(fd))
  154.                 return cnt;
  155.             p++;
  156.             } 
  157.             else
  158.         if (*p == __tchars[TC_LNEXTC]) 
  159.             {
  160.             if (__ttymode & ECHO) 
  161.                 {
  162.                 console_write_byte(fd, '^');
  163.                 console_write_byte(fd, '\b');
  164.                 }
  165.             *p = console_read_byte(fd);
  166.             echochar(fd, *p++);
  167.             cnt++;
  168.             }
  169.             else
  170.         if (*p == __tchars[TC_EOFC]) 
  171.             {
  172.             if (__ttymode & ECHO)
  173.                 {
  174.                 int i = _echochar(fd, *p);
  175.                 __col_pos -= i;
  176.                 while (i-- > 0)
  177.                     console_write_byte(fd, '\b');
  178.                 }
  179.             return cnt;
  180.             }
  181.             else
  182.         if (*p == '\n' || *p == __tchars[TC_BRKC]) 
  183.             {
  184.             if (__ttymode & ECHO)
  185.                 if (*p == '\n')
  186.                     {
  187.                     console_write_byte(fd, '\n');
  188.                     if (__ttymode & CRMOD) 
  189.                         {
  190.                         console_write_byte(fd, '\r');
  191.                         __col_pos = 0;
  192.                         }
  193.                     }
  194.                     else
  195.                     (void) _echochar(fd, *p);
  196.             return ++cnt;
  197.             }
  198.             else
  199.         if ((*p == __tchars[TC_ERASE]) || (*p == __tchars[TC_ERASE]))
  200.             {
  201.             if (cnt) 
  202.                 {
  203.                 --p; --cnt;
  204.                 delchar(fd, (int)cnt);
  205.                 }
  206.             }
  207.             else
  208.         if (*p == __tchars[TC_KILL]) 
  209.             {
  210.             while (--cnt >= 0) 
  211.                 {
  212.                 delchar(fd, (int)cnt);
  213.                 p--;
  214.                 }
  215.             cnt = 0;
  216.             } 
  217.             else
  218.         if (*p == __tchars[TC_WERASC]) 
  219.             {
  220.             p--;
  221.             while (cnt && iswhite(*p)) 
  222.                 {
  223.                 --p; --cnt;
  224.                 delchar(fd, (int)cnt);
  225.                 }
  226.             while (cnt && !iswhite(*p)) 
  227.                 {
  228.                 --p; --cnt;
  229.                 delchar(fd, (int)cnt);
  230.                 }
  231.             p++;
  232.             }
  233.             else
  234.         if (*p == __tchars[TC_RPRNTC]) 
  235.             {
  236.             char    *s;
  237.  
  238.             echochar(fd, __tchars[TC_RPRNTC]);
  239.             console_write_byte(fd, '\r');
  240.             console_write_byte(fd, '\n');
  241.             __col_pos = 0;
  242.             start_col = 0;
  243.             if (__ttymode & ECHO)
  244.                 for (s = buf ; s < p ; s++)
  245.                     echochar(fd, *s);
  246.             }
  247.             else
  248.             {
  249.             echochar(fd, *p); p++;
  250.             cnt++;
  251.             }
  252.         if (cnt >= nbytes)
  253.             return cnt;
  254.     }
  255.     /*NOTREACHED*/
  256. }
  257.  
  258. static    int
  259. _echochar(fd, c)
  260.     int    fd;
  261.     int    c;
  262. {
  263.     int    len = 0;
  264.  
  265.     c &= 0xff;
  266.     if (c < ' ') {
  267.         if (c == '\t') {
  268.             int    i;
  269.  
  270.             len = ((__col_pos | 7) + 1) - __col_pos;
  271.             if (__ttymode & XTABS)
  272.                 for (i = len ; i-- ;)
  273.                     console_write_byte(fd, ' ');
  274.             else
  275.                 console_write_byte(fd, '\t');
  276.         } else {
  277.             console_write_byte(fd, '^');
  278.             console_write_byte(fd, c + 0x40);
  279.             len += 2;
  280.         }
  281.     } else if (c == 0x7f) {
  282.         console_write_byte(fd, '^');
  283.         console_write_byte(fd, '?');
  284.         len += 2;
  285.     } else {
  286.         console_write_byte(fd, c);
  287.         len++;
  288.     }
  289.     __col_pos += len;
  290.     return len;
  291. }
  292.  
  293. static    void
  294. _delchar(fd, n)
  295.     int    fd, n;
  296. {
  297.     int    len = 0;
  298.     char    c = thebuf[n];
  299.  
  300.     if ((c >= 0 && c < ' ') || c == 0x7f) {
  301.         if (c == '\t')
  302.             len = __col_pos - str_length(thebuf, n);
  303.         else
  304.             len += 2;
  305.     } else
  306.         len++;
  307.     __col_pos -= len;
  308.     while (len--) {
  309.         console_write_byte(fd, '\b');
  310.         console_write_byte(fd, ' ');
  311.         console_write_byte(fd, '\b');
  312.     }
  313. }
  314.  
  315. static    int
  316. str_length(p, n)
  317.     char    *p;
  318.     int    n;
  319. {
  320.     int    pos = start_col;
  321.     char    c;
  322.  
  323.     while (n--) {
  324.         c = *p++;
  325.         if ((c >= 0 && c < ' ') || c == 0x7f)
  326.             if (c == '\t')
  327.                 pos = (pos | 7) + 1;
  328.             else
  329.                 pos += 2;
  330.         else
  331.             pos++;
  332.     }
  333.     return pos;
  334. }
  335.