1 /* 2 * Copyright (c) 1985, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * This file includes significant work done at Cornell University by 6 * Bill Nesheim. That work included by permission. 7 * 8 * %sccs.include.redist.c% 9 */ 10 11 #ifndef lint 12 static char sccsid[] = "@(#)timer.c 8.1 (Berkeley) 06/05/93"; 13 #endif /* not lint */ 14 15 /* 16 * Routing Table Management Daemon 17 */ 18 #include "defs.h" 19 20 int timeval = -TIMER_RATE; 21 22 /* 23 * Timer routine. Performs routing information supply 24 * duties and manages timers on routing table entries. 25 */ 26 void 27 timer() 28 { 29 register struct rthash *rh; 30 register struct rt_entry *rt; 31 struct rthash *base = hosthash; 32 int doinghost = 1, timetobroadcast; 33 34 timeval += TIMER_RATE; 35 if (lookforinterfaces && (timeval % CHECK_INTERVAL) == 0) 36 ifinit(); 37 timetobroadcast = supplier && (timeval % SUPPLY_INTERVAL) == 0; 38 again: 39 for (rh = base; rh < &base[ROUTEHASHSIZ]; rh++) { 40 rt = rh->rt_forw; 41 for (; rt != (struct rt_entry *)rh; rt = rt->rt_forw) { 42 /* 43 * We don't advance time on a routing entry for 44 * a passive gateway or that for our only interface. 45 * The latter is excused because we don't act as 46 * a routing information supplier and hence would 47 * time it out. This is fair as if it's down 48 * we're cut off from the world anyway and it's 49 * not likely we'll grow any new hardware in 50 * the mean time. 51 */ 52 if (!(rt->rt_state & RTS_PASSIVE) && 53 (supplier || !(rt->rt_state & RTS_INTERFACE))) 54 rt->rt_timer += TIMER_RATE; 55 if (rt->rt_timer >= EXPIRE_TIME) 56 rt->rt_metric = HOPCNT_INFINITY; 57 if (rt->rt_timer >= GARBAGE_TIME) { 58 rt = rt->rt_back; 59 /* Perhaps we should send a REQUEST for this route? */ 60 rtdelete(rt->rt_forw); 61 continue; 62 } 63 if (rt->rt_state & RTS_CHANGED) { 64 rt->rt_state &= ~RTS_CHANGED; 65 /* don't send extraneous packets */ 66 if (!supplier || timetobroadcast) 67 continue; 68 msg->rip_cmd = htons(RIPCMD_RESPONSE); 69 msg->rip_nets[0].rip_dst = 70 (satons_addr(rt->rt_dst)).x_net; 71 msg->rip_nets[0].rip_metric = 72 htons(min(rt->rt_metric+1, HOPCNT_INFINITY)); 73 toall(sndmsg); 74 } 75 } 76 } 77 if (doinghost) { 78 doinghost = 0; 79 base = nethash; 80 goto again; 81 } 82 if (timetobroadcast) 83 toall(supply); 84 alarm(TIMER_RATE); 85 } 86 87 /* 88 * On hangup, let everyone know we're going away. 89 */ 90 void 91 hup() 92 { 93 register struct rthash *rh; 94 register struct rt_entry *rt; 95 struct rthash *base = hosthash; 96 int doinghost = 1; 97 98 if (supplier) { 99 again: 100 for (rh = base; rh < &base[ROUTEHASHSIZ]; rh++) { 101 rt = rh->rt_forw; 102 for (; rt != (struct rt_entry *)rh; rt = rt->rt_forw) 103 rt->rt_metric = HOPCNT_INFINITY; 104 } 105 if (doinghost) { 106 doinghost = 0; 107 base = nethash; 108 goto again; 109 } 110 toall(supply); 111 } 112 exit(1); 113 } 114