home *** CD-ROM | disk | FTP | other *** search
/ The Pier Shareware 6 / The_Pier_Shareware_Number_6_(The_Pier_Exchange)_(1995).iso / 024 / psi110g.zip / NR4SUBR.C < prev    next >
C/C++ Source or Header  |  1994-04-17  |  5KB  |  246 lines

  1. /*
  2.  * nr4subr.c:  subroutines for net/rom transport layer.
  3.  * Copyright 1989 by Daniel M. Frank, W9NK.  Permission granted for
  4.  * non-commercial distribution only.
  5.  */
  6.   
  7. #include "global.h"
  8. #ifdef NETROM
  9. #include "mbuf.h"
  10. #include "timer.h"
  11. #include "ax25.h"
  12. #include "netrom.h"
  13. #include "nr4.h"
  14. #include "lapb.h"
  15. #include <ctype.h>
  16.   
  17.   
  18.   
  19. /* Get a free circuit table entry, and allocate a circuit descriptor.
  20.  * Initialize control block circuit number and ID fields.
  21.  * Return a pointer to the circuit control block if successful,
  22.  * NULLNR4CB if not.
  23.  */
  24.   
  25. struct nr4cb *
  26. new_n4circ()
  27. {
  28.     int i ;
  29.     struct nr4cb *cb ;
  30.   
  31.     for (i = 0 ; i <  NR4MAXCIRC ; i++)     /* find a free circuit */
  32.         if (Nr4circuits[i].ccb == NULLNR4CB)
  33.             break ;
  34.   
  35.     if (i == NR4MAXCIRC)    /* no more circuits */
  36.         return NULLNR4CB ;
  37.   
  38.     cb = Nr4circuits[i].ccb =
  39.     (struct nr4cb *)callocw(1,sizeof(struct nr4cb));
  40.     cb->mynum = i ;
  41.     cb->myid = Nr4circuits[i].cid ;
  42.     return cb ;
  43. }
  44.   
  45.   
  46. /* Set the window size for a circuit and allocate the buffers for
  47.  * the transmit and receive windows.  Set the control block window
  48.  * parameter.  Return 0 if successful, -1 if not.
  49.  */
  50.   
  51. int
  52. init_nr4window(cb, window)
  53. struct nr4cb *cb ;
  54. unsigned window ;
  55. {
  56.   
  57.     if (window == 0 || window > NR4MAXWIN) /* reject silly window sizes */
  58.         return -1 ;
  59.   
  60.     cb->txbufs =
  61.     (struct nr4txbuf *)callocw(window,sizeof(struct nr4txbuf));
  62.   
  63.     cb->rxbufs =
  64.     (struct nr4rxbuf *)callocw(window,sizeof(struct nr4rxbuf));
  65.   
  66.     cb->window = window ;
  67.   
  68.     return 0 ;
  69. }
  70.   
  71.   
  72. /* Free a circuit.  Deallocate the control block and buffers, and
  73.  * increment the circuit ID.  No return value.
  74.  */
  75.   
  76. void
  77. free_n4circ(cb)
  78. struct nr4cb *cb ;
  79. {
  80.     unsigned circ ;
  81.   
  82.     if (cb == NULLNR4CB)
  83.         return ;
  84.   
  85.     circ = cb->mynum ;
  86.   
  87.     if (cb->txbufs != (struct nr4txbuf *)0)
  88.         free(cb->txbufs) ;
  89.   
  90.     if (cb->rxbufs != (struct nr4rxbuf *)0)
  91.         free(cb->rxbufs) ;
  92.   
  93.     /* Better be safe than sorry: */
  94.   
  95.     free_q(&cb->txq) ;
  96.     free_q(&cb->rxq) ;
  97.   
  98.     free(cb) ;
  99.   
  100.     if (circ > NR4MAXCIRC)      /* Shouldn't happen. */
  101.         return ;
  102.   
  103.     Nr4circuits[circ].ccb = NULLNR4CB ;
  104.   
  105.     Nr4circuits[circ].cid++ ;
  106. }
  107.   
  108. /* See if any open circuit matches the given parameters.  This is used
  109.  * to prevent opening multiple circuits on a duplicate connect request.
  110.  * Returns the control block address if a match is found, or NULLNR4CB
  111.  * otherwise.
  112.  */
  113.   
  114. struct nr4cb *
  115. match_n4circ(index, id, user, node)
  116. int index ;                 /* index of remote circuit */
  117. int id ;                    /* id of remote circuit */
  118. char *user ;    /* address of remote user */
  119. char *node ;    /* address of originating node */
  120. {
  121.     int i ;
  122.     struct nr4cb *cb ;
  123.   
  124.     for (i = 0 ; i < NR4MAXCIRC ; i++) {
  125.         if ((cb = Nr4circuits[i].ccb) == NULLNR4CB)
  126.             continue ;      /* not an open circuit */
  127.         if (cb->yournum == index && cb->yourid == id
  128.             && addreq(cb->remote.user,user)
  129.             && addreq(cb->remote.node,node))
  130.             return cb ;
  131.     }
  132.     /* if we get to here, we didn't find a match */
  133.   
  134.     return NULLNR4CB ;
  135. }
  136.   
  137. /* Validate the index and id of a local circuit, returning the control
  138.  * block if it is valid, or NULLNR4CB if it is not.
  139.  */
  140.   
  141. struct nr4cb *
  142. get_n4circ(index, id)
  143. int index ;             /* local circuit index */
  144. int id ;                /* local circuit id */
  145. {
  146.     struct nr4cb *cb ;
  147.   
  148.     if (index >= NR4MAXCIRC)
  149.         return NULLNR4CB ;
  150.   
  151.     if ((cb = Nr4circuits[index].ccb) == NULLNR4CB)
  152.         return NULLNR4CB ;
  153.   
  154.     if (cb->myid == id)
  155.         return cb ;
  156.     else
  157.         return NULLNR4CB ;
  158. }
  159.   
  160. /* Return 1 if b is "between" (modulo the size of an unsigned char)
  161.  * a and c, 0 otherwise.
  162.  */
  163.   
  164. int
  165. nr4between(a, b, c)
  166. unsigned a, b, c ;
  167. {
  168.     if ((a <= b && b < c) || (c < a && a <= b) || (b < c && c < a))
  169.         return 1 ;
  170.     else
  171.         return 0 ;
  172. }
  173.   
  174. /* Set up default timer values, etc., in newly connected control block.
  175.  */
  176.   
  177. void
  178. nr4defaults(cb)
  179. struct nr4cb *cb ;
  180. {
  181.     int i ;
  182.     struct timer *t ;
  183.   
  184.     if (cb == NULLNR4CB)
  185.         return ;
  186.   
  187.     /* Set up the ACK and CHOKE timers */
  188.   
  189.     set_timer(&cb->tack,Nr4acktime) ;
  190.     cb->tack.func = nr4ackit ;
  191.     cb->tack.arg = cb ;
  192.   
  193.     set_timer(&cb->tchoke,Nr4choketime) ;
  194.     cb->tchoke.func = nr4unchoke ;
  195.     cb->tchoke.arg = cb ;
  196.   
  197.     cb->rxpastwin = cb->window ;
  198.   
  199.     /* Don't actually set the timers, since this is done */
  200.     /* in nr4sbuf */
  201.   
  202.     for (i = 0 ; i < cb->window ; i++) {
  203.         t = &cb->txbufs[i].tretry ;
  204.         t->func = nr4txtimeout ;
  205.         t->arg = cb ;
  206.     }
  207. }
  208.   
  209. /* See if this control block address is valid */
  210.   
  211. int
  212. nr4valcb(cb)
  213. struct nr4cb *cb ;
  214. {
  215.     int i ;
  216.   
  217.     if (cb == NULLNR4CB)
  218.         return 0 ;
  219.   
  220.     for (i = 0 ; i < NR4MAXCIRC ; i++)
  221.         if (Nr4circuits[i].ccb == cb)
  222.             return 1 ;
  223.   
  224.     return 0 ;
  225. }
  226.   
  227. #ifndef LINUX
  228.   
  229. void
  230. nr_garbage(red)
  231. int red;
  232. {
  233.     int i;
  234.     struct nr4cb *ncp;
  235.   
  236.     for(i=0;i<NR4MAXCIRC;i++){
  237.         ncp = Nr4circuits[i].ccb;
  238.         if(ncp != NULLNR4CB)
  239.             mbuf_crunch(&ncp->rxq);
  240.     }
  241. }
  242. #endif /* LINUX */
  243.   
  244. #endif /* NETROM */
  245.   
  246.