about summary refs log tree commit diff
path: root/Completion/Unix/Command/_tcpdump
blob: 9aad84d7b46a0d600689bf1d120b392bc497e3a8 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
#compdef tcpdump

local args ret=1
local root
(( EUID )) && root='!'

_tcpdump_interfaces() {
  local disp expl sep interfaces
  [[ $OSTYPE != openbsd* ]] &&
      interfaces=( ${${${${(f)"$(_call_program interfaces tcpdump -D)"}#<->.}//[()]/}/ /:} )
  if (( $#interfaces )); then
    _describe -t interfaces 'network interface' interfaces
  else
    _description interfaces expl 'network interface'
    _net_interfaces "$expl[@]"
    if zstyle -t ":completion:${curcontext}:interfaces" verbose; then
      zstyle -s ":completion:${curcontext}:interfaces" list-separator sep || sep=--
      disp=( "any $sep capture on all interfaces" )
      compadd "$expl[@]" -ld disp any
    else
      compadd "$expl[@]" any
    fi
  fi
}

_esp_secrets () {
  if [[ $OSTYPE = openbsd* ]]; then
    _values -S : 'ESP algorithm' \
      aes128:secret \
      aes128-hmac96:secret \
      blowfish:secret \
      blowfish-hmac96:secret \
      cast:secret \
      cast-hmac96:secret \
      des3:secret \
      des3-hmac96:secret \
      des:secret \
      des-hmac96:secret
  else
    _values -S : 'ESP algorithm' \
      'des-cbc:secret' \
      '3des-cbc:secret' \
      'blowfish-cbc:secret' \
      'rc3-cbc:secret' \
      'cast128-cbc:secret' \
      none
  fi
}

_packet_types () {
  local -a types
  types=(
    'cnfp:Cisco NetFlow protocol'
    'rpc:Remote Procedure Call'
    'rtp:Real-Time Applications protocol'
    'rtcp:Real-Time Applications control protocol'
    'vat:Visual Audio Tool'
    'wb:distributed White Board'
  )
  if [[ $OSTYPE = openbsd* ]]; then
    types+=(
      'sack:RFC 2018 TCP Selective Acknowledgements Options'
      'vrrp:Virtual Router Redundancy Protocol'
      'tcp:Transmission Control Protocol'
    )
  else
    types+=(
      'aodv:Ad-hoc On-demand Distance Vector protocol'
      'carp:Common Address Redundancy Protocol'
      'radius:RADIUS'
      'snmp:Simple Network Management Protocol'
      'tftp:Trivial File Transfer Protocol'
      'vxlan:Virtual eXtensible Local Area Network'
      'zmtpl:ZeroMQ Message Transport Protocol'
    )
  fi
  _describe -t packet-types 'packet type' types
}

_time_stamp_types () {
  local vals
  vals=( ${${${(ps:\n  :)"$(_call_program time-stamp-types tcpdump -J ${(kv)opt_args[(i)-i|--interface]} 2>&1)"}[2,-1]:#*cannot be set*}/ /:} )
  _describe -t time-stamp-types "time stamp type" vals
}

_data_link_types () {
  local vals expl
  if (( $+opt_args[(i)-i|--interface] )); then
    vals=( ${${${(s:  :)"$(_call_program data-link-types tcpdump -L ${(kv)opt_args[(i)-i|--interface]} 2>&1)"}[2,-1]}/ /:} )
    _describe -t data-link-types "data link type (${(v)opt_args[(i)-i|--interface]})" vals
  else
    _wanted data-link-types expl "data link type (general)" \
        compadd EN10MB LINUX_SLL
  fi
}

_bpf_filter () {
}

args=(
  '-A[print each packet in ASCII]'
  '-c+[exit after receiving specified number of packets]:number of packets'
  '(-ddd)-d[dump the compiled packet-matching code in a human readable form]'
  '(-ddd)-dd[dump packet-matching code as a C program fragment]'
  '(-d -dd)-ddd[dump packet-matching code as decimal numbers (preceded with a count)]'
  "-E[decrypting IPsec ESP packets]:spi@ipaddr::algo\:secret:_esp_secrets"
  '-e[print the link-level header on each dump line]'
  '-F+[specify input file for the filter expression]:filter expression file:_files'
  "-f[print 'foreign' IPv4 addresses numerically]"
  '-l[make stdout line buffered]'
  "-N[don't print domain name qualification of host names]"
  "(-nn)-n[don't convert addresses to names]"
  "-O[don't run the packet-matching code optimizer]"
  '(-p --no-promiscuous-mode)'{-p,--no-promiscuous-mode}"[don't put the interface into promiscuous mode]"
  '-q[quick (quiet?) output]'
  '-r+[read packets from file]:input file:_files'
  '(-S --absolute-tcp-sequence-numbers)'{-S,--absolute-tcp-sequence-numbers}'[print absolute TCP sequence numbers]'
  '-T+[interpret captured packets as specified type]:packet type:_packet_types'
  "(-tt -ttt -tttt -ttttt)-t[don't print a timestamp on each dump line]"
  '(-t -ttt -tttt -ttttt)-tt[print an unformatted timestamp on each dump line]'
  '(-vv -vvv)-v[slightly more verbose output]'
  '(-v -vvv)-vv[more verbose output]'
  '-w+[write the raw packets to file]:output file:_files'
  '-X[print each packet (minus its link level header) in hex and ASCII]'
  '-x[print each packet (minus its link level header) in hex]'
  '(-y --linktype)'{-y+,--linktype=}'[set the data link type to use while capturing packets]: :_data_link_types'
)

if [[ $OSTYPE = openbsd* ]]; then
  args=(
    '-i+[specify interface]:interface:_tcpdump_interfaces'
    - listd
    '-L[list data link types for the interface]'
    - capture
    ${(R)args:#(|\*)(|\(*\))--*} # removes any long-options
    '(-n)-a[attempt to convert network and broadcast addresses to names]'
    '-B+[specify drop action to be used when filter expression matches a packet]:drop action:(pass capture drop)'
    '-D[select packet flowing in specified direction]:direction:(in out)'
    '-I[print the interface on each dump line]'
    '-o[print a guess of the possible operating system(s)]'
    '-s+[specify amount of data to snarf from each packet]:length (bytes) [116]'
    '(-t -tt -tttt -ttttt)-ttt[print day and month in timestamp]'
    '(-t -tt -ttt -ttttt)-tttt[print timestamp difference between packets]'
    '(-t -tt -ttt -tttt)-ttttt[print timestamp difference since the first packet]'
  )
else
  args=(
    '(-i --interface -D --list-interfaces)'{-i+,--interface=}'[specify interface]:interface:_tcpdump_interfaces'
    - listt
    '(-J --list-time-stamp-types)'{-J,--list-time-stamp-types}'[list supported time stamp types]'
    - listd
    '(-L --list-data-link-types)'{-L,--list-data-link-types}'[list data link types for the interface]'
    - capture
    $args
    '(-B --buffer-size)'{-B+,--buffer-size=}'[set the operating system capture buffer size]:size (kiB)'
    '-b[print the AS number in BGP packets in ASDOT notation]'
    '-C+[specify output file size]:output file size (MB)'
    '(-)'{-D,--list-interfaces}'[print the list of the network interfaces available on the system]'
    '-G+[rotate dump file specified with -w at specified interval]:interval (seconds)'
    '-H[attempt to detect 802.11s draft mesh headers]'
    '(- *)'{-h,--help}'[display help information]'
    '(- *)--version[display version information]'
    '(-I --monitor-mode)'{-I,--monitor-mode}'[put the Wi-Fi interface in monitor mode]'
    '--immediate-mode[deliver packets to tcpdump as soon as they arrive without buffering]'
    '-I[put the interface in monitor mode]'
    '(-j --time-stamp-type)'{-j+,--time-stamp-type=}'[set the time stamp type for the capture]: :_time_stamp_types'
    '--time-stamp-precision=[set the time stamp precision for the capture]:precision [micro]:(micro nano)'
    '(-K --dont-verify-checksums)'{-K,--dont-verify-checksums}"[don't verify IP, TCP, or UDP checksums]"
    '*-m+[load SMI MIB module definitions]:SMI MIB module definition:_files'
    "(-n)-nn[don't convert protocol and port numbers to names]"
    '-M+[specify shared secret for validating the digests in TCP segments with the TCP-MD5 option]:secret'
    '(-# --number)'{-\#,--number}'[print an optional packet number at the beginning of the line]'
    '(-O --no-optimize)'{-O,--no-optimize}"[don't run the packet-matching code optimizer]"
    '(-s --snapshot-length)'{-s+,--snapshot-length=}'[specify amount of data to snarf from each packet]:length (bytes) [65535]'
    '(-t -tt -tttt -ttttt)-ttt[print a delta (in micro-seconds) on each line since previous line]'
    '(-t -tt -ttt -ttttt)-tttt[print a timestamp in default format preceded by date on each dump line]'
    '(-t -tt -ttt -tttt)-ttttt[print a delta (in micro-seconds) on each line since first line]'
    '(-U --packet-buffered)'{-U,--packet-buffered}'[make output packet-buffered when saving to file (-w)]'
    '-u[print undecoded NFS handles]'
    '-V+[read a list of filenames from specified file]:file:_files'
    '(-v -vv)-vvv[most verbose output]'
    '-W+[limit the number of created files (-C)]:number of files'
    '(-X)-XX[print each packet, including its link level header, in hex and ASCII]'
    '(-x)-xx[print each packet, including its link level header, in hex]'
    "${root}(-Z --relinquish-privileges)"{-Z+,--relinquish-privileges=}'[drop privileges and run as specified user]:user:_users'
    '-z+[specify command to run on files (with -C or -G)]:command:_command_names -e'
  )
fi
[[ $OSTYPE = freebsd* ]] && args+=(
  '-R[assume ESP/AH packets to be based on old specification (RFC1825 to RFC1829)]'
)

_arguments -s $args \
  '*::BPF filter:= _bpf_filters'