ktcpdump.c
最終更新:2010/1/12
001: /*
002: * ktcpdump.c
003: * libpcap を使った TCP パケット解析サンプルコード
004: * Ctrl-C で終了。
005: */
006:
007: #define PROG_NAME "ktcpdump"
008:
009: #include "mystab_pcap.h"
010: #include "apr_getopt.h"
011:
012: static const apr_getopt_option_t opt_option[] = {
013: /* long-option, short-option, has-arg flag, description */
014: { "port_number", 'p', TRUE, "[MUST] port_number" },
015: { "interface", 'i', TRUE, "[MUST] network device to use" },
016: { "help", 'h', FALSE, "[OPTION] show help" }, /* -h or --help */
017:
018: #if defined(WIN32) || defined(WINDOWS) || defined(MSVC)
019:
020: { "disp_interfaces", 'D', FALSE,
021: "[OPTION] displays avalable interfaces (Windows Only)" },
022:
023: #endif
024:
025:
026: { NULL, 0, 0, NULL }, /* SENTINEL */
027: };
028:
029: void print_usage (apr_file_t *out) {
030: apr_getopt_option_t *ptr = (apr_getopt_option_t *)opt_option;
031:
032: apr_file_printf(out, "Usage: %s ", PROG_NAME);
033: while (ptr && ptr->name) {
034: if (ptr->has_arg) {
035: apr_file_printf(out, "[ -%c <arg> | --%s <arg> ] ", ptr->optch,
036: ptr->name);
037: } else {
038: apr_file_printf(out, "[ -%c | --%s ] ", ptr->optch, ptr->name);
039: }
040: ptr++;
041: }
042: apr_file_printf(out, "\n");
043: ptr = (apr_getopt_option_t *)opt_option;
044: while (ptr && ptr->name) {
045: apr_file_printf(out, "\t-%c, --%s\t: %s\n", ptr->optch, ptr->name,
046: ptr->description);
047: ptr++;
048: }
049:
050: }
051:
052: int my_pcap_init (
053: int ac
054: , char **av
055: , my_pcap_params *params
056: , apr_file_t *astderr
057: , apr_pool_t *pool
058: ) {
059: apr_status_t rv = APR_SUCCESS;
060:
061: apr_getopt_t *opt = NULL;
062: int opt_ch = 0;
063: const char *opt_arg = NULL;
064:
065: apr_uint16_t port_number = 0;
066: const char * interface_str = NULL;
067:
068: if (ac < 2) {
069: print_usage(astderr);
070: return 0;
071: }
072:
073: rv = apr_getopt_init(&opt, pool, ac, (const char * const *)av);
074:
075: if (rv != APR_SUCCESS) {
076: apr_file_printf(astderr, "ERROR: apr_getopt_init\n");
077: return 0;
078: }
079:
080: while ((rv = apr_getopt_long(opt, opt_option, &opt_ch, &opt_arg))
081: == APR_SUCCESS) {
082:
083: switch (opt_ch) {
084: case 'p':
085: port_number = atoi(opt_arg);
086: break;
087: case 'i':
088: interface_str = opt_arg;
089: break;
090:
091: #if defined(WIN32) || defined(WINDOWS) || defined(MSVC)
092:
093: case 'D':
094: {
095: char errbuf[80];
096: if (! disp_devices(astderr, errbuf, sizeof(errbuf))) {
097: apr_file_printf(astderr, "ERROR: disp_devices: %s\n", errbuf);
098: }
099: }
100: return 0;
101: break;
102:
103: #endif
104:
105: case 'h':
106: print_usage(astderr);
107: return 0;
108: }
109:
110: }
111:
112: if (rv != APR_EOF || port_number<=0 || !interface_str) {
113: print_usage(astderr);
114: return 0;
115: }
116:
117: params->device = interface_str;
118: params->filter = apr_psprintf(pool, "tcp port %d", port_number);
119:
120: return 1;
121: }
122:
123: void my_pcap_main(
124: apr_pool_t *pool
125: , apr_file_t *out
126: , my_tcp_pkt *d
127: ) {
128: if (!d || !pool || !out) {
129: return;
130: }
131:
132: apr_file_printf(out, "[%s:%d-%s:%d] seq_no=%d ack_no=%d size=%d\n",
133: d->ip_src_addr, d->tcp_src_port, d->ip_dst_addr, d->tcp_dst_port,
134: d->tcp_seq_no, d->tcp_ack_no,
135: d->tcp_payload_size);
136: apr_file_printf(out, "\turg=%d ack=%d psh=%d rst=%d syn=%d fin=%d",
137: d->tcp_urg_bit, d->tcp_ack_bit, d->tcp_psh_bit, d->tcp_rst_bit,
138: d->tcp_syn_bit, d->tcp_fin_bit);
139:
140: if (d->tcp_payload_size > 0) {
141: int i=0;
142: for (i=0; i<d->tcp_payload_size; i++) {
143: if (i%32 == 0) {
144: apr_file_printf(out, "\n");
145: }
146: apr_file_printf(out, "%02X", d->tcp_payload_pos[i]);
147: }
148: apr_file_printf(out, "\n");
149: }
150:
151: apr_file_printf(out, "\n");
152: }
153:
154: void my_pcap_finally (
155: apr_file_t *out
156: ) {
157: apr_file_printf(out, "done.\n");
158: }
![]() | KAKU PROJECT (2009) |