ip.c revision 31142
16059Samurai/* 26059Samurai * PPP IP Protocol Interface 36059Samurai * 46059Samurai * Written by Toshiharu OHNO (tony-o@iij.ad.jp) 56059Samurai * 66059Samurai * Copyright (C) 1993, Internet Initiative Japan, Inc. All rights reserverd. 76059Samurai * 86059Samurai * Redistribution and use in source and binary forms are permitted 96059Samurai * provided that the above copyright notice and this paragraph are 106059Samurai * duplicated in all such forms and that any documentation, 116059Samurai * advertising materials, and other materials related to such 126059Samurai * distribution and use acknowledge that the software was developed 136059Samurai * by the Internet Initiative Japan. The name of the 146059Samurai * IIJ may not be used to endorse or promote products derived 156059Samurai * from this software without specific prior written permission. 166059Samurai * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 176059Samurai * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 186059Samurai * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. 198857Srgrimes * 2031142Sbrian * $Id: ip.c,v 1.27 1997/10/26 12:42:10 brian Exp $ 218857Srgrimes * 226059Samurai * TODO: 236059Samurai * o Return ICMP message for filterd packet 246059Samurai * and optionaly record it into log. 256059Samurai */ 2630715Sbrian#include <sys/param.h> 2730715Sbrian#include <netinet/in.h> 286059Samurai#include <netinet/in_systm.h> 296059Samurai#include <netinet/ip.h> 306059Samurai#include <netinet/ip_icmp.h> 316059Samurai#include <netinet/udp.h> 326059Samurai#include <netinet/tcp.h> 3313389Sphk#include <arpa/inet.h> 3430715Sbrian 3526031Sbrian#include <alias.h> 3630092Sbrian#include <errno.h> 3730715Sbrian#include <stdio.h> 3830715Sbrian#include <stdlib.h> 3930715Sbrian#include <string.h> 4030733Sbrian#include <termios.h> 4130715Sbrian#include <unistd.h> 4230715Sbrian 4330715Sbrian#include "mbuf.h" 4430715Sbrian#include "log.h" 4530715Sbrian#include "defs.h" 4630715Sbrian#include "timer.h" 4730715Sbrian#include "fsm.h" 4830715Sbrian#include "lcpproto.h" 4930715Sbrian#include "hdlc.h" 5026142Sbrian#include "loadalias.h" 5130715Sbrian#include "command.h" 526059Samurai#include "vars.h" 536059Samurai#include "filter.h" 5426516Sbrian#include "log.h" 5529043Sbrian#include "os.h" 5630715Sbrian#include "ipcp.h" 5730715Sbrian#include "vjcomp.h" 5830715Sbrian#include "lcp.h" 5930733Sbrian#include "modem.h" 6030715Sbrian#include "ip.h" 616059Samurai 626059Samuraistatic struct pppTimer IdleTimer; 636059Samurai 6428679Sbrianstatic void 6528679SbrianIdleTimeout() 666059Samurai{ 6726516Sbrian LogPrintf(LogPHASE, "Idle timer expired.\n"); 6826098Sbrian reconnect(RECON_FALSE); 696059Samurai LcpClose(); 706059Samurai} 716059Samurai 726059Samurai/* 736059Samurai * Start Idle timer. If timeout is reached, we call LcpClose() to 746059Samurai * close LCP and link. 756059Samurai */ 766059Samuraivoid 776059SamuraiStartIdleTimer() 786059Samurai{ 7928679Sbrian if (!(mode & (MODE_DEDICATED | MODE_DDIAL))) { 806059Samurai StopTimer(&IdleTimer); 816059Samurai IdleTimer.func = IdleTimeout; 826059Samurai IdleTimer.load = VarIdleTimeout * SECTICKS; 836059Samurai IdleTimer.state = TIMER_STOPPED; 846059Samurai StartTimer(&IdleTimer); 856059Samurai } 866059Samurai} 876059Samurai 886059Samuraivoid 8926516SbrianUpdateIdleTimer() 9026516Sbrian{ 9129043Sbrian if (OsLinkIsUp()) 9226516Sbrian StartIdleTimer(); 9326516Sbrian} 9426516Sbrian 9526516Sbrianvoid 966059SamuraiStopIdleTimer() 976059Samurai{ 986059Samurai StopTimer(&IdleTimer); 996059Samurai} 1006059Samurai 1016059Samurai/* 1026059Samurai * If any IP layer traffic is detected, refresh IdleTimer. 1036059Samurai */ 1046059Samuraistatic void 1056059SamuraiRestartIdleTimer() 1066059Samurai{ 10728679Sbrian if (!(mode & (MODE_DEDICATED | MODE_DDIAL)) && ipKeepAlive) { 1086059Samurai StartTimer(&IdleTimer); 1096059Samurai ipIdleSecs = 0; 1106059Samurai } 1116059Samurai} 1126059Samurai 11313733Sdfrstatic u_short interactive_ports[32] = { 11428679Sbrian 544, 513, 514, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11528679Sbrian 0, 0, 0, 0, 0, 21, 22, 23, 0, 0, 0, 0, 0, 0, 0, 543, 1166059Samurai}; 1176059Samurai 11813733Sdfr#define INTERACTIVE(p) (interactive_ports[(p) & 0x1F] == (p)) 1196059Samurai 1206059Samuraistatic char *TcpFlags[] = { 1216059Samurai "FIN", "SYN", "RST", "PSH", "ACK", "URG", 1226059Samurai}; 1236059Samurai 12428679Sbrianstatic char *Direction[] = {"INP", "OUT", "OUT", "IN/OUT"}; 12528679Sbrianstatic struct filterent *Filters[] = {ifilters, ofilters, dfilters, afilters}; 1266059Samurai 1276059Samuraistatic int 12828679SbrianPortMatch(int op, u_short pport, u_short rport) 1296059Samurai{ 1306059Samurai switch (op) { 13128679Sbrian case OP_EQ: 13228679Sbrian return (pport == rport); 1336059Samurai case OP_GT: 13428679Sbrian return (pport > rport); 1356059Samurai case OP_LT: 13628679Sbrian return (pport < rport); 1376059Samurai default: 13828679Sbrian return (0); 1396059Samurai } 1406059Samurai} 1416059Samurai 1426059Samurai/* 1436059Samurai * Check a packet against with defined filters 1446059Samurai */ 1456059Samuraistatic int 14628679SbrianFilterCheck(struct ip * pip, int direction) 1476059Samurai{ 1486059Samurai struct filterent *fp = Filters[direction]; 1496059Samurai int gotinfo, cproto, estab, n; 1506059Samurai struct tcphdr *th; 1516059Samurai struct udphdr *uh; 1526059Samurai struct icmp *ih; 1536059Samurai char *ptop; 1546059Samurai u_short sport, dport; 1556059Samurai 1566059Samurai if (fp->action) { 1576059Samurai cproto = gotinfo = estab = 0; 1586059Samurai sport = dport = 0; 1596059Samurai for (n = 0; n < MAXFILTERS; n++) { 1606059Samurai if (fp->action) { 16128679Sbrian /* permit fragments on in and out filter */ 16228679Sbrian if ((direction == FL_IN || direction == FL_OUT) && 16328679Sbrian (ntohs(pip->ip_off) & IP_OFFMASK) != 0) { 16428679Sbrian return (A_PERMIT); 16528679Sbrian } 16628679Sbrian LogPrintf(LogDEBUG, "rule = %d\n", n); 1676059Samurai if ((pip->ip_src.s_addr & fp->smask.s_addr) == fp->saddr.s_addr 1686059Samurai && (pip->ip_dst.s_addr & fp->dmask.s_addr) == fp->daddr.s_addr) { 1696059Samurai if (fp->proto) { 1706059Samurai if (!gotinfo) { 17128679Sbrian ptop = (char *) pip + (pip->ip_hl << 2); 1726059Samurai 1736059Samurai switch (pip->ip_p) { 1746059Samurai case IPPROTO_ICMP: 17528679Sbrian cproto = P_ICMP; 17628679Sbrian ih = (struct icmp *) ptop; 17728679Sbrian sport = ih->icmp_type; 17828679Sbrian estab = 1; 1796059Samurai break; 1806059Samurai case IPPROTO_UDP: 18128679Sbrian cproto = P_UDP; 18228679Sbrian uh = (struct udphdr *) ptop; 18328679Sbrian sport = ntohs(uh->uh_sport); 18428679Sbrian dport = ntohs(uh->uh_dport); 1856059Samurai estab = 1; 1866059Samurai break; 1876059Samurai case IPPROTO_TCP: 18828679Sbrian cproto = P_TCP; 18928679Sbrian th = (struct tcphdr *) ptop; 19028679Sbrian sport = ntohs(th->th_sport); 19128679Sbrian dport = ntohs(th->th_dport); 1926059Samurai estab = (th->th_flags & TH_ACK); 19328679Sbrian if (estab == 0) 19428679Sbrian LogPrintf(LogDEBUG, "flag = %02x, sport = %d, dport = %d\n", 19528679Sbrian th->th_flags, sport, dport); 1966059Samurai break; 1976059Samurai default: 19828679Sbrian return (A_DENY);/* We'll block unknown type of packet */ 1996059Samurai } 2006059Samurai gotinfo = 1; 20128679Sbrian LogPrintf(LogDEBUG, "dir = %d, proto = %d, srcop = %d," 20228679Sbrian " dstop = %d, estab = %d\n", direction, cproto, 20328679Sbrian fp->opt.srcop, fp->opt.dstop, estab); 2046059Samurai } 20526516Sbrian LogPrintf(LogDEBUG, "check0: rule = %d, proto = %d, sport = %d," 20628679Sbrian " dport = %d\n", n, cproto, sport, dport); 20726516Sbrian LogPrintf(LogDEBUG, "check0: action = %d\n", fp->action); 20826516Sbrian 2096059Samurai if (cproto == fp->proto) { 2106059Samurai if ((fp->opt.srcop == OP_NONE || 21128679Sbrian PortMatch(fp->opt.srcop, sport, fp->opt.srcport)) 21228679Sbrian && 2136059Samurai (fp->opt.dstop == OP_NONE || 21428679Sbrian PortMatch(fp->opt.dstop, dport, fp->opt.dstport)) 21528679Sbrian && 2166059Samurai (fp->opt.estab == 0 || estab)) { 21728679Sbrian return (fp->action); 2186059Samurai } 2196059Samurai } 2206059Samurai } else { 2216059Samurai /* Address is mached. Make a decision. */ 22226516Sbrian LogPrintf(LogDEBUG, "check1: action = %d\n", fp->action); 22328679Sbrian return (fp->action); 2246059Samurai } 2256059Samurai } 2266059Samurai } 2276059Samurai fp++; 2286059Samurai } 22928679Sbrian return (A_DENY); /* No rule is mached. Deny this packet */ 2306059Samurai } 23128679Sbrian return (A_PERMIT); /* No rule is given. Permit this packet */ 2326059Samurai} 2336059Samurai 2346059Samuraistatic void 23528679SbrianIcmpError(struct ip * pip, int code) 2366059Samurai{ 2376059Samurai#ifdef notdef 2386059Samurai struct mbuf *bp; 2396059Samurai 2406059Samurai if (pip->ip_p != IPPROTO_ICMP) { 2416059Samurai bp = mballoc(cnt, MB_IPIN); 24230715Sbrian memcpy(MBUF_CTOP(bp), ptr, cnt); 24313733Sdfr SendPppFrame(bp); 2446059Samurai RestartIdleTimer(); 2456059Samurai ipOutOctets += cnt; 2466059Samurai } 2476059Samurai#endif 2486059Samurai} 2496059Samurai 2506059Samurai/* 2516059Samurai * For debugging aid. 2526059Samurai */ 2536059Samuraiint 25428679SbrianPacketCheck(char *cp, int nb, int direction) 2556059Samurai{ 2566059Samurai struct ip *pip; 2576059Samurai struct tcphdr *th; 2586059Samurai struct udphdr *uh; 2596059Samurai struct icmp *icmph; 2606059Samurai char *ptop; 2616059Samurai int mask, len, n; 2626059Samurai int pri = PRI_NORMAL; 26326692Sbrian int logit, loglen; 26426692Sbrian static char logbuf[200]; 2656059Samurai 26626516Sbrian logit = LogIsKept(LogTCPIP); 26726692Sbrian loglen = 0; 2686059Samurai 26928679Sbrian pip = (struct ip *) cp; 2708857Srgrimes 27126692Sbrian if (logit && loglen < sizeof logbuf) { 27228679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, "%s ", 27328679Sbrian Direction[direction]); 27428679Sbrian loglen += strlen(logbuf + loglen); 27526692Sbrian } 2766059Samurai ptop = (cp + (pip->ip_hl << 2)); 2776059Samurai 2786059Samurai switch (pip->ip_p) { 2796059Samurai case IPPROTO_ICMP: 28026692Sbrian if (logit && loglen < sizeof logbuf) { 28128679Sbrian icmph = (struct icmp *) ptop; 28228679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 28328679Sbrian "ICMP: %s:%d ---> ", inet_ntoa(pip->ip_src), icmph->icmp_type); 28428679Sbrian loglen += strlen(logbuf + loglen); 28528679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 28628679Sbrian "%s:%d", inet_ntoa(pip->ip_dst), icmph->icmp_type); 28728679Sbrian loglen += strlen(logbuf + loglen); 2886059Samurai } 2896059Samurai break; 2906059Samurai case IPPROTO_UDP: 29126692Sbrian if (logit && loglen < sizeof logbuf) { 29228679Sbrian uh = (struct udphdr *) ptop; 29328679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 29428679Sbrian "UDP: %s:%d ---> ", inet_ntoa(pip->ip_src), ntohs(uh->uh_sport)); 29528679Sbrian loglen += strlen(logbuf + loglen); 29628679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 29728679Sbrian "%s:%d", inet_ntoa(pip->ip_dst), ntohs(uh->uh_dport)); 29828679Sbrian loglen += strlen(logbuf + loglen); 2996059Samurai } 3006059Samurai break; 3016059Samurai case IPPROTO_TCP: 30228679Sbrian th = (struct tcphdr *) ptop; 3036059Samurai if (pip->ip_tos == IPTOS_LOWDELAY) 3046059Samurai pri = PRI_FAST; 30513733Sdfr else if ((ntohs(pip->ip_off) & IP_OFFMASK) == 0) { 3066059Samurai if (INTERACTIVE(ntohs(th->th_sport)) || INTERACTIVE(ntohs(th->th_dport))) 30728679Sbrian pri = PRI_FAST; 3086059Samurai } 30926692Sbrian if (logit && loglen < sizeof logbuf) { 3106059Samurai len = ntohs(pip->ip_len) - (pip->ip_hl << 2) - (th->th_off << 2); 31128679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 31228679Sbrian "TCP: %s:%d ---> ", inet_ntoa(pip->ip_src), ntohs(th->th_sport)); 31328679Sbrian loglen += strlen(logbuf + loglen); 31428679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 31528679Sbrian "%s:%d", inet_ntoa(pip->ip_dst), ntohs(th->th_dport)); 31628679Sbrian loglen += strlen(logbuf + loglen); 3176059Samurai n = 0; 3186059Samurai for (mask = TH_FIN; mask != 0x40; mask <<= 1) { 31926692Sbrian if (th->th_flags & mask) { 32028679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, " %s", TcpFlags[n]); 32128679Sbrian loglen += strlen(logbuf + loglen); 32228679Sbrian } 3236059Samurai n++; 3246059Samurai } 32528679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 32628679Sbrian " seq:%x ack:%x (%d/%d)", 32728679Sbrian ntohl(th->th_seq), ntohl(th->th_ack), len, nb); 32828679Sbrian loglen += strlen(logbuf + loglen); 3296059Samurai if ((th->th_flags & TH_SYN) && nb > 40) { 33028679Sbrian u_short *sp; 3316059Samurai 3326059Samurai ptop += 20; 33328679Sbrian sp = (u_short *) ptop; 33426692Sbrian if (ntohs(sp[0]) == 0x0204) { 33528679Sbrian snprintf(logbuf + loglen, sizeof logbuf - loglen, 33628679Sbrian " MSS = %d", ntohs(sp[1])); 33728679Sbrian loglen += strlen(logbuf + loglen); 33828679Sbrian } 3396059Samurai } 3406059Samurai } 3416059Samurai break; 3426059Samurai } 34326692Sbrian 34413733Sdfr if ((FilterCheck(pip, direction) & A_DENY)) { 34531142Sbrian if (logit) 34631142Sbrian LogPrintf(LogTCPIP, "%s - BLOCKED\n", logbuf); 34728679Sbrian if (direction == 0) 34828679Sbrian IcmpError(pip, pri); 34928679Sbrian return (-1); 3506059Samurai } else { 35128679Sbrian if (FilterCheck(pip, FL_KEEP) & A_DENY) { /* Check Keep Alive filter */ 35231142Sbrian if (logit) 35331142Sbrian LogPrintf(LogTCPIP, "%s - NO KEEPALIVE\n", logbuf); 35430715Sbrian ipKeepAlive = 0; 3556735Samurai } else { 35631142Sbrian if (logit) 35731142Sbrian LogPrintf(LogTCPIP, "%s\n", logbuf); 35830715Sbrian ipKeepAlive = 1; 3596735Samurai } 36028679Sbrian return (pri); 3616059Samurai } 3626059Samurai} 3636059Samurai 3646059Samuraivoid 36528679SbrianIpInput(struct mbuf * bp) 36628679Sbrian{ /* IN: Pointer to IP pakcet */ 3676059Samurai u_char *cp; 3686059Samurai struct mbuf *wp; 3696059Samurai int nb, nw; 3706059Samurai u_char tunbuff[MAX_MRU]; 3716059Samurai 3726059Samurai cp = tunbuff; 3736059Samurai nb = 0; 37428679Sbrian for (wp = bp; wp; wp = wp->next) { /* Copy to contiguous region */ 37530715Sbrian memcpy(cp, MBUF_CTOP(wp), wp->cnt); 3766059Samurai cp += wp->cnt; 3776059Samurai nb += wp->cnt; 3786059Samurai } 3796059Samurai 38020365Sjkh if (mode & MODE_ALIAS) { 38126031Sbrian int iresult; 38226031Sbrian char *fptr; 38326031Sbrian 38426142Sbrian iresult = VarPacketAliasIn(tunbuff, sizeof tunbuff); 38526031Sbrian nb = ntohs(((struct ip *) tunbuff)->ip_len); 38626031Sbrian 38726031Sbrian if (nb > MAX_MRU) { 38826516Sbrian LogPrintf(LogERROR, "IpInput: Problem with IP header length\n"); 38926031Sbrian pfree(bp); 39026031Sbrian return; 39126031Sbrian } 39226031Sbrian if (iresult == PKT_ALIAS_OK 39328679Sbrian || iresult == PKT_ALIAS_FOUND_HEADER_FRAGMENT) { 39428679Sbrian if (PacketCheck(tunbuff, nb, FL_IN) < 0) { 39528679Sbrian pfree(bp); 39628679Sbrian return; 39726031Sbrian } 39826031Sbrian ipInOctets += nb; 39926031Sbrian 40026031Sbrian nb = ntohs(((struct ip *) tunbuff)->ip_len); 40126031Sbrian nw = write(tun_out, tunbuff, nb); 40226031Sbrian if (nw != nb) 40330092Sbrian if (nw == -1) 40430092Sbrian LogPrintf(LogERROR, "IpInput: wrote %d, got %s\n", nb, 40530092Sbrian strerror(errno)); 40630092Sbrian else 40730092Sbrian LogPrintf(LogERROR, "IpInput: wrote %d, got %d\n", nb, nw); 40826031Sbrian 40926031Sbrian if (iresult == PKT_ALIAS_FOUND_HEADER_FRAGMENT) { 41028679Sbrian while ((fptr = VarPacketAliasGetFragment(tunbuff)) != NULL) { 41128679Sbrian VarPacketAliasFragmentIn(tunbuff, fptr); 41228679Sbrian nb = ntohs(((struct ip *) fptr)->ip_len); 41328679Sbrian nw = write(tun_out, fptr, nb); 41428679Sbrian if (nw != nb) 41530092Sbrian if (nw == -1) 41630092Sbrian LogPrintf(LogERROR, "IpInput: wrote %d, got %s\n", nb, 41730092Sbrian strerror(errno)); 41830092Sbrian else 41930092Sbrian LogPrintf(LogERROR, "IpInput: wrote %d, got %d\n", nb, nw); 42028679Sbrian free(fptr); 42128679Sbrian } 42226031Sbrian } 42328679Sbrian } else if (iresult == PKT_ALIAS_UNRESOLVED_FRAGMENT) { 42426031Sbrian nb = ntohs(((struct ip *) tunbuff)->ip_len); 42526031Sbrian fptr = malloc(nb); 42626516Sbrian if (fptr == NULL) 42728679Sbrian LogPrintf(LogALERT, "IpInput: Cannot allocate memory for fragment\n"); 42826031Sbrian else { 42928679Sbrian memcpy(fptr, tunbuff, nb); 43028679Sbrian VarPacketAliasSaveFragment(fptr); 43126031Sbrian } 43226031Sbrian } 43328679Sbrian } else { /* no aliasing */ 43428679Sbrian if (PacketCheck(tunbuff, nb, FL_IN) < 0) { 43526031Sbrian pfree(bp); 43626031Sbrian return; 43726031Sbrian } 43826031Sbrian ipInOctets += nb; 43926031Sbrian nw = write(tun_out, tunbuff, nb); 44026031Sbrian if (nw != nb) 44130092Sbrian if (nw == -1) 44230092Sbrian LogPrintf(LogERROR, "IpInput: wrote %d, got %s\n", nb, strerror(errno)); 44330092Sbrian else 44430092Sbrian LogPrintf(LogERROR, "IpInput: wrote %d, got %d\n", nb, nw); 4456059Samurai } 4466059Samurai pfree(bp); 4476059Samurai 4486059Samurai RestartIdleTimer(); 4496059Samurai} 4506059Samurai 45128679Sbrianstatic struct mqueue IpOutputQueues[PRI_FAST + 1]; 4526059Samurai 4536059Samuraivoid 45428679SbrianIpEnqueue(int pri, char *ptr, int count) 4556059Samurai{ 4566059Samurai struct mbuf *bp; 4576059Samurai 4586059Samurai bp = mballoc(count, MB_IPQ); 45930715Sbrian memcpy(MBUF_CTOP(bp), ptr, count); 4606059Samurai Enqueue(&IpOutputQueues[pri], bp); 4616059Samurai} 4626059Samurai 46330715Sbrian#if 0 4648857Srgrimesint 4657001SamuraiIsIpEnqueued() 4667001Samurai{ 4677001Samurai struct mqueue *queue; 46830715Sbrian int exist = 0; 46928679Sbrian 47013733Sdfr for (queue = &IpOutputQueues[PRI_FAST]; queue >= IpOutputQueues; queue--) { 47128679Sbrian if (queue->qlen > 0) { 47230715Sbrian exist = 1; 47328679Sbrian break; 47428679Sbrian } 4757001Samurai } 47628679Sbrian return (exist); 4777001Samurai} 47830715Sbrian#endif 4797001Samurai 4806059Samuraivoid 4816059SamuraiIpStartOutput() 4826059Samurai{ 4836059Samurai struct mqueue *queue; 4846059Samurai struct mbuf *bp; 48525630Sbrian int cnt; 4866059Samurai 4876059Samurai if (IpcpFsm.state != ST_OPENED) 4886059Samurai return; 48913733Sdfr for (queue = &IpOutputQueues[PRI_FAST]; queue >= IpOutputQueues; queue--) { 4906059Samurai if (queue->top) { 4916059Samurai bp = Dequeue(queue); 4926059Samurai if (bp) { 4936059Samurai cnt = plength(bp); 49413733Sdfr SendPppFrame(bp); 4956059Samurai RestartIdleTimer(); 4966059Samurai ipOutOctets += cnt; 49713733Sdfr break; 49828679Sbrian } 4996059Samurai } 5006059Samurai } 5016059Samurai} 502