static int ipip_send(struct mbuf **bpp, struct iface *ifp, int32 gateway, uint8 tos) { char buf[MAX_FRAME]; int l; struct edv_t *edv; struct sockaddr_in addr; dump(ifp, IF_TRACE_OUT, *bpp); ifp->rawsndcnt++; ifp->lastsent = secclock(); if (ifp->trace & IF_TRACE_RAW) raw_dump(ifp, -1, *bpp); l = pullup(bpp, buf, sizeof(buf)); if (l <= 0 || *bpp) { free_p(bpp); return -1; } edv = (struct edv_t *) ifp->edv; addr.sin_family = AF_INET; addr.sin_addr.s_addr = htonl(gateway); addr.sin_port = htons(edv->port); sendto(edv->fd, buf, l, 0, (struct sockaddr *) &addr, sizeof(addr)); return l; }
static int ethertap_send(struct mbuf **bpp, struct iface *ifp, int32 gateway, uint8 tos) { int l; struct edv_t *edv; struct ethertap_packet ethertap_packet; static const unsigned char ethernet_header[16] = { 0x00, 0x00, /* ??? */ 0xfe, 0xfd, 0x00, 0x00, 0x00, 0x00, /* Destination address (kernel ethertap module) */ 0xfe, 0xfe, 0x00, 0x00, 0x00, 0x00, /* Source address (WAMPES ethertap module) */ 0x08, 0x00 /* Protocol (IP) */ }; edv = (struct edv_t *) ifp->edv; dump(ifp, IF_TRACE_OUT, *bpp); ifp->rawsndcnt++; ifp->lastsent = secclock(); if (ifp->trace & IF_TRACE_RAW) { raw_dump(ifp, -1, *bpp); } l = pullup(bpp, ethertap_packet.data, sizeof(ethertap_packet.data)); if (l <= 0 || *bpp) { free_p(bpp); return -1; } memcpy(ethertap_packet.ethernet_header, (const char *) ethernet_header, sizeof(ethernet_header)); write(edv->fd, ðertap_packet, l + sizeof(ethertap_packet.ethernet_header)); return l; }
static int domail_list(int argc, char *argv[], void *p) { char *state; char waittime[16]; struct mailsys *sp; printf("System Mailer Transport State Wait time\n"); for (sp = Systems; sp; sp = sp->next) { *waittime = 0; switch (sp->state) { case MS_NEVER: state = ""; break; case MS_SUCCESS: state = "Success"; break; case MS_FAILURE: state = "Failure"; if (sp->nexttime > secclock()) sprintf(waittime, "%ld sec", sp->nexttime - secclock()); break; case MS_TRYING: state = "Trying"; break; case MS_TALKING: state = "Talking"; break; default: state = "?"; break; } printf("%-10s %-7s %-10s %-8s %9s\n", sp->sysname, sp->mailer->name, sp->protocol, state, waittime); } return 0; }
/* Send a raw slip frame */ int slip_raw( struct iface *iface, struct mbuf **bpp ){ struct mbuf *bp1; dump(iface,IF_TRACE_OUT,*bpp); iface->rawsndcnt++; iface->lastsent = secclock(); if((bp1 = slip_encode(bpp)) == NULL){ return -1; } if (iface->trace & IF_TRACE_RAW) raw_dump(iface,-1,bp1); return Slip[iface->xdev].send(iface->dev,&bp1); }
static void read_configuration(void) { FILE *fp; char *cp; char *sysname, *mailername, *protocol, *address; char line[1024]; const struct mailers *mailer; static int lastmtime; struct mailsys *sp; struct stat statbuf; for (sp = Systems; sp; sp = sp->next) if (sp->state >= MS_TRYING) return; if (stat(CONFFILE, &statbuf)) return; if (lastmtime == statbuf.st_mtime || statbuf.st_mtime > secclock() - 5) return; if (!(fp = fopen(CONFFILE, "r"))) return; while ((sp = Systems)) { Systems = Systems->next; free(sp->sysname); free(sp->protocol); free(sp->address); free(sp); } while (fgets(line, sizeof(line), fp)) { if ((cp = strchr(line, '#'))) *cp = 0; if (!(sysname = strtok(line, ":"))) continue; if (!(mailername = strtok(NULL, ":"))) continue; if (!(protocol = strtok(NULL, ":"))) continue; if (!(address = strtok(NULL, ":"))) continue; strtrim(address); for (mailer = Mailers; mailer->name; mailer++) if (!strcmp(mailer->name, mailername)) break; if (!mailer->name) continue; sp = (struct mailsys *) calloc(1, sizeof(struct mailsys)); sp->sysname = strdup(sysname); sp->mailer = mailer; sp->protocol = strdup(protocol); sp->address = strdup(address); sp->next = Systems; Systems = sp; } fclose(fp); lastmtime = (int) statbuf.st_mtime; }
/* Log messages of the form * Tue Jan 31 00:00:00 1987 44.64.0.7:1003 open FTP */ void trace_log(struct iface *ifp,char *fmt, ...) { va_list ap; char *cp; long t; FILE *fp; if((fp = ifp->trfp) == NULL) return; t = secclock(); cp = ctime((time_t *) &t); rip(cp); fprintf(fp,"%s - ",cp); va_start(ap,fmt); vfprintf(fp,fmt,ap); va_end(ap); fprintf(fp,"\n"); }
static char *date_time_str (int32 timepast) { long days, hours, mins, secs; static char tmptime[50]; char *fptr, *tmpptr; /* 14Aug2010, Maiko, Should really be using a format string here */ sprintf (tmptime, "%s", tformat (secclock() - timepast)); tmpptr = tmptime; // log (-1, "date_time_str (%d) [%s]", strlen (tmptime), tmptime); days = strtol (tmpptr, &tmpptr, 0); hours = strtol (tmpptr+1, &tmpptr, 0); mins = strtol (tmpptr+1, &tmpptr, 0); secs = strtol (tmpptr+1, &tmpptr, 0); fptr = tmptime; /* log (-1, "days %ld hours %ld mins %ld secs %ld", days, hours, mins, secs); */ *fptr = 0; /* always start with a null string */ if (days) fptr += sprintf (fptr, " %ld day", days); if (hours) fptr += sprintf (fptr, " %ld hour", hours); if (mins) fptr += sprintf (fptr, " %ld min", mins); if (secs) fptr += sprintf (fptr, " %ld sec", secs); return tmptime; }
/* Send an IP datagram. Modeled after the example interface on p 32 of * RFC 791 */ int ip_send( int32 source, /* source address */ int32 dest, /* Destination address */ char protocol, /* Protocol */ char tos, /* Type of service */ char ttl, /* Time-to-live */ struct mbuf **bpp, /* Data portion of datagram */ uint16 length, /* Optional length of data portion */ uint16 id, /* Optional identification */ char df /* Don't-fragment flag */ ){ struct ip ip; /* IP header */ ipOutRequests++; if(bpp == NULL) return -1; if(source == INADDR_ANY) source = locaddr(dest); if(length == 0 && *bpp != NULL) length = len_p(*bpp); if(id == 0) id = Id_cntr++; if(ttl == 0) ttl = ipDefaultTTL; /* Fill in IP header */ ip.version = IPVERSION; ip.tos = tos; ip.length = IPLEN + length; ip.id = id; ip.offset = 0; ip.flags.mf = 0; ip.flags.df = df; ip.flags.congest = 0; ip.ttl = ttl; ip.protocol = protocol; ip.source = source; ip.dest = dest; ip.optlen = 0; if(Ip_trace) dumpip(NULL,&ip,*bpp,0); htonip(&ip,bpp,IP_CS_NEW); if(ismyaddr(ip.dest)){ /* Pretend it has been sent by the loopback interface before * it appears in the receive queue */ #ifdef SIM net_sim(bpp); #else net_route(&Loopback,bpp); #endif Loopback.ipsndcnt++; Loopback.rawsndcnt++; Loopback.lastsent = secclock(); } else net_route(NULL,bpp); return 0; }
void dump( struct iface *ifp, int direction, struct mbuf *bp ){ struct mbuf *tbp; uint size; time_t timer; char *cp; struct iftype *ift; FILE *fp; if(ifp == NULL || (ifp->trace & direction) == 0 || (fp = ifp->trfp) == NULL) return; /* Nothing to trace */ ift = ifp->iftype; switch(direction){ case IF_TRACE_IN: if((ifp->trace & IF_TRACE_NOBC) && ift != NULL && (ift->addrtest != NULL) && (*ift->addrtest)(ifp,bp) == 0) return; /* broadcasts are suppressed */ timer = (time_t) secclock(); cp = ctime(&timer); cp[24] = '\0'; fprintf(fp,"\n%s - %s recv:\n",cp,ifp->name); break; case IF_TRACE_OUT: timer = (time_t) secclock(); cp = ctime(&timer); cp[24] = '\0'; fprintf(fp,"\n%s - %s sent:\n",cp,ifp->name); break; } if(bp == NULL || (size = len_p(bp)) == 0){ fprintf(fp,"empty packet!!\n"); return; } dup_p(&tbp,bp,0,size); if(tbp == NULL){ fprintf(fp,nospace); return; } if(ift != NULL && ift->trace != NULL) (*ift->trace)(fp,&tbp,1); if(ifp->trace & IF_TRACE_ASCII){ /* Dump only data portion of packet in ascii */ ascii_dump(fp,&tbp); } else if(ifp->trace & IF_TRACE_HEX){ /* Dump entire packet in hex/ascii */ free_p(&tbp); dup_p(&tbp,bp,0,len_p(bp)); if(tbp != NULL) hex_dump(fp,&tbp); else fprintf(fp,nospace); } free_p(&tbp); }
static void mail_tick(char *sysname) { DIR *dirp; FILE *fp; char line[1024]; char spooldir[80]; char tmp1[1024]; char tmp2[1024]; char tmp3[1024]; int clients; int cnt; struct dirent *dp; struct mailjob mj, *jp, *tail; struct mailsys *sp; struct stat statbuf; struct filelist { struct filelist *next; char name[16]; } *filelist, *p, *q; if (!*UUCP_DIR) return; start_timer(&Mail_timer); read_configuration(); for (clients = 0, sp = Systems; sp; sp = sp->next) if (sp->state >= MS_TRYING) clients++; for (sp = Systems; sp && clients < Maxclients; sp = sp->next) { if (sysname && !strcmp(sp->sysname, sysname)) sp->nexttime = 0; if (sp->state >= MS_TRYING || sp->nexttime > secclock()) continue; sprintf(spooldir, "%s/%s", UUCP_DIR, sp->sysname); if (!(dirp = opendir(spooldir))) continue; filelist = 0; cnt = 0; for (dp = readdir(dirp); dp; dp = readdir(dirp)) { if (*dp->d_name != 'C') continue; p = (struct filelist *) malloc(sizeof(struct filelist)); strcpy(p->name, dp->d_name); if (!filelist || strcmp(p->name, filelist->name) < 0) { p->next = filelist; filelist = p; } else { for (q = filelist; q->next && strcmp(p->name, q->next->name) > 0; q = q->next) ; p->next = q->next; q->next = p; } if (++cnt > MAXJOBS) { for (q = 0, p = filelist; p->next; q = p, p = p->next) ; q->next = 0; free(p); cnt--; } } closedir(dirp); tail = 0; for (; (p = filelist); filelist = p->next, free(p)) { memset(&mj, 0, sizeof(mj)); sprintf(mj.cfile, "%s/%s", spooldir, p->name); if (!(fp = fopen(mj.cfile, "r"))) continue; while (fgets(line, sizeof(line), fp)) { if (*line == 'E' && sscanf(line, "%*s %*s %*s %*s %*s %s %*s %*s %*s %s %s", tmp1, tmp2, tmp3) == 3 && *tmp1 == 'D' && !strcmp(tmp2, "rmail")) { sprintf(mj.dfile, "%s/%s", spooldir, tmp1); sprintf(mj.to, "%s!%s", sp->sysname, tmp3); strtrim(mj.to); } if (*line == 'S' && sscanf(line, "%*s %*s %s %*s %*s %s", tmp1, tmp2) == 2 && *tmp1 == 'D') sprintf(mj.dfile, "%s/%s", spooldir, tmp2); if (*line == 'S' && sscanf(line, "%*s %*s %s %*s %*s %s", tmp1, tmp2) == 2 && *tmp1 == 'X') sprintf(mj.xfile, "%s/%s", spooldir, tmp2); } fclose(fp); if (!*mj.dfile) continue; if (*mj.xfile) { if (!(fp = fopen(mj.xfile, "r"))) continue; while (fgets(line, sizeof(line), fp)) if (!strncmp(line, "C rmail ", 8)) { sprintf(mj.to, "%s!%s", sp->sysname, line + 8); strtrim(mj.to); break; } fclose(fp); } if (!*mj.to) continue; if (!(fp = fopen(mj.dfile, "r"))) continue; if (fscanf(fp, "%*s %s", tmp1) == 1) { if (!strcmp(tmp1, "MAILER-DAEMON") || !strcmp(tmp1, "!")) strcpy(tmp1, Hostname); sprintf(mj.from, "%s!%s", Hostname, tmp1); strtrim(mj.from); while (fgets(line, sizeof(line), fp)) if (!strncmp(line, "Subject: ", 9)) { strcpy(mj.subject, line + 9); strtrim(mj.subject); break; } } fclose(fp); if (!*mj.from) continue; if (stat(mj.cfile, &statbuf)) continue; if (statbuf.st_mtime + RETURNTIME < secclock()) { sprintf(mj.return_reason, "520 %s... Cannot connect for %ld days\n", sp->sysname, RETURNTIME / (60L*60*24)); mail_return(&mj); } else { jp = (struct mailjob *) malloc(sizeof(struct mailjob)); *jp = mj; if (!sp->jobs) sp->jobs = jp; else tail->next = jp; tail = jp; } } if (sp->jobs) { sp->state = MS_TRYING; clients++; (*sp->mailer->func)(sp); } } }