diff --git a/Makefile b/Makefile index 29db8d2..e7dffcb 100644 --- a/Makefile +++ b/Makefile @@ -1,3 +1,10 @@ CFLAGS = -Wall -Werror +TARGETS = pmerge puniq -pmerge: pmerge.o pcap.o \ No newline at end of file +all: $(TARGETS) + +pmerge: pmerge.o pcap.o +puniq: puniq.o pcap.o + +clean: + rm -f $(TARGETS) diff --git a/pcap.c b/pcap.c index 7e1770c..e3e6ae9 100644 --- a/pcap.c +++ b/pcap.c @@ -1,54 +1,42 @@ #include #include +#include #include "pcap.h" int -pcap_read_header(FILE *f) +pcap_open_in(struct pcap_file *ctx, FILE *f) { struct pcap_file_header h; - int swap; if (1 != fread(&h, sizeof(h), 1, f)) { h.magic = 0; } if (MAGIC == h.magic) { - swap = 0; + ctx->swap = 0; } else if (bswap32(MAGIC) == h.magic) { - swap = 1; + ctx->swap = 1; } else { return -1; } if ((h.version_major != 2) || (h.version_minor != 4)) return -1; - if (swap) h.snaplen = bswap32(h.snaplen); + if (ctx->swap) h.snaplen = bswap32(h.snaplen); if (h.snaplen > MAXFRAME) return -1; - return swap; -} - -int -pcap_write_header(FILE *f) -{ - struct pcap_file_header h = { MAGIC, 2, 4, 0, 0, MAXFRAME, 1 }; - - if (1 != fwrite(&h, sizeof(h), 1, stdout)) { - return -1; - } - + ctx->f = f; return 0; } int -pcap_open_in(struct pcap_file *ctx, FILE *f) +pcap_open_out(struct pcap_file *ctx, FILE *f) { - int ret; + struct pcap_file_header h = { MAGIC, 2, 4, 0, 0, MAXFRAME, 1 }; - ret = pcap_read_header(f); - if (-1 == ret) return -1; - - ctx->swap = ret; + if (1 != fwrite(&h, sizeof(h), 1, f)) return -1; ctx->f = f; + ctx->swap = 0; + return 0; } @@ -69,6 +57,26 @@ pcap_read_pkthdr(struct pcap_file *ctx, struct pcap_pkthdr *hdr) return 0; } +int +pcap_write_pkthdr(struct pcap_file *ctx, struct pcap_pkthdr *hdr) +{ + if (ctx->swap) { + struct pcap_pkthdr ohdr; + + memcpy(&ohdr, hdr, sizeof(ohdr)); + hdr->ts.tv_sec = bswap32(hdr->ts.tv_sec); + hdr->ts.tv_usec = bswap32(hdr->ts.tv_usec); + hdr->caplen = bswap32(hdr->caplen); + hdr->len = bswap32(hdr->len); + + if (1 != fwrite(&ohdr, sizeof(ohdr), 1, ctx->f)) return -1; + } else { + if (1 != fwrite(hdr, sizeof(*hdr), 1, ctx->f)) return -1; + } + + return 0; +} + void pcap_close(struct pcap_file *ctx) { diff --git a/pcap.h b/pcap.h index 0c08feb..41ffe6f 100644 --- a/pcap.h +++ b/pcap.h @@ -57,10 +57,10 @@ struct pcap_pkthdr { #define DUMP_c(v) DUMPf("%s = %c", #v, v) #define DUMP_p(v) DUMPf("%s = %p", #v, v) -int pcap_read_header(FILE *f); -int pcap_write_header(FILE *f); int pcap_open_in(struct pcap_file *ctx, FILE *f); +int pcap_open_out(struct pcap_file *ctx, FILE *f); int pcap_read_pkthdr(struct pcap_file *ctx, struct pcap_pkthdr *hdr); +int pcap_write_pkthdr(struct pcap_file *ctx, struct pcap_pkthdr *hdr); void pcap_close(struct pcap_file *ctx); #endif /* __PCAP_H__ */ diff --git a/pmerge.c b/pmerge.c index dae49a9..94c0c13 100644 --- a/pmerge.c +++ b/pmerge.c @@ -40,7 +40,8 @@ main(int argc, char *argv[]) struct input_file files[argc-1]; int nfiles = 0; int nopen; - int i, ret; + int i; + struct pcap_file out; if (1 == argc) return usage(0); @@ -58,8 +59,7 @@ main(int argc, char *argv[]) return EX_NOINPUT; } - ret = pcap_open_in(&cur->p, f); - if (-1 == ret) { + if (-1 == pcap_open_in(&cur->p, f)) { fprintf(stderr, "%s: unable to process\n", fn); return EX_IOERR; } @@ -70,14 +70,12 @@ main(int argc, char *argv[]) } } - ret = pcap_write_header(stdout); - if (-1 == ret) { + if (-1 == pcap_open_out(&out, stdout)) { perror("writing header"); return EX_IOERR; } nopen = nfiles; - DUMP_d(nopen); while (nopen) { struct input_file *cur = &files[0]; char frame[MAXFRAME]; diff --git a/puniq.c b/puniq.c new file mode 100644 index 0000000..0a5f767 --- /dev/null +++ b/puniq.c @@ -0,0 +1,64 @@ +#include +#include +#include +#include +#include "pcap.h" + +int +main(int argc, char *argv[]) +{ + int i; + struct pcap_pkthdr hdr[2]; + char frame[2][MAXFRAME]; + int cur = 0; + struct pcap_file out; + + memset(&hdr, 0, sizeof(hdr)); + memset(frame, 0, 2 * MAXFRAME); + + if (-1 == pcap_open_out(&out, stdout)) { + perror("writing header"); + return EX_IOERR; + } + + i = 1; + do { + char *fn = argv[i]; + FILE *f; + struct pcap_file p; + + if ((! fn) || (0 == strcmp("-", fn))) { + f = stdin; + } else { + f = fopen(fn, "rb"); + if (NULL == f) { + perror(fn); + return EX_IOERR; + } + } + + if (-1 == pcap_open_in(&p, f)) { + fprintf(stderr, "%s: unable to process\n", fn); + return EX_IOERR; + } + + while (1) { + if (-1 == pcap_read_pkthdr(&p, &hdr[cur])) break; + if (1 != fread(frame[cur], hdr[cur].caplen, 1, p.f)) break; + + if ((0 == memcmp(&hdr[0], &hdr[1], sizeof(hdr[0]))) && + (0 == memcmp(frame[0], frame[1], hdr[cur].caplen))) { + /* Skip this duplicate */ + } else { + if (-1 == pcap_write_pkthdr(&out, &hdr[cur])) break; + if (1 != fwrite(frame[cur], hdr[cur].caplen, 1, out.f)) break; + } + cur = (1 - cur); + } + pcap_close(&p); + + i += 1; + } while (i < argc); + + return 0; +}