home *** CD-ROM | disk | FTP | other *** search
/ hobbes.nmsu.edu / 2008-06-02_hobbes.nmsu.edu.zip / dos / prntst.zip / prnintst.c next >
C/C++ Source or Header  |  1989-10-14  |  4KB  |  178 lines

  1. /*
  2. **    TEST FOR PROPER INTERRUPT-DRIVEN OPERATION OF LPT1
  3. **    
  4. **    Written in MIcrosoft C Version 5.1 on Saturday October 14, 1989
  5. */
  6.  
  7. char copyr[] = "Copyright 1989 John Navas II, All Rights Reserved";
  8.  
  9. #include <bios.h>
  10. #include <conio.h>
  11. #include <dos.h>
  12. #include <io.h>
  13. #include <stdio.h>
  14. #include <stdlib.h>
  15.  
  16. #define TSTAMT    100                        /* number of characters for test */
  17.  
  18. #define TIMEOUT    182                        /* timer ticks for timeout */
  19.  
  20. #define STDERR    2                        /* DOS standard error handle */
  21. #define STDPRN    4                        /* DOS printer handle */
  22.  
  23. #define PRNRDY    0x0F                    /* printer ready interrupt */
  24.  
  25. #define INTA00    0x20                    /* 8259 control port */
  26. #define EOI        0x20                    /* end of interrupt code */
  27. #define INTA01    0x21                    /* 8259 control port */
  28. #define    PRN        0x80                    /* printer interrupt bit */
  29.  
  30. #define PRNPORT    (*(unsigned far*)0x400008L)    /* LPT1 I/O port address */
  31.  
  32. #define PRNBUSY    0x80                    /* printer NOT busy */
  33. #define PRNSEL    0x10                    /* printer selected */
  34. #define OKSTAT    (PRNSEL | PRNBUSY)        /* printer ready */
  35.  
  36. #define LPT1    0x378                    /* standard LPT1 address */
  37.  
  38. void (interrupt far* oldprn)() = 0L;    /* save old interrupt vector */
  39.  
  40. unsigned intcnt = 0;                    /* count of interrupts */
  41.  
  42. /*
  43. **    SERVICE PRINTER INTERRUPTS
  44. */
  45. void interrupt far
  46. service(void)
  47. {
  48.     ++intcnt;                            /* count interrupt */
  49.     outp(INTA00, EOI);                    /* end of interrupt to 8259 */
  50. }
  51.  
  52. /*
  53. **    CLEAN UP INTERRUPTS AT EXIT
  54. */
  55. void
  56. cleanup(void)
  57. {
  58.     unsigned char c;
  59.  
  60.     _disable();
  61.     c = (char) inp(INTA01);
  62.     c |= PRN;                            /* disable printer ready interrupts */
  63.     outp(INTA01, c);
  64.     _enable();
  65.  
  66.     if (oldprn != 0L)                    /* restore old interrupt vector */
  67.         _dos_setvect(PRNRDY, oldprn);
  68. }
  69.  
  70. /*
  71. **    SETUP PRINTER INTERRUPT VECTOR AND ENABLE INTERRUPTS
  72. */
  73. void
  74. enable(void)
  75. {
  76.     unsigned char c;
  77.  
  78.     fprintf(stderr, "PRN base address is %3Xh\n", PRNPORT);
  79.     if (!PRNPORT) {
  80.         fprintf(stderr, "NO PRN PORT FOUND!\a\n");
  81.         abort();
  82.     }
  83.     if (PRNPORT != LPT1)
  84.         fprintf(stderr, "PRN address NON-STANDARD (should be %3Xh)!\a\n",
  85.             LPT1);
  86.     if (_bios_printer(_PRINTER_STATUS, 0, 0) != OKSTAT) {
  87.         fprintf(stderr, "Printer not ready!\a\n");
  88.         abort();
  89.     }
  90.  
  91.     atexit(cleanup);
  92.     oldprn = _dos_getvect(PRNRDY);        /* save old interrupt vector */
  93.     _dos_setvect(PRNRDY, service);        /* install my interrupt vector */
  94.  
  95.     _disable();
  96.     c = (char) inp(INTA01);
  97.     c &= ~PRN;                            /* enable printer ready interrupts */
  98.     outp(INTA01, c);
  99.     _enable();
  100. }
  101.  
  102. /*
  103. **    FORCE A BRIEF DELAY
  104. */
  105. void
  106. pause(void){}
  107.  
  108. /*
  109. **    PRINT A CHARACTER ON LPT1 WITH INTERRUPTS ENABLED
  110. */
  111. int                                        /* 0 : OK; non-zero : BUSY */
  112. print(char c)
  113. {
  114.     outp(PRNPORT, c);                    /* setup character */
  115.     if (inp(PRNPORT+1) & PRNBUSY) {        /* printer not busy */
  116.         outp(PRNPORT+2, 0x0D);            /* set printer strobe */
  117.         pause();
  118.         outp(PRNPORT+2, 0x1C);            /* reset strobe & enable interrupts */
  119.         return 0;
  120.     }
  121.     else
  122.         return -1;                        /* not ready */
  123. }
  124.  
  125. /*
  126. **    RUN THE PRINTER TEST
  127. */
  128. void
  129. runtest(void)
  130. {
  131.     long t1, t2 = 0L;
  132.     unsigned u, v;
  133.  
  134.     for (u = TSTAMT; u;) {                /* output character loop */
  135.         _bios_timeofday(_TIME_GETCLOCK, &t1);
  136.         if (t1 - t2 == 0)                /* wait at least one timer tick */
  137.             continue;
  138.         if (t1 - t2 >= TIMEOUT && t2 != 0) {    /* maximum time to wait */
  139. timeout:
  140.             fprintf(stderr, "\nPrinter time out!\a\n");
  141.             abort();
  142.         }
  143.         if (print('\r'))                /* don't waste paper */
  144.             continue;                    /* not ready */
  145.         write(STDERR, ".", 1);            /* display progress */
  146.         t2 = t1;
  147.         --u;                            /* count output */
  148.     }
  149.     while (!(inp(PRNPORT+1) & PRNBUSY))    {    /* printer busy */
  150.         _bios_timeofday(_TIME_GETCLOCK, &t1);
  151.         if (t1 - t2 >= TIMEOUT)            /* maximum time to wait */
  152.             goto timeout;
  153.     }
  154. }
  155.  
  156. main()
  157. {
  158.     fprintf(stderr,
  159.         "Test for proper operation of LPT1 printer interrupts\n%s\n\n"
  160.         "Boot system naked (i.e. with NO TSR's installed!)\n"
  161.         "Ready printer on LPT1 and press any key to continue\n",
  162.         copyr);
  163.     getch();
  164.  
  165.     enable();
  166.     
  167.     runtest();
  168.  
  169.     fprintf(stderr, "\n\n%u interrupts detected for %u characters\n",
  170.         intcnt, TSTAMT);
  171.     if (TSTAMT != intcnt)
  172.         fprintf(stderr, "%d INTERRUPTS LOST!\a\n", TSTAMT - intcnt);
  173.     else if (PRNPORT == LPT1)
  174.         fprintf(stderr, "Test completed successfully.\n");
  175.  
  176.     return 0;
  177. }
  178.