home *** CD-ROM | disk | FTP | other *** search
/ Programmer 7500 / MAX_PROGRAMMERS.iso / INFO / NCSATELN / TEL23SRC.ZIP / NET / ENET / PACKET.C < prev    next >
Encoding:
C/C++ Source or Header  |  1991-07-05  |  9.8 KB  |  409 lines

  1. /* cu-notic.txt         NCSA Telnet version 2.2C     2/3/89
  2.    Notice:
  3.         Portions of this file have been modified by
  4.         The Educational Resources Center of Clarkson University.
  5.  
  6.         All modifications made by Clarkson University are hereby placed
  7.         in the public domain, provided the following statement remain in
  8.         all source files.
  9.  
  10.         "Portions Developed by the Educational Resources Center, 
  11.                 Clarkson University"
  12.  
  13.         Bugs and comments to bkc@omnigate.clarkson.edu
  14.                                 bkc@clgw.bitnet
  15.  
  16.         Brad Clements
  17.         Educational Resources Center
  18.         Clarkson University
  19. */
  20.  
  21. /* packet.c - FTP Software Packet Interface for NCSA TELNET
  22.    Author: Brad Clements  bkc@omnigate.clarkson.edu
  23.            Clarskon University
  24.            10/24/88
  25.  
  26.    Assumes Microsoft C large model
  27. */
  28. /*
  29. *  packet.c
  30. *****************************************************************************
  31. *                                                                              *
  32. *      part of:                                                                *
  33. *      TCP/UDP/ICMP/IP Network kernel for NCSA Telnet                        *
  34. *      by Tim Krauskopf                                                        *
  35. *                                                                              *
  36. *      National Center for Supercomputing Applications                         *
  37. *      152 Computing Applications Building                                     *
  38. *      605 E. Springfield Ave.                                                 *
  39. *      Champaign, IL  61820                                                    *
  40. *                                                                              *
  41. *****************************************************************************
  42. *
  43. *    Packet driver code modifed for Microsoft and Lattice C by
  44. *        Quincey Koziol 8/18/89
  45. */
  46. /* #define XDEBUG  1 */
  47.  
  48. /*#define DEBUG*/
  49.  
  50. #ifdef DEBUG    
  51. #include <conio.h>
  52. #endif
  53.  
  54. #include "debug.h"
  55.  
  56. #ifdef    __TURBO__
  57. #pragma inline
  58. #endif
  59. #include <stdio.h>
  60. #include <string.h>
  61. #include <dos.h>
  62. #ifdef MEMORY_DEBUG
  63. #include "memdebug.h"
  64. #endif
  65. #include "whatami.h"
  66. #include "windat.h"
  67. #include "externs.h"
  68. #define MK_FP(seg,ofs)    ((void far *) (((unsigned long)(seg) << 16) | (unsigned)(ofs)))
  69.  
  70. int     ip_handle=(-1),arp_handle=(-1),rarp_handle=(-1);
  71.  
  72. extern unsigned char rstat;                    /* status from last read */
  73. extern char *bufpt,*bufend,*bufread,*buforg;
  74. extern int bufbig,buflim;
  75. static int packet_vector;                       /* non-zero if we found it */
  76.  
  77. #define    IC_ANY      0
  78. #define IC_ETHERNET     1
  79. #define IC_SLIP         6
  80. #define    IT_ANY        0xFFFF
  81.  
  82. extern    void pkt_receiver();
  83. static int locate_pkt_vector(int vec);
  84. static  int     oldvec;
  85.  
  86. static int locate_pkt_vector(vec)             /* search for the packet driver */
  87. int vec;
  88. {
  89.         struct vector_ptr{
  90.                 char far *real_vector;
  91.         } *vptr;
  92.         char    far     *xvptr;
  93.         int     vector,vmax;
  94.  
  95.         if(packet_vector)
  96.                 return(0);         /* already found!       */
  97.         vector = 0x60;
  98.         vmax = 0x7f;
  99.  
  100. #ifdef DEBUG
  101.         printf("%s[%d],vec = %d\n",__FILE__,__LINE__,vec);
  102.         printf("setting vec to 0x60\n");
  103.         printf("%s[%d],vec = %d\n",__FILE__,__LINE__,vec);
  104. #endif
  105.         if((vec >= 0x60) && (vec <= 0x7f))
  106.             vmax = vector = vec;
  107.         else if (vec != 0) /* zero specifies use search */
  108.             n_puts("Warning, packet driver vector incorrect, using default search\n\r");
  109.  
  110.         for(; vector <= vmax; vector++) {
  111.             vptr = (struct vector_ptr *)MK_FP(0,vector * 4);
  112.             xvptr = vptr->real_vector;
  113. #ifdef DEBUG
  114.             printf("Checking vector %X\n", vector);
  115.             printf("vptr = %p\n",vptr);
  116.             printf("real vec = %p\n",xvptr);
  117.             printf("string = %s\n",xvptr+3);
  118. #endif
  119.             if(!strncmp(xvptr+3,"PKT DRVR",8)) {
  120.                 packet_vector = vector;
  121.                 BUG("found vector");
  122.                 return(0);
  123.             }
  124.         }
  125.  
  126.         BUG("didn't find vector");
  127.         return(-1);
  128. }
  129.  
  130. int pkt_access_type(if_class,if_type,if_number,type,typelen,receiver)
  131. int if_class,
  132.     if_type,
  133.     if_number;
  134. char *type;
  135. int typelen;
  136. void  (*receiver)();
  137. {
  138.    union REGS regs;
  139.    struct SREGS segregs;
  140.  
  141.    if(!packet_vector)
  142.         return(-1);
  143.     regs.h.ah = 2;
  144.     regs.h.al= (char)if_class;
  145.     regs.x.bx = if_type;
  146.     regs.x.dx = if_number;
  147.     segregs.ds = FP_SEG(type);
  148.     regs.x.si = FP_OFF(type);
  149.     regs.x.cx = typelen;
  150.     segregs.es = FP_SEG(receiver);
  151.     regs.x.di = FP_OFF(receiver);
  152.     int86x(packet_vector,®s,®s,&segregs);
  153.     if(regs.x.cflag) {
  154.         char    buff[512];
  155.  
  156.         sprintf(buff,"Packet Access Type Error %d\n\r",regs.h.dh);
  157.         n_puts(buff);
  158.         return(-1);
  159.       }    /* end if */
  160.    return(regs.x.ax);
  161. }
  162.  
  163. int pkt_set_rcv_mode(handle,mode)
  164. int handle,
  165.     mode;
  166. {
  167.    union REGS regs;
  168.  
  169.    if(!packet_vector)
  170.       return(-1);
  171.    regs.x.ax = 0x2000;
  172.    regs.x.bx = handle;
  173.    regs.x.cx = mode;
  174.    int86(packet_vector,®s,®s);
  175.    if(regs.x.cflag) 
  176.       return(regs.h.dh);
  177.    return(0);
  178. }
  179.  
  180. void pkt_release_type(handle)
  181. int    handle;
  182. {
  183.    union REGS regs;
  184.    
  185.    if(!packet_vector)
  186.       return;
  187.  
  188.    regs.x.ax = 0x0300;
  189.    regs.x.bx = handle;
  190.    int86(packet_vector,®s,®s);
  191.    return;
  192. }
  193.  
  194. void pkt_get_address(handle,storage,len)
  195. int handle;
  196. char *storage;
  197. int len;
  198.  
  199. {
  200.    union REGS regs;
  201.    struct SREGS segregs;
  202.  
  203.    if(!packet_vector)
  204.         return;
  205.  
  206.    regs.x.ax = 0x0600;
  207.    regs.x.bx = handle;
  208.    regs.x.di = FP_OFF(storage);
  209.    segregs.es = FP_SEG(storage);
  210.    regs.x.cx = len;
  211.    int86x(packet_vector,®s,®s,&segregs);
  212.    if(regs.x.cflag) {
  213.         char    buff[128];
  214.         sprintf(buff,"Error retrieving address %d\n\r",regs.h.dh);
  215.         n_puts(buff);
  216.    }
  217. }
  218.  
  219. int pkt_send(packet,len)
  220. char *packet;
  221. int len;
  222.  
  223. {
  224.    union REGS regs;
  225.    struct SREGS segregs;
  226.  
  227.    if(!packet_vector)
  228.       return(-1);
  229.     regs.h.ah=4;
  230.     regs.h.al=0;
  231.     regs.x.si = FP_OFF(packet);
  232.     regs.x.cx = len;
  233.     segregs.ds = FP_SEG(packet);
  234.     int86x(packet_vector,®s,®s,&segregs);
  235. #ifdef  XDEBUG
  236.         { char xx[80]; 
  237.            sprintf(xx,"pkt_send %d bytes rc is %d (%d)\n",len, regs.h.dh, regs.x.cflag);
  238.            n_puts(xx);
  239.         }
  240. #endif
  241.  
  242.     if(regs.x.cflag)
  243.         return(regs.h.dh);
  244.     return(0);
  245. }
  246.  
  247. /* we try and locate the packet driver and open ARP and IP handles. */
  248. /* also open RARP handle */
  249. int pketopen(s,irq,address,ioaddr)
  250. unsigned char *s;            /* ethernet address */
  251. unsigned int    irq;            /* don't need this      */
  252. unsigned int    address;        /* address is packet class */
  253. unsigned int    ioaddr;            /* packet int, or 0 */
  254. {
  255.     static char iptype[]={8,0};
  256.     static char arptype[]={8,6};
  257.     static char rarptype[]={0x80,0x35};
  258.     char buff[256];
  259.  
  260.     irq=irq;        /* get rid of compiler warning */
  261.     if(!locate_pkt_vector(ioaddr))
  262.         oldvec = ioaddr;
  263.     else {
  264.         n_puts("No Packet Driver found at specified location. Change ioaddr in config.tel\n\r");
  265.         return(-1);
  266.       }    /* end else */
  267.     if(ip_handle!=(-1))
  268.         return(0);
  269.     if(address<1 || address>11)        /* 11 is the highest number for if_class at the present time */
  270.         address = IC_ETHERNET;
  271.  
  272.     if((ip_handle = pkt_access_type(address,IT_ANY,0,iptype,sizeof(iptype),pkt_receiver)) == -1) {
  273.         sprintf(buff,"Can't Access IP handle interface type %d\n\rPacket Driver probably not loaded\n\r",address);
  274.         n_puts(buff);
  275.         return(-2);
  276.       }    /* end if */
  277.  
  278.     if((arp_handle = pkt_access_type(address,IT_ANY,0,arptype,sizeof(arptype),pkt_receiver)) == -1) {
  279.         sprintf(buff,"Can't Access ARP handle\n\r");
  280.         n_puts(buff);
  281.         pkt_release_type(ip_handle);
  282.         return(-3);
  283.       }    /* end if */
  284.  
  285. /* Grab the RARP handle also */
  286.     if((rarp_handle = pkt_access_type(address,IT_ANY,0,rarptype,sizeof(rarptype),pkt_receiver)) == -1) {
  287.         sprintf(buff,"Can't Access RARP handle\n\r");
  288.         n_puts(buff);
  289.         pkt_release_type(ip_handle);
  290.         pkt_release_type(arp_handle);    /* let go of the arp handle also */
  291.         return(-4);
  292.       }    /* end if */
  293.  
  294.     pkt_get_address(ip_handle,s,6);
  295.     pkt_set_rcv_mode(ip_handle,3);       /* receive broadcasts also */
  296.     return(0);
  297. }
  298.  
  299. int pkgetaddr(s,address,ioaddr)       /* get the ethernet address */
  300. unsigned char    *s;            /* ethernet address */
  301. unsigned int     address;        /* address is packet class */
  302. unsigned int     ioaddr;        /* packet int, or 0 */
  303. {
  304.    BUG("pkgetaddr");
  305.    if(ip_handle==(-1))
  306.       return(pketopen(s,0,address,ioaddr));
  307.    BUG("about to pkt_get_address");
  308.    pkt_get_address(ip_handle,s,6);
  309.    return(0);
  310. }
  311.  
  312. void pkrecv()                        /* no op for this interface     */
  313. {
  314. }
  315.  
  316. int pketclose()                     /* throw away our handles */
  317. {
  318.    pkt_release_type(ip_handle);
  319.    pkt_release_type(arp_handle);
  320.    pkt_release_type(rarp_handle);
  321.    return(0);
  322. }
  323.  
  324. int pkxmit(packet,length)           /* transmit a packet    */
  325. DLAYER *packet;
  326. int    length;
  327. {
  328.    if(length < 60)
  329.         length=60;            /* what a terrible hack! */
  330.    if(pkt_send((char *)packet,length))
  331.         return(-1);
  332.    return(0);
  333. }
  334.  
  335. unsigned pkt_es,pkt_di;
  336.  
  337. #ifdef _TURBOC_
  338. void interrupt pkt_receiver2(bp,di,si,ds,es,dx,cx,bx,ax)
  339. unsigned int bp,di,si,ds,es,dx,cx,bx,ax;
  340. #else
  341. void interrupt pkt_receiver2(es,ds,di,si,bp,sp,bx,dx,cx,ax)
  342. unsigned int bp,sp,
  343.     di,si,
  344.     ds,es,
  345.     dx,cx,bx,ax;
  346. #endif
  347. {
  348.    char  *where_to_write;
  349.    int   *save_packet_size;
  350.  
  351.    /* this receiver function assumes that between the first and second call
  352.       from the packet driver, the underlying telnet code will not access
  353.       the buffer.
  354.    */
  355.  
  356.    /* here's an incoming packet from the packet driver, first see if we
  357.       have enough space for it */
  358.  
  359.     ds=ds;        /* get rid of compiler warnings */
  360.     si=si;
  361.     bp=bp;
  362.     sp=sp;
  363.     bx=bx;
  364.     dx=dx;
  365.     if(!ax) {
  366.         if(bufbig <= buflim) {  /* if there is space remaining */
  367.             if(bufpt > bufend)   /* if at end of wrap area then wrap it */
  368.                 bufpt = buforg;
  369.             save_packet_size = (int *) bufpt;
  370.             bufpt += sizeof(int);        /* we're so clean here! */
  371.             where_to_write = bufpt;
  372.             *save_packet_size = cx;
  373.             bufpt += cx;
  374.             bufbig += cx + sizeof(int);
  375.             es = FP_SEG(where_to_write);
  376.             di = FP_OFF(where_to_write);
  377.             return;
  378.           }
  379.         else {
  380.             es = di = 0;                /* no room */
  381.         }
  382.     }
  383.     return;                      /* we do nothing if its the second call */
  384. }
  385.  
  386. void pketupdate()                    /* update the pointers */
  387. {
  388.    int packet_size;
  389.    int *size_ptr;
  390.  
  391.  
  392.    size_ptr = (int *) bufread;
  393.    packet_size = *size_ptr;
  394.    bufread += packet_size + sizeof(int);
  395.    if(bufread > bufend)
  396.       bufread = buforg;
  397.  
  398.     clear_int();
  399. #ifdef __TURBO__
  400.     asm cli                      /* inline assembly  no ints during this operation     */
  401. #endif
  402.     bufbig -= packet_size + sizeof(int);
  403.     set_int();
  404. #ifdef __TURBO__
  405.     asm sti                      /* inline assembly      */
  406. #endif
  407. }
  408.  
  409.