xref: /aosp_15_r20/external/ethtool/shell-completion/bash/ethtool (revision 1b481fc3bb1b45d4cf28d1ec12969dc1055f555d)
1*1b481fc3SMaciej Żenczykowski# bash completion for ethtool(8)                          -*- shell-script -*-
2*1b481fc3SMaciej Żenczykowski# shellcheck shell=bash disable=SC2207
3*1b481fc3SMaciej Żenczykowski
4*1b481fc3SMaciej Żenczykowski# Complete a word representing a set of characters.
5*1b481fc3SMaciej Żenczykowski# @param $@ chars	Characters which may be present in completed set.
6*1b481fc3SMaciej Żenczykowski_ethtool_compgen_letterset()
7*1b481fc3SMaciej Żenczykowski{
8*1b481fc3SMaciej Żenczykowski	local char
9*1b481fc3SMaciej Żenczykowski	for char; do
10*1b481fc3SMaciej Żenczykowski		case "$cur" in
11*1b481fc3SMaciej Żenczykowski			*"$char"*)
12*1b481fc3SMaciej Żenczykowski				# $cur already contains $char
13*1b481fc3SMaciej Żenczykowski				;;
14*1b481fc3SMaciej Żenczykowski			*)
15*1b481fc3SMaciej Żenczykowski				COMPREPLY+=( "$cur$char" )
16*1b481fc3SMaciej Żenczykowski				;;
17*1b481fc3SMaciej Żenczykowski		esac
18*1b481fc3SMaciej Żenczykowski	done
19*1b481fc3SMaciej Żenczykowski}
20*1b481fc3SMaciej Żenczykowski
21*1b481fc3SMaciej Żenczykowski# Generate completions for words matched case-insensitively
22*1b481fc3SMaciej Żenczykowski# @param $@ choices	Completion choices.
23*1b481fc3SMaciej Żenczykowski_ethtool_compgen_nocase()
24*1b481fc3SMaciej Żenczykowski{
25*1b481fc3SMaciej Żenczykowski	local reset
26*1b481fc3SMaciej Żenczykowski	reset=$( shopt -p nocasematch )
27*1b481fc3SMaciej Żenczykowski	shopt -s nocasematch
28*1b481fc3SMaciej Żenczykowski
29*1b481fc3SMaciej Żenczykowski	local choice
30*1b481fc3SMaciej Żenczykowski	for choice; do
31*1b481fc3SMaciej Żenczykowski		case "$choice" in
32*1b481fc3SMaciej Żenczykowski			"$cur"*) COMPREPLY+=( "$choice" ) ;;
33*1b481fc3SMaciej Żenczykowski		esac
34*1b481fc3SMaciej Żenczykowski	done
35*1b481fc3SMaciej Żenczykowski
36*1b481fc3SMaciej Żenczykowski	$reset
37*1b481fc3SMaciej Żenczykowski}
38*1b481fc3SMaciej Żenczykowski
39*1b481fc3SMaciej Żenczykowski# Gets names from a section of ethtool output.
40*1b481fc3SMaciej Żenczykowski# @param $1 section_bre	POSIX BRE matching section heading (without : at end).
41*1b481fc3SMaciej Żenczykowski# @param $@		ethtool arguments
42*1b481fc3SMaciej Żenczykowski_ethtool_get_names_in_section()
43*1b481fc3SMaciej Żenczykowski{
44*1b481fc3SMaciej Żenczykowski	local section_bre="$1"
45*1b481fc3SMaciej Żenczykowski	shift
46*1b481fc3SMaciej Żenczykowski
47*1b481fc3SMaciej Żenczykowski	PATH="$PATH:/sbin:/usr/sbin:/usr/local/sbin" \
48*1b481fc3SMaciej Żenczykowski		ethtool "$@" 2>/dev/null |
49*1b481fc3SMaciej Żenczykowski		command sed -n "
50*1b481fc3SMaciej Żenczykowski# Line is section heading iff it ends with :
51*1b481fc3SMaciej Żenczykowski# From requested section heading to next section heading
52*1b481fc3SMaciej Żenczykowski/^$section_bre:$/,/:$/ {
53*1b481fc3SMaciej Żenczykowski	# If line is section heading, ignore it
54*1b481fc3SMaciej Żenczykowski	/:$/d
55*1b481fc3SMaciej Żenczykowski	# Remove value and separator, if present
56*1b481fc3SMaciej Żenczykowski	s/[[:space:]]*:.*//
57*1b481fc3SMaciej Żenczykowski	# Remove leading space, if present
58*1b481fc3SMaciej Żenczykowski	s/^[[:space:]]*//
59*1b481fc3SMaciej Żenczykowski	# Print the line
60*1b481fc3SMaciej Żenczykowski	p
61*1b481fc3SMaciej Żenczykowski}"
62*1b481fc3SMaciej Żenczykowski}
63*1b481fc3SMaciej Żenczykowski
64*1b481fc3SMaciej Żenczykowski# Complete an RSS Context ID
65*1b481fc3SMaciej Żenczykowski_ethtool_context()
66*1b481fc3SMaciej Żenczykowski{
67*1b481fc3SMaciej Żenczykowski	COMPREPLY=(
68*1b481fc3SMaciej Żenczykowski		$(PATH="$PATH:/sbin:/usr/sbin:/usr/local/sbin" \
69*1b481fc3SMaciej Żenczykowski			ethtool --show-nfc "${words[2]}" 2>/dev/null |
70*1b481fc3SMaciej Żenczykowski			command sed -n 's/^[[:space:]]*RSS Context ID:[[:space:]]*\([0-9]*\)$/\1/p' |
71*1b481fc3SMaciej Żenczykowski			sort -u) )
72*1b481fc3SMaciej Żenczykowski}
73*1b481fc3SMaciej Żenczykowski
74*1b481fc3SMaciej Żenczykowski# Complete a network flow traffic type
75*1b481fc3SMaciej Żenczykowski# Available OPTIONS:
76*1b481fc3SMaciej Żenczykowski#	 --hash  Complete only types suitable for rx hashing
77*1b481fc3SMaciej Żenczykowski_ethtool_flow_type()
78*1b481fc3SMaciej Żenczykowski{
79*1b481fc3SMaciej Żenczykowski	local types='ah4 ah6 esp4 esp6 ether sctp4 sctp6 tcp4 tcp6 udp4 udp6'
80*1b481fc3SMaciej Żenczykowski	if [ "${1-}" != --hash ]; then
81*1b481fc3SMaciej Żenczykowski		types="$types ip4 ip6"
82*1b481fc3SMaciej Żenczykowski	fi
83*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "$types" -- "$cur" ) )
84*1b481fc3SMaciej Żenczykowski}
85*1b481fc3SMaciej Żenczykowski
86*1b481fc3SMaciej Żenczykowski# Completion for ethtool --change
87*1b481fc3SMaciej Żenczykowski_ethtool_change()
88*1b481fc3SMaciej Żenczykowski{
89*1b481fc3SMaciej Żenczykowski	local -A settings=(
90*1b481fc3SMaciej Żenczykowski		[advertise]=notseen
91*1b481fc3SMaciej Żenczykowski		[autoneg]=notseen
92*1b481fc3SMaciej Żenczykowski		[duplex]=notseen
93*1b481fc3SMaciej Żenczykowski		[mdix]=notseen
94*1b481fc3SMaciej Żenczykowski		[msglvl]=notseen
95*1b481fc3SMaciej Żenczykowski		[port]=notseen
96*1b481fc3SMaciej Żenczykowski		[phyad]=notseen
97*1b481fc3SMaciej Żenczykowski		[speed]=notseen
98*1b481fc3SMaciej Żenczykowski		[wol]=notseen
99*1b481fc3SMaciej Żenczykowski		[xcvr]=notseen
100*1b481fc3SMaciej Żenczykowski		[lanes]=notseen
101*1b481fc3SMaciej Żenczykowski	)
102*1b481fc3SMaciej Żenczykowski
103*1b481fc3SMaciej Żenczykowski	local -A msgtypes=(
104*1b481fc3SMaciej Żenczykowski		[drv]=notseen
105*1b481fc3SMaciej Żenczykowski		[hw]=notseen
106*1b481fc3SMaciej Żenczykowski		[ifdown]=notseen
107*1b481fc3SMaciej Żenczykowski		[ifup]=notseen
108*1b481fc3SMaciej Żenczykowski		[intr]=notseen
109*1b481fc3SMaciej Żenczykowski		[link]=notseen
110*1b481fc3SMaciej Żenczykowski		[pktdata]=notseen
111*1b481fc3SMaciej Żenczykowski		[probe]=notseen
112*1b481fc3SMaciej Żenczykowski		[rx_err]=notseen
113*1b481fc3SMaciej Żenczykowski		[rx_status]=notseen
114*1b481fc3SMaciej Żenczykowski		[timer]=notseen
115*1b481fc3SMaciej Żenczykowski		[tx_done]=notseen
116*1b481fc3SMaciej Żenczykowski		[tx_err]=notseen
117*1b481fc3SMaciej Żenczykowski		[tx_queued]=notseen
118*1b481fc3SMaciej Żenczykowski		[wol]=notseen
119*1b481fc3SMaciej Żenczykowski	)
120*1b481fc3SMaciej Żenczykowski
121*1b481fc3SMaciej Żenczykowski	# Mark seen settings and msgtypes, and whether in msglvl sub-command
122*1b481fc3SMaciej Żenczykowski	local in_msglvl=
123*1b481fc3SMaciej Żenczykowski	local word
124*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
125*1b481fc3SMaciej Żenczykowski		if [ "$in_msglvl" ] && [ "${msgtypes[$word]+set}" ]; then
126*1b481fc3SMaciej Żenczykowski			msgtypes[$word]=seen
127*1b481fc3SMaciej Żenczykowski		elif [ "${settings[$word]+set}" ]; then
128*1b481fc3SMaciej Żenczykowski			settings[$word]=seen
129*1b481fc3SMaciej Żenczykowski			if [ "$word" = msglvl ]; then
130*1b481fc3SMaciej Żenczykowski				in_msglvl=1
131*1b481fc3SMaciej Żenczykowski			else
132*1b481fc3SMaciej Żenczykowski				in_msglvl=
133*1b481fc3SMaciej Żenczykowski			fi
134*1b481fc3SMaciej Żenczykowski		fi
135*1b481fc3SMaciej Żenczykowski	done
136*1b481fc3SMaciej Żenczykowski
137*1b481fc3SMaciej Żenczykowski	if [ "$in_msglvl" ] && [ "${msgtypes[$prev]+set}" ]; then
138*1b481fc3SMaciej Żenczykowski		# All msgtypes take an on/off argument
139*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
140*1b481fc3SMaciej Żenczykowski		return
141*1b481fc3SMaciej Żenczykowski	fi
142*1b481fc3SMaciej Żenczykowski
143*1b481fc3SMaciej Żenczykowski	case "$prev" in
144*1b481fc3SMaciej Żenczykowski		advertise)
145*1b481fc3SMaciej Żenczykowski			# Hex number
146*1b481fc3SMaciej Żenczykowski			return ;;
147*1b481fc3SMaciej Żenczykowski		autoneg)
148*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
149*1b481fc3SMaciej Żenczykowski			return ;;
150*1b481fc3SMaciej Żenczykowski		duplex)
151*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'half full' -- "$cur" ) )
152*1b481fc3SMaciej Żenczykowski			return ;;
153*1b481fc3SMaciej Żenczykowski		mdix)
154*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'auto on off' -- "$cur" ) )
155*1b481fc3SMaciej Żenczykowski			return ;;
156*1b481fc3SMaciej Żenczykowski		msglvl)
157*1b481fc3SMaciej Żenczykowski			# Unsigned integer or msgtype
158*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W "${!msgtypes[*]}" -- "$cur" ) )
159*1b481fc3SMaciej Żenczykowski			return ;;
160*1b481fc3SMaciej Żenczykowski		port)
161*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'aui bnc fibre mii tp' -- "$cur" ) )
162*1b481fc3SMaciej Żenczykowski			return ;;
163*1b481fc3SMaciej Żenczykowski		phyad)
164*1b481fc3SMaciej Żenczykowski			# Integer
165*1b481fc3SMaciej Żenczykowski			return ;;
166*1b481fc3SMaciej Żenczykowski		sopass)
167*1b481fc3SMaciej Żenczykowski			_mac_addresses
168*1b481fc3SMaciej Żenczykowski			return ;;
169*1b481fc3SMaciej Żenczykowski		speed)
170*1b481fc3SMaciej Żenczykowski			# Number
171*1b481fc3SMaciej Żenczykowski			return ;;
172*1b481fc3SMaciej Żenczykowski		wol)
173*1b481fc3SMaciej Żenczykowski			# $cur is a set of wol type characters.
174*1b481fc3SMaciej Żenczykowski			_ethtool_compgen_letterset p u m b a g s f d
175*1b481fc3SMaciej Żenczykowski			return ;;
176*1b481fc3SMaciej Żenczykowski		xcvr)
177*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'internal external' -- "$cur" ) )
178*1b481fc3SMaciej Żenczykowski			return ;;
179*1b481fc3SMaciej Żenczykowski		lanes)
180*1b481fc3SMaciej Żenczykowski			# Number
181*1b481fc3SMaciej Żenczykowski			return ;;
182*1b481fc3SMaciej Żenczykowski	esac
183*1b481fc3SMaciej Żenczykowski
184*1b481fc3SMaciej Żenczykowski	local -a comp_words=()
185*1b481fc3SMaciej Żenczykowski
186*1b481fc3SMaciej Żenczykowski	# Add settings not seen to completions
187*1b481fc3SMaciej Żenczykowski	local setting
188*1b481fc3SMaciej Żenczykowski	for setting in "${!settings[@]}"; do
189*1b481fc3SMaciej Żenczykowski		if [ "${settings[$setting]}" = notseen ]; then
190*1b481fc3SMaciej Żenczykowski			comp_words+=( "$setting" )
191*1b481fc3SMaciej Żenczykowski		fi
192*1b481fc3SMaciej Żenczykowski	done
193*1b481fc3SMaciej Żenczykowski
194*1b481fc3SMaciej Żenczykowski	# Add settings not seen to completions
195*1b481fc3SMaciej Żenczykowski	if [ "$in_msglvl" ]; then
196*1b481fc3SMaciej Żenczykowski		local msgtype
197*1b481fc3SMaciej Żenczykowski		for msgtype in "${!msgtypes[@]}"; do
198*1b481fc3SMaciej Żenczykowski			if [ "${msgtypes[$msgtype]}" = notseen ]; then
199*1b481fc3SMaciej Żenczykowski				comp_words+=( "$msgtype" )
200*1b481fc3SMaciej Żenczykowski			fi
201*1b481fc3SMaciej Żenczykowski		done
202*1b481fc3SMaciej Żenczykowski	fi
203*1b481fc3SMaciej Żenczykowski
204*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${comp_words[*]}" -- "$cur" ) )
205*1b481fc3SMaciej Żenczykowski}
206*1b481fc3SMaciej Żenczykowski
207*1b481fc3SMaciej Żenczykowski# Completion for ethtool --change-eeprom
208*1b481fc3SMaciej Żenczykowski_ethtool_change_eeprom()
209*1b481fc3SMaciej Żenczykowski{
210*1b481fc3SMaciej Żenczykowski	local -A settings=(
211*1b481fc3SMaciej Żenczykowski		[length]=1
212*1b481fc3SMaciej Żenczykowski		[magic]=1
213*1b481fc3SMaciej Żenczykowski		[offset]=1
214*1b481fc3SMaciej Żenczykowski		[value]=1
215*1b481fc3SMaciej Żenczykowski	)
216*1b481fc3SMaciej Żenczykowski
217*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
218*1b481fc3SMaciej Żenczykowski		# All settings take an unsigned integer argument
219*1b481fc3SMaciej Żenczykowski		return
220*1b481fc3SMaciej Żenczykowski	fi
221*1b481fc3SMaciej Żenczykowski
222*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
223*1b481fc3SMaciej Żenczykowski	local word
224*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
225*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
226*1b481fc3SMaciej Żenczykowski	done
227*1b481fc3SMaciej Żenczykowski
228*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
229*1b481fc3SMaciej Żenczykowski}
230*1b481fc3SMaciej Żenczykowski
231*1b481fc3SMaciej Żenczykowski# Completion for ethtool --coalesce
232*1b481fc3SMaciej Żenczykowski_ethtool_coalesce()
233*1b481fc3SMaciej Żenczykowski{
234*1b481fc3SMaciej Żenczykowski	local -A settings=(
235*1b481fc3SMaciej Żenczykowski		[adaptive-rx]=1
236*1b481fc3SMaciej Żenczykowski		[adaptive-tx]=1
237*1b481fc3SMaciej Żenczykowski		[pkt-rate-high]=1
238*1b481fc3SMaciej Żenczykowski		[pkt-rate-low]=1
239*1b481fc3SMaciej Żenczykowski		[rx-frames]=1
240*1b481fc3SMaciej Żenczykowski		[rx-frames-high]=1
241*1b481fc3SMaciej Żenczykowski		[rx-frames-irq]=1
242*1b481fc3SMaciej Żenczykowski		[rx-frames-low]=1
243*1b481fc3SMaciej Żenczykowski		[rx-usecs]=1
244*1b481fc3SMaciej Żenczykowski		[rx-usecs-high]=1
245*1b481fc3SMaciej Żenczykowski		[rx-usecs-irq]=1
246*1b481fc3SMaciej Żenczykowski		[rx-usecs-low]=1
247*1b481fc3SMaciej Żenczykowski		[sample-interval]=1
248*1b481fc3SMaciej Żenczykowski		[stats-block-usecs]=1
249*1b481fc3SMaciej Żenczykowski		[tx-frames]=1
250*1b481fc3SMaciej Żenczykowski		[tx-frames-high]=1
251*1b481fc3SMaciej Żenczykowski		[tx-frames-irq]=1
252*1b481fc3SMaciej Żenczykowski		[tx-frames-low]=1
253*1b481fc3SMaciej Żenczykowski		[tx-usecs]=1
254*1b481fc3SMaciej Żenczykowski		[tx-usecs-high]=1
255*1b481fc3SMaciej Żenczykowski		[tx-usecs-irq]=1
256*1b481fc3SMaciej Żenczykowski		[tx-usecs-low]=1
257*1b481fc3SMaciej Żenczykowski		[tx-aggr-max-bytes]=1
258*1b481fc3SMaciej Żenczykowski		[tx-aggr-max-frames]=1
259*1b481fc3SMaciej Żenczykowski		[tx-aggr-time-usecs]=1
260*1b481fc3SMaciej Żenczykowski	)
261*1b481fc3SMaciej Żenczykowski
262*1b481fc3SMaciej Żenczykowski	case "$prev" in
263*1b481fc3SMaciej Żenczykowski		adaptive-rx|\
264*1b481fc3SMaciej Żenczykowski		adaptive-tx)
265*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
266*1b481fc3SMaciej Żenczykowski			return ;;
267*1b481fc3SMaciej Żenczykowski	esac
268*1b481fc3SMaciej Żenczykowski
269*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
270*1b481fc3SMaciej Żenczykowski		# Unsigned integer
271*1b481fc3SMaciej Żenczykowski		return
272*1b481fc3SMaciej Żenczykowski	fi
273*1b481fc3SMaciej Żenczykowski
274*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
275*1b481fc3SMaciej Żenczykowski	local word
276*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
277*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
278*1b481fc3SMaciej Żenczykowski	done
279*1b481fc3SMaciej Żenczykowski
280*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
281*1b481fc3SMaciej Żenczykowski}
282*1b481fc3SMaciej Żenczykowski
283*1b481fc3SMaciej Żenczykowski# Completion for ethtool --config-nfc <devname> flow-type
284*1b481fc3SMaciej Żenczykowski_ethtool_config_nfc_flow_type()
285*1b481fc3SMaciej Żenczykowski{
286*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 4 ]; then
287*1b481fc3SMaciej Żenczykowski		_ethtool_flow_type --spec
288*1b481fc3SMaciej Żenczykowski		return
289*1b481fc3SMaciej Żenczykowski	fi
290*1b481fc3SMaciej Żenczykowski
291*1b481fc3SMaciej Żenczykowski	case "$prev" in
292*1b481fc3SMaciej Żenczykowski		context)
293*1b481fc3SMaciej Żenczykowski			_ethtool_context
294*1b481fc3SMaciej Żenczykowski			return ;;
295*1b481fc3SMaciej Żenczykowski		dst|\
296*1b481fc3SMaciej Żenczykowski		dst-mac|\
297*1b481fc3SMaciej Żenczykowski		src)
298*1b481fc3SMaciej Żenczykowski			# TODO: Complete only local for dst and remote for src
299*1b481fc3SMaciej Żenczykowski			_mac_addresses
300*1b481fc3SMaciej Żenczykowski			return ;;
301*1b481fc3SMaciej Żenczykowski		dst-ip)
302*1b481fc3SMaciej Żenczykowski			# Note: RX classification, so dst is usually local
303*1b481fc3SMaciej Żenczykowski			case "${words[4]}" in
304*1b481fc3SMaciej Żenczykowski				*4) _ip_addresses -4 return ;;
305*1b481fc3SMaciej Żenczykowski				*6) _ip_addresses -6 return ;;
306*1b481fc3SMaciej Żenczykowski			esac
307*1b481fc3SMaciej Żenczykowski			return ;;
308*1b481fc3SMaciej Żenczykowski		src-ip)
309*1b481fc3SMaciej Żenczykowski			# Note: RX classification, so src is usually remote
310*1b481fc3SMaciej Żenczykowski			# TODO: Remote IP addresses (ARP cache + /etc/hosts + ?)
311*1b481fc3SMaciej Żenczykowski			return ;;
312*1b481fc3SMaciej Żenczykowski		m|\
313*1b481fc3SMaciej Żenczykowski		*-mask)
314*1b481fc3SMaciej Żenczykowski			# MAC, IP, or integer bitmask
315*1b481fc3SMaciej Żenczykowski			return ;;
316*1b481fc3SMaciej Żenczykowski	esac
317*1b481fc3SMaciej Żenczykowski
318*1b481fc3SMaciej Żenczykowski	local -A settings=(
319*1b481fc3SMaciej Żenczykowski		[action]=1
320*1b481fc3SMaciej Żenczykowski		[context]=1
321*1b481fc3SMaciej Żenczykowski		[loc]=1
322*1b481fc3SMaciej Żenczykowski		[queue]=1
323*1b481fc3SMaciej Żenczykowski		[vf]=1
324*1b481fc3SMaciej Żenczykowski	)
325*1b481fc3SMaciej Żenczykowski
326*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
327*1b481fc3SMaciej Żenczykowski		# Integer
328*1b481fc3SMaciej Żenczykowski		return
329*1b481fc3SMaciej Żenczykowski	fi
330*1b481fc3SMaciej Żenczykowski
331*1b481fc3SMaciej Żenczykowski	case "${words[4]}" in
332*1b481fc3SMaciej Żenczykowski		ah4|\
333*1b481fc3SMaciej Żenczykowski		esp4)
334*1b481fc3SMaciej Żenczykowski			local -A fields=(
335*1b481fc3SMaciej Żenczykowski				[dst-ip]=1
336*1b481fc3SMaciej Żenczykowski				[dst-mac]=1
337*1b481fc3SMaciej Żenczykowski				[spi]=1
338*1b481fc3SMaciej Żenczykowski				[src-ip]=1
339*1b481fc3SMaciej Żenczykowski				[tos]=1
340*1b481fc3SMaciej Żenczykowski				[user-def]=1
341*1b481fc3SMaciej Żenczykowski				[vlan-etype]=1
342*1b481fc3SMaciej Żenczykowski				[vlan]=1
343*1b481fc3SMaciej Żenczykowski			)
344*1b481fc3SMaciej Żenczykowski			;;
345*1b481fc3SMaciej Żenczykowski		ah6|\
346*1b481fc3SMaciej Żenczykowski		esp6)
347*1b481fc3SMaciej Żenczykowski			local -A fields=(
348*1b481fc3SMaciej Żenczykowski				[dst-ip]=1
349*1b481fc3SMaciej Żenczykowski				[dst-mac]=1
350*1b481fc3SMaciej Żenczykowski				[spi]=1
351*1b481fc3SMaciej Żenczykowski				[src-ip]=1
352*1b481fc3SMaciej Żenczykowski				[tclass]=1
353*1b481fc3SMaciej Żenczykowski				[user-def]=1
354*1b481fc3SMaciej Żenczykowski				[vlan-etype]=1
355*1b481fc3SMaciej Żenczykowski				[vlan]=1
356*1b481fc3SMaciej Żenczykowski			)
357*1b481fc3SMaciej Żenczykowski			;;
358*1b481fc3SMaciej Żenczykowski		ether)
359*1b481fc3SMaciej Żenczykowski			local -A fields=(
360*1b481fc3SMaciej Żenczykowski				[dst]=1
361*1b481fc3SMaciej Żenczykowski				[proto]=1
362*1b481fc3SMaciej Żenczykowski				[src]=1
363*1b481fc3SMaciej Żenczykowski				[user-def]=1
364*1b481fc3SMaciej Żenczykowski				[vlan-etype]=1
365*1b481fc3SMaciej Żenczykowski				[vlan]=1
366*1b481fc3SMaciej Żenczykowski			)
367*1b481fc3SMaciej Żenczykowski			;;
368*1b481fc3SMaciej Żenczykowski		ip4)
369*1b481fc3SMaciej Żenczykowski			local -A fields=(
370*1b481fc3SMaciej Żenczykowski				[dst-ip]=1
371*1b481fc3SMaciej Żenczykowski				[dst-mac]=1
372*1b481fc3SMaciej Żenczykowski				[dst-port]=1
373*1b481fc3SMaciej Żenczykowski				[l4data]=1
374*1b481fc3SMaciej Żenczykowski				[l4proto]=1
375*1b481fc3SMaciej Żenczykowski				[spi]=1
376*1b481fc3SMaciej Żenczykowski				[src-ip]=1
377*1b481fc3SMaciej Żenczykowski				[src-port]=1
378*1b481fc3SMaciej Żenczykowski				[tos]=1
379*1b481fc3SMaciej Żenczykowski				[user-def]=1
380*1b481fc3SMaciej Żenczykowski				[vlan-etype]=1
381*1b481fc3SMaciej Żenczykowski				[vlan]=1
382*1b481fc3SMaciej Żenczykowski			)
383*1b481fc3SMaciej Żenczykowski			;;
384*1b481fc3SMaciej Żenczykowski		ip6)
385*1b481fc3SMaciej Żenczykowski			local -A fields=(
386*1b481fc3SMaciej Żenczykowski				[dst-ip]=1
387*1b481fc3SMaciej Żenczykowski				[dst-mac]=1
388*1b481fc3SMaciej Żenczykowski				[dst-port]=1
389*1b481fc3SMaciej Żenczykowski				[l4data]=1
390*1b481fc3SMaciej Żenczykowski				[l4proto]=1
391*1b481fc3SMaciej Żenczykowski				[spi]=1
392*1b481fc3SMaciej Żenczykowski				[src-ip]=1
393*1b481fc3SMaciej Żenczykowski				[src-port]=1
394*1b481fc3SMaciej Żenczykowski				[tclass]=1
395*1b481fc3SMaciej Żenczykowski				[user-def]=1
396*1b481fc3SMaciej Żenczykowski				[vlan-etype]=1
397*1b481fc3SMaciej Żenczykowski				[vlan]=1
398*1b481fc3SMaciej Żenczykowski			)
399*1b481fc3SMaciej Żenczykowski			;;
400*1b481fc3SMaciej Żenczykowski		sctp4|\
401*1b481fc3SMaciej Żenczykowski		tcp4|\
402*1b481fc3SMaciej Żenczykowski		udp4)
403*1b481fc3SMaciej Żenczykowski			local -A fields=(
404*1b481fc3SMaciej Żenczykowski				[dst-ip]=1
405*1b481fc3SMaciej Żenczykowski				[dst-mac]=1
406*1b481fc3SMaciej Żenczykowski				[dst-port]=1
407*1b481fc3SMaciej Żenczykowski				[src-ip]=1
408*1b481fc3SMaciej Żenczykowski				[src-port]=1
409*1b481fc3SMaciej Żenczykowski				[tos]=1
410*1b481fc3SMaciej Żenczykowski				[user-def]=1
411*1b481fc3SMaciej Żenczykowski				[vlan-etype]=1
412*1b481fc3SMaciej Żenczykowski				[vlan]=1
413*1b481fc3SMaciej Żenczykowski			)
414*1b481fc3SMaciej Żenczykowski			;;
415*1b481fc3SMaciej Żenczykowski		sctp6|\
416*1b481fc3SMaciej Żenczykowski		tcp6|\
417*1b481fc3SMaciej Żenczykowski		udp6)
418*1b481fc3SMaciej Żenczykowski			local -A fields=(
419*1b481fc3SMaciej Żenczykowski				[dst-ip]=1
420*1b481fc3SMaciej Żenczykowski				[dst-mac]=1
421*1b481fc3SMaciej Żenczykowski				[dst-port]=1
422*1b481fc3SMaciej Żenczykowski				[src-ip]=1
423*1b481fc3SMaciej Żenczykowski				[src-port]=1
424*1b481fc3SMaciej Żenczykowski				[tclass]=1
425*1b481fc3SMaciej Żenczykowski				[user-def]=1
426*1b481fc3SMaciej Żenczykowski				[vlan-etype]=1
427*1b481fc3SMaciej Żenczykowski				[vlan]=1
428*1b481fc3SMaciej Żenczykowski			)
429*1b481fc3SMaciej Żenczykowski			;;
430*1b481fc3SMaciej Żenczykowski		*)
431*1b481fc3SMaciej Żenczykowski			return ;;
432*1b481fc3SMaciej Żenczykowski	esac
433*1b481fc3SMaciej Żenczykowski
434*1b481fc3SMaciej Żenczykowski	if [ "${fields[$prev]+set}" ]; then
435*1b481fc3SMaciej Żenczykowski		# Integer
436*1b481fc3SMaciej Żenczykowski		return
437*1b481fc3SMaciej Żenczykowski	fi
438*1b481fc3SMaciej Żenczykowski
439*1b481fc3SMaciej Żenczykowski	# If the previous 2 words were a field+value, suggest a mask
440*1b481fc3SMaciej Żenczykowski	local mask=
441*1b481fc3SMaciej Żenczykowski	if [ "${fields[${words[$cword-2]}]+set}" ]; then
442*1b481fc3SMaciej Żenczykowski		mask="m ${words[$cword-2]}-mask"
443*1b481fc3SMaciej Żenczykowski	fi
444*1b481fc3SMaciej Żenczykowski
445*1b481fc3SMaciej Żenczykowski	# Remove fields and settings which have been seen
446*1b481fc3SMaciej Żenczykowski	local word
447*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:5:${#words[@]}-6}"; do
448*1b481fc3SMaciej Żenczykowski		unset "fields[$word]" "settings[$word]"
449*1b481fc3SMaciej Żenczykowski	done
450*1b481fc3SMaciej Żenczykowski
451*1b481fc3SMaciej Żenczykowski	# Remove mutually-exclusive options
452*1b481fc3SMaciej Żenczykowski	if ! [ "${settings[action]+set}" ]; then
453*1b481fc3SMaciej Żenczykowski		unset 'settings[queue]' 'settings[vf]'
454*1b481fc3SMaciej Żenczykowski	fi
455*1b481fc3SMaciej Żenczykowski	if ! [ "${settings[queue]+set}" ]; then
456*1b481fc3SMaciej Żenczykowski		unset 'settings[action]'
457*1b481fc3SMaciej Żenczykowski	fi
458*1b481fc3SMaciej Żenczykowski	if ! [ "${settings[vf]+set}" ]; then
459*1b481fc3SMaciej Żenczykowski		unset 'settings[action]'
460*1b481fc3SMaciej Żenczykowski	fi
461*1b481fc3SMaciej Żenczykowski
462*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "$mask ${!fields[*]} ${!settings[*]}" -- "$cur" ) )
463*1b481fc3SMaciej Żenczykowski}
464*1b481fc3SMaciej Żenczykowski
465*1b481fc3SMaciej Żenczykowski# Completion for ethtool --config-nfc
466*1b481fc3SMaciej Żenczykowski_ethtool_config_nfc()
467*1b481fc3SMaciej Żenczykowski{
468*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
469*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'delete flow-type rx-flow-hash' -- "$cur" ) )
470*1b481fc3SMaciej Żenczykowski		return
471*1b481fc3SMaciej Żenczykowski	fi
472*1b481fc3SMaciej Żenczykowski
473*1b481fc3SMaciej Żenczykowski	case "${words[3]}" in
474*1b481fc3SMaciej Żenczykowski		delete)
475*1b481fc3SMaciej Żenczykowski			# Unsigned integer
476*1b481fc3SMaciej Żenczykowski			return ;;
477*1b481fc3SMaciej Żenczykowski		flow-type)
478*1b481fc3SMaciej Żenczykowski			_ethtool_config_nfc_flow_type
479*1b481fc3SMaciej Żenczykowski			return ;;
480*1b481fc3SMaciej Żenczykowski		rx-flow-hash)
481*1b481fc3SMaciej Żenczykowski			case "$cword" in
482*1b481fc3SMaciej Żenczykowski				4)
483*1b481fc3SMaciej Żenczykowski					_ethtool_flow_type --hash
484*1b481fc3SMaciej Żenczykowski					return ;;
485*1b481fc3SMaciej Żenczykowski				5)
486*1b481fc3SMaciej Żenczykowski					_ethtool_compgen_letterset m v t s d f n r
487*1b481fc3SMaciej Żenczykowski					return ;;
488*1b481fc3SMaciej Żenczykowski				6)
489*1b481fc3SMaciej Żenczykowski					COMPREPLY=( $( compgen -W context -- "$cur" ) )
490*1b481fc3SMaciej Żenczykowski					return ;;
491*1b481fc3SMaciej Żenczykowski				7)
492*1b481fc3SMaciej Żenczykowski					_ethtool_context
493*1b481fc3SMaciej Żenczykowski					return ;;
494*1b481fc3SMaciej Żenczykowski			esac
495*1b481fc3SMaciej Żenczykowski			return ;;
496*1b481fc3SMaciej Żenczykowski	esac
497*1b481fc3SMaciej Żenczykowski}
498*1b481fc3SMaciej Żenczykowski
499*1b481fc3SMaciej Żenczykowski# Completion for ethtool --eeprom-dump
500*1b481fc3SMaciej Żenczykowski_ethtool_eeprom_dump()
501*1b481fc3SMaciej Żenczykowski{
502*1b481fc3SMaciej Żenczykowski	local -A settings=(
503*1b481fc3SMaciej Żenczykowski		[length]=1
504*1b481fc3SMaciej Żenczykowski		[offset]=1
505*1b481fc3SMaciej Żenczykowski		[raw]=1
506*1b481fc3SMaciej Żenczykowski	)
507*1b481fc3SMaciej Żenczykowski
508*1b481fc3SMaciej Żenczykowski	if [ "$prev" = raw ]; then
509*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
510*1b481fc3SMaciej Żenczykowski		return
511*1b481fc3SMaciej Żenczykowski	fi
512*1b481fc3SMaciej Żenczykowski
513*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
514*1b481fc3SMaciej Żenczykowski		# Unsigned integer argument
515*1b481fc3SMaciej Żenczykowski		return
516*1b481fc3SMaciej Żenczykowski	fi
517*1b481fc3SMaciej Żenczykowski
518*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
519*1b481fc3SMaciej Żenczykowski	local word
520*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
521*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
522*1b481fc3SMaciej Żenczykowski	done
523*1b481fc3SMaciej Żenczykowski
524*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
525*1b481fc3SMaciej Żenczykowski}
526*1b481fc3SMaciej Żenczykowski
527*1b481fc3SMaciej Żenczykowski# Completion for ethtool --features
528*1b481fc3SMaciej Żenczykowski_ethtool_features()
529*1b481fc3SMaciej Żenczykowski{
530*1b481fc3SMaciej Żenczykowski	local -A abbreviations=(
531*1b481fc3SMaciej Żenczykowski		[generic-receive-offload]=gro
532*1b481fc3SMaciej Żenczykowski		[generic-segmentation-offload]=gso
533*1b481fc3SMaciej Żenczykowski		[large-receive-offload]=lro
534*1b481fc3SMaciej Żenczykowski		[ntuple-filters]=ntuple
535*1b481fc3SMaciej Żenczykowski		[receive-hashing]=rxhash
536*1b481fc3SMaciej Żenczykowski		[rx-checksumming]=rx
537*1b481fc3SMaciej Żenczykowski		[rx-vlan-offload]=rxvlan
538*1b481fc3SMaciej Żenczykowski		[scatter-gather]=sg
539*1b481fc3SMaciej Żenczykowski		[tcp-segmentation-offload]=tso
540*1b481fc3SMaciej Żenczykowski		[tx-checksumming]=tx
541*1b481fc3SMaciej Żenczykowski		[tx-vlan-offload]=txvlan
542*1b481fc3SMaciej Żenczykowski		[udp-fragmentation-offload]=ufo
543*1b481fc3SMaciej Żenczykowski	)
544*1b481fc3SMaciej Żenczykowski
545*1b481fc3SMaciej Żenczykowski	local -A features=()
546*1b481fc3SMaciej Żenczykowski	local feature status fixed
547*1b481fc3SMaciej Żenczykowski	# shellcheck disable=SC2034
548*1b481fc3SMaciej Żenczykowski	while read -r feature status fixed; do
549*1b481fc3SMaciej Żenczykowski		if [ -z "$feature" ]; then
550*1b481fc3SMaciej Żenczykowski			# Ignore blank line from empty expansion in here-document
551*1b481fc3SMaciej Żenczykowski			continue
552*1b481fc3SMaciej Żenczykowski		fi
553*1b481fc3SMaciej Żenczykowski
554*1b481fc3SMaciej Żenczykowski		if [ "$feature" = Features ]; then
555*1b481fc3SMaciej Żenczykowski			# Ignore heading
556*1b481fc3SMaciej Żenczykowski			continue
557*1b481fc3SMaciej Żenczykowski		fi
558*1b481fc3SMaciej Żenczykowski
559*1b481fc3SMaciej Żenczykowski		if [ "$fixed" = '[fixed]' ]; then
560*1b481fc3SMaciej Żenczykowski			# Fixed features can't be changed
561*1b481fc3SMaciej Żenczykowski			continue
562*1b481fc3SMaciej Żenczykowski		fi
563*1b481fc3SMaciej Żenczykowski
564*1b481fc3SMaciej Żenczykowski		feature=${feature%:}
565*1b481fc3SMaciej Żenczykowski		if [ "${abbreviations[$feature]+set}" ]; then
566*1b481fc3SMaciej Żenczykowski			features[${abbreviations[$feature]}]=1
567*1b481fc3SMaciej Żenczykowski		else
568*1b481fc3SMaciej Żenczykowski			features[$feature]=1
569*1b481fc3SMaciej Żenczykowski		fi
570*1b481fc3SMaciej Żenczykowski	done <<ETHTOOL_FEATURES
571*1b481fc3SMaciej Żenczykowski$(PATH="$PATH:/sbin:/usr/sbin:/usr/local/sbin" \
572*1b481fc3SMaciej Żenczykowski	ethtool --show-features "${words[2]}" 2>/dev/null)
573*1b481fc3SMaciej ŻenczykowskiETHTOOL_FEATURES
574*1b481fc3SMaciej Żenczykowski
575*1b481fc3SMaciej Żenczykowski	if [ "${features[$prev]+set}" ]; then
576*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
577*1b481fc3SMaciej Żenczykowski		return
578*1b481fc3SMaciej Żenczykowski	fi
579*1b481fc3SMaciej Żenczykowski
580*1b481fc3SMaciej Żenczykowski	# Remove features which have been seen
581*1b481fc3SMaciej Żenczykowski	local word
582*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
583*1b481fc3SMaciej Żenczykowski		unset "features[$word]"
584*1b481fc3SMaciej Żenczykowski	done
585*1b481fc3SMaciej Żenczykowski
586*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!features[*]}" -- "$cur" ) )
587*1b481fc3SMaciej Żenczykowski}
588*1b481fc3SMaciej Żenczykowski
589*1b481fc3SMaciej Żenczykowski# Complete the current word as a kernel firmware file (for request_firmware)
590*1b481fc3SMaciej Żenczykowski# See https://www.kernel.org/doc/html/latest/driver-api/firmware/core.html
591*1b481fc3SMaciej Żenczykowski_ethtool_firmware()
592*1b481fc3SMaciej Żenczykowski{
593*1b481fc3SMaciej Żenczykowski	local -a firmware_paths=(
594*1b481fc3SMaciej Żenczykowski		/lib/firmware/updates/
595*1b481fc3SMaciej Żenczykowski		/lib/firmware/
596*1b481fc3SMaciej Żenczykowski	)
597*1b481fc3SMaciej Żenczykowski
598*1b481fc3SMaciej Żenczykowski	local release
599*1b481fc3SMaciej Żenczykowski	if release=$( uname -r 2>/dev/null ); then
600*1b481fc3SMaciej Żenczykowski		firmware_paths+=(
601*1b481fc3SMaciej Żenczykowski			"/lib/firmware/updates/$release/"
602*1b481fc3SMaciej Żenczykowski			"/lib/firmware/$release/"
603*1b481fc3SMaciej Żenczykowski		)
604*1b481fc3SMaciej Żenczykowski	fi
605*1b481fc3SMaciej Żenczykowski
606*1b481fc3SMaciej Żenczykowski	local fw_path_para
607*1b481fc3SMaciej Żenczykowski	if fw_path_para=$( cat /sys/module/firmware_class/parameters/path 2>/dev/null ) \
608*1b481fc3SMaciej Żenczykowski			&& [ -n "$fw_path_para" ]; then
609*1b481fc3SMaciej Żenczykowski		firmware_paths+=( "$fw_path_para" )
610*1b481fc3SMaciej Żenczykowski	fi
611*1b481fc3SMaciej Żenczykowski
612*1b481fc3SMaciej Żenczykowski	local -A firmware_files=()
613*1b481fc3SMaciej Żenczykowski
614*1b481fc3SMaciej Żenczykowski	local firmware_path
615*1b481fc3SMaciej Żenczykowski	for firmware_path in "${firmware_paths[@]}"; do
616*1b481fc3SMaciej Żenczykowski		local firmware_file
617*1b481fc3SMaciej Żenczykowski		for firmware_file in "$firmware_path"*; do
618*1b481fc3SMaciej Żenczykowski			if [ -f "$firmware_file" ]; then
619*1b481fc3SMaciej Żenczykowski				firmware_files[${firmware_file##*/}]=1
620*1b481fc3SMaciej Żenczykowski			fi
621*1b481fc3SMaciej Żenczykowski		done
622*1b481fc3SMaciej Żenczykowski	done
623*1b481fc3SMaciej Żenczykowski
624*1b481fc3SMaciej Żenczykowski	local IFS='
625*1b481fc3SMaciej Żenczykowski'
626*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!firmware_files[*]}" -- "$cur" ) )
627*1b481fc3SMaciej Żenczykowski}
628*1b481fc3SMaciej Żenczykowski
629*1b481fc3SMaciej Żenczykowski# Completion for ethtool --flash
630*1b481fc3SMaciej Żenczykowski_ethtool_flash()
631*1b481fc3SMaciej Żenczykowski{
632*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
633*1b481fc3SMaciej Żenczykowski		_ethtool_firmware
634*1b481fc3SMaciej Żenczykowski		return
635*1b481fc3SMaciej Żenczykowski	fi
636*1b481fc3SMaciej Żenczykowski}
637*1b481fc3SMaciej Żenczykowski
638*1b481fc3SMaciej Żenczykowski# Completion for ethtool --get-dump
639*1b481fc3SMaciej Żenczykowski_ethtool_get_dump()
640*1b481fc3SMaciej Żenczykowski{
641*1b481fc3SMaciej Żenczykowski	case "$cword" in
642*1b481fc3SMaciej Żenczykowski		3)
643*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W data -- "$cur" ) )
644*1b481fc3SMaciej Żenczykowski			return ;;
645*1b481fc3SMaciej Żenczykowski		4)
646*1b481fc3SMaciej Żenczykowski			# Output filename
647*1b481fc3SMaciej Żenczykowski			local IFS='
648*1b481fc3SMaciej Żenczykowski'
649*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -f -- "$cur" ) )
650*1b481fc3SMaciej Żenczykowski			return ;;
651*1b481fc3SMaciej Żenczykowski	esac
652*1b481fc3SMaciej Żenczykowski}
653*1b481fc3SMaciej Żenczykowski
654*1b481fc3SMaciej Żenczykowski# Completion for ethtool --get-phy-tunable
655*1b481fc3SMaciej Żenczykowski_ethtool_get_phy_tunable()
656*1b481fc3SMaciej Żenczykowski{
657*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
658*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W downshift -- "$cur" ) )
659*1b481fc3SMaciej Żenczykowski		return
660*1b481fc3SMaciej Żenczykowski	fi
661*1b481fc3SMaciej Żenczykowski}
662*1b481fc3SMaciej Żenczykowski
663*1b481fc3SMaciej Żenczykowski# Completion for ethtool --module-info
664*1b481fc3SMaciej Żenczykowski_ethtool_module_info()
665*1b481fc3SMaciej Żenczykowski{
666*1b481fc3SMaciej Żenczykowski	local -A settings=(
667*1b481fc3SMaciej Żenczykowski		[hex]=1
668*1b481fc3SMaciej Żenczykowski		[length]=1
669*1b481fc3SMaciej Żenczykowski		[offset]=1
670*1b481fc3SMaciej Żenczykowski		[raw]=1
671*1b481fc3SMaciej Żenczykowski	)
672*1b481fc3SMaciej Żenczykowski
673*1b481fc3SMaciej Żenczykowski	case "$prev" in
674*1b481fc3SMaciej Żenczykowski		hex|\
675*1b481fc3SMaciej Żenczykowski		raw)
676*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
677*1b481fc3SMaciej Żenczykowski			return ;;
678*1b481fc3SMaciej Żenczykowski	esac
679*1b481fc3SMaciej Żenczykowski
680*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
681*1b481fc3SMaciej Żenczykowski		# Unsigned integer argument
682*1b481fc3SMaciej Żenczykowski		return
683*1b481fc3SMaciej Żenczykowski	fi
684*1b481fc3SMaciej Żenczykowski
685*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
686*1b481fc3SMaciej Żenczykowski	local word
687*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
688*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
689*1b481fc3SMaciej Żenczykowski	done
690*1b481fc3SMaciej Żenczykowski
691*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
692*1b481fc3SMaciej Żenczykowski}
693*1b481fc3SMaciej Żenczykowski
694*1b481fc3SMaciej Żenczykowski# Completion for ethtool --pause
695*1b481fc3SMaciej Żenczykowski_ethtool_pause()
696*1b481fc3SMaciej Żenczykowski{
697*1b481fc3SMaciej Żenczykowski	local -A settings=(
698*1b481fc3SMaciej Żenczykowski		[autoneg]=1
699*1b481fc3SMaciej Żenczykowski		[rx]=1
700*1b481fc3SMaciej Żenczykowski		[tx]=1
701*1b481fc3SMaciej Żenczykowski	)
702*1b481fc3SMaciej Żenczykowski
703*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
704*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
705*1b481fc3SMaciej Żenczykowski		return
706*1b481fc3SMaciej Żenczykowski	fi
707*1b481fc3SMaciej Żenczykowski
708*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
709*1b481fc3SMaciej Żenczykowski	local word
710*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
711*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
712*1b481fc3SMaciej Żenczykowski	done
713*1b481fc3SMaciej Żenczykowski
714*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
715*1b481fc3SMaciej Żenczykowski}
716*1b481fc3SMaciej Żenczykowski
717*1b481fc3SMaciej Żenczykowski# Completion for ethtool --per-queue
718*1b481fc3SMaciej Żenczykowski_ethtool_per_queue()
719*1b481fc3SMaciej Żenczykowski{
720*1b481fc3SMaciej Żenczykowski	local -a subcommands=(
721*1b481fc3SMaciej Żenczykowski		--coalesce
722*1b481fc3SMaciej Żenczykowski		--show-coalesce
723*1b481fc3SMaciej Żenczykowski	)
724*1b481fc3SMaciej Żenczykowski
725*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
726*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W "queue_mask ${subcommands[*]}" -- "$cur" ) )
727*1b481fc3SMaciej Żenczykowski		return
728*1b481fc3SMaciej Żenczykowski	fi
729*1b481fc3SMaciej Żenczykowski
730*1b481fc3SMaciej Żenczykowski	local sc_start=3
731*1b481fc3SMaciej Żenczykowski	if [ "${words[3]}" = queue_mask ] ; then
732*1b481fc3SMaciej Żenczykowski		case "$cword" in
733*1b481fc3SMaciej Żenczykowski			4)
734*1b481fc3SMaciej Żenczykowski				# Hex number
735*1b481fc3SMaciej Żenczykowski				return ;;
736*1b481fc3SMaciej Żenczykowski			5)
737*1b481fc3SMaciej Żenczykowski				COMPREPLY=( $( compgen -W "${subcommands[*]}" -- "$cur" ) )
738*1b481fc3SMaciej Żenczykowski				return ;;
739*1b481fc3SMaciej Żenczykowski		esac
740*1b481fc3SMaciej Żenczykowski
741*1b481fc3SMaciej Żenczykowski		sc_start=5
742*1b481fc3SMaciej Żenczykowski	fi
743*1b481fc3SMaciej Żenczykowski
744*1b481fc3SMaciej Żenczykowski	case "${words[$sc_start]}" in
745*1b481fc3SMaciej Żenczykowski		--coalesce)
746*1b481fc3SMaciej Żenczykowski			# Remove --per-queue args to match normal --coalesce invocation
747*1b481fc3SMaciej Żenczykowski			local words=(
748*1b481fc3SMaciej Żenczykowski				"${words[0]}"
749*1b481fc3SMaciej Żenczykowski				--coalesce
750*1b481fc3SMaciej Żenczykowski				"${words[2]}"
751*1b481fc3SMaciej Żenczykowski				"${words[@]:$sc_start+1:${#words[@]}-$sc_start-1}"
752*1b481fc3SMaciej Żenczykowski			)
753*1b481fc3SMaciej Żenczykowski			_ethtool_coalesce
754*1b481fc3SMaciej Żenczykowski			return ;;
755*1b481fc3SMaciej Żenczykowski		--show-coalesce)
756*1b481fc3SMaciej Żenczykowski			# No args
757*1b481fc3SMaciej Żenczykowski			return ;;
758*1b481fc3SMaciej Żenczykowski	esac
759*1b481fc3SMaciej Żenczykowski}
760*1b481fc3SMaciej Żenczykowski
761*1b481fc3SMaciej Żenczykowski# Completion for ethtool --register-dump
762*1b481fc3SMaciej Żenczykowski_ethtool_register_dump()
763*1b481fc3SMaciej Żenczykowski{
764*1b481fc3SMaciej Żenczykowski	local -A settings=(
765*1b481fc3SMaciej Żenczykowski		[file]=1
766*1b481fc3SMaciej Żenczykowski		[hex]=1
767*1b481fc3SMaciej Żenczykowski		[raw]=1
768*1b481fc3SMaciej Żenczykowski	)
769*1b481fc3SMaciej Żenczykowski
770*1b481fc3SMaciej Żenczykowski	case "$prev" in
771*1b481fc3SMaciej Żenczykowski		hex|\
772*1b481fc3SMaciej Żenczykowski		raw)
773*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
774*1b481fc3SMaciej Żenczykowski			return ;;
775*1b481fc3SMaciej Żenczykowski		file)
776*1b481fc3SMaciej Żenczykowski			local IFS='
777*1b481fc3SMaciej Żenczykowski'
778*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -f -- "$cur" ) )
779*1b481fc3SMaciej Żenczykowski			return ;;
780*1b481fc3SMaciej Żenczykowski	esac
781*1b481fc3SMaciej Żenczykowski
782*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
783*1b481fc3SMaciej Żenczykowski	local word
784*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
785*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
786*1b481fc3SMaciej Żenczykowski	done
787*1b481fc3SMaciej Żenczykowski
788*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
789*1b481fc3SMaciej Żenczykowski}
790*1b481fc3SMaciej Żenczykowski
791*1b481fc3SMaciej Żenczykowski# Completion for ethtool --reset
792*1b481fc3SMaciej Żenczykowski_ethtool_reset()
793*1b481fc3SMaciej Żenczykowski{
794*1b481fc3SMaciej Żenczykowski	if [ "$prev" = flags ]; then
795*1b481fc3SMaciej Żenczykowski		# Unsigned integer
796*1b481fc3SMaciej Żenczykowski		return
797*1b481fc3SMaciej Żenczykowski	fi
798*1b481fc3SMaciej Żenczykowski
799*1b481fc3SMaciej Żenczykowski	local -A flag_names=(
800*1b481fc3SMaciej Żenczykowski		[ap]=1
801*1b481fc3SMaciej Żenczykowski		[dma]=1
802*1b481fc3SMaciej Żenczykowski		[filter]=1
803*1b481fc3SMaciej Żenczykowski		[irq]=1
804*1b481fc3SMaciej Żenczykowski		[mac]=1
805*1b481fc3SMaciej Żenczykowski		[mgmt]=1
806*1b481fc3SMaciej Żenczykowski		[offload]=1
807*1b481fc3SMaciej Żenczykowski		[phy]=1
808*1b481fc3SMaciej Żenczykowski		[ram]=1
809*1b481fc3SMaciej Żenczykowski	)
810*1b481fc3SMaciej Żenczykowski
811*1b481fc3SMaciej Żenczykowski	local -A all_flag_names=()
812*1b481fc3SMaciej Żenczykowski	local flag_name
813*1b481fc3SMaciej Żenczykowski	for flag_name in "${!flag_names[@]}"; do
814*1b481fc3SMaciej Żenczykowski		all_flag_names[$flag_name]=1
815*1b481fc3SMaciej Żenczykowski		all_flag_names[$flag_name-shared]=1
816*1b481fc3SMaciej Żenczykowski	done
817*1b481fc3SMaciej Żenczykowski
818*1b481fc3SMaciej Żenczykowski	# Remove all_flag_names which have been seen
819*1b481fc3SMaciej Żenczykowski	local any_dedicated=
820*1b481fc3SMaciej Żenczykowski	local word
821*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
822*1b481fc3SMaciej Żenczykowski		case "$word" in
823*1b481fc3SMaciej Żenczykowski			all)
824*1b481fc3SMaciej Żenczykowski				# Flags are always additive.
825*1b481fc3SMaciej Żenczykowski				# Nothing to add after "all".
826*1b481fc3SMaciej Żenczykowski				return ;;
827*1b481fc3SMaciej Żenczykowski			dedicated)
828*1b481fc3SMaciej Żenczykowski				any_dedicated=1
829*1b481fc3SMaciej Żenczykowski				# "dedicated" sets all non-shared flags
830*1b481fc3SMaciej Żenczykowski				for flag_name in "${!flag_names[@]}"; do
831*1b481fc3SMaciej Żenczykowski					unset "all_flag_names[$flag_name]"
832*1b481fc3SMaciej Żenczykowski				done
833*1b481fc3SMaciej Żenczykowski				continue ;;
834*1b481fc3SMaciej Żenczykowski		esac
835*1b481fc3SMaciej Żenczykowski
836*1b481fc3SMaciej Żenczykowski		if [ "${flag_names[$word]+set}" ]; then
837*1b481fc3SMaciej Żenczykowski			any_dedicated=1
838*1b481fc3SMaciej Żenczykowski		fi
839*1b481fc3SMaciej Żenczykowski
840*1b481fc3SMaciej Żenczykowski		unset "all_flag_names[$word]"
841*1b481fc3SMaciej Żenczykowski	done
842*1b481fc3SMaciej Żenczykowski
843*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!all_flag_names[*]}" -- "$cur" ) )
844*1b481fc3SMaciej Żenczykowski
845*1b481fc3SMaciej Żenczykowski	# Although it is permitted to mix named and un-named flags or duplicate
846*1b481fc3SMaciej Żenczykowski	# flags with "all" or "dedicated", it's not likely intentional.
847*1b481fc3SMaciej Żenczykowski	# Reconsider if a real use-case (or good consistency argument) is found.
848*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
849*1b481fc3SMaciej Żenczykowski		COMPREPLY+=( all dedicated flags )
850*1b481fc3SMaciej Żenczykowski	elif [ -z "$any_dedicated" ]; then
851*1b481fc3SMaciej Żenczykowski		COMPREPLY+=( dedicated )
852*1b481fc3SMaciej Żenczykowski	fi
853*1b481fc3SMaciej Żenczykowski}
854*1b481fc3SMaciej Żenczykowski
855*1b481fc3SMaciej Żenczykowski# Completion for ethtool --rxfh
856*1b481fc3SMaciej Żenczykowski_ethtool_rxfh()
857*1b481fc3SMaciej Żenczykowski{
858*1b481fc3SMaciej Żenczykowski	local -A settings=(
859*1b481fc3SMaciej Żenczykowski		[context]=1
860*1b481fc3SMaciej Żenczykowski		[default]=1
861*1b481fc3SMaciej Żenczykowski		[delete]=1
862*1b481fc3SMaciej Żenczykowski		[equal]=1
863*1b481fc3SMaciej Żenczykowski		[hfunc]=1
864*1b481fc3SMaciej Żenczykowski		[hkey]=1
865*1b481fc3SMaciej Żenczykowski		[weight]=1
866*1b481fc3SMaciej Żenczykowski	)
867*1b481fc3SMaciej Żenczykowski
868*1b481fc3SMaciej Żenczykowski	case "$prev" in
869*1b481fc3SMaciej Żenczykowski		context)
870*1b481fc3SMaciej Żenczykowski			_ethtool_context
871*1b481fc3SMaciej Żenczykowski			# "new" to create a new context
872*1b481fc3SMaciej Żenczykowski			COMPREPLY+=( new )
873*1b481fc3SMaciej Żenczykowski			return ;;
874*1b481fc3SMaciej Żenczykowski		equal)
875*1b481fc3SMaciej Żenczykowski			# Positive integer
876*1b481fc3SMaciej Żenczykowski			return ;;
877*1b481fc3SMaciej Żenczykowski		hfunc)
878*1b481fc3SMaciej Żenczykowski			# Complete available RSS hash functions
879*1b481fc3SMaciej Żenczykowski			COMPREPLY=(
880*1b481fc3SMaciej Żenczykowski				$(_ethtool_get_names_in_section 'RSS hash function' \
881*1b481fc3SMaciej Żenczykowski					--show-rxfh "${words[2]}")
882*1b481fc3SMaciej Żenczykowski			)
883*1b481fc3SMaciej Żenczykowski			return ;;
884*1b481fc3SMaciej Żenczykowski		hkey)
885*1b481fc3SMaciej Żenczykowski			# Pairs of hex digits separated by :
886*1b481fc3SMaciej Żenczykowski			return ;;
887*1b481fc3SMaciej Żenczykowski		weight)
888*1b481fc3SMaciej Żenczykowski			# Non-negative integer
889*1b481fc3SMaciej Żenczykowski			return ;;
890*1b481fc3SMaciej Żenczykowski	esac
891*1b481fc3SMaciej Żenczykowski
892*1b481fc3SMaciej Żenczykowski	local word
893*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
894*1b481fc3SMaciej Żenczykowski		# Remove settings which have been seen
895*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
896*1b481fc3SMaciej Żenczykowski
897*1b481fc3SMaciej Żenczykowski		# Remove settings which are mutually-exclusive with seen settings
898*1b481fc3SMaciej Żenczykowski		case "$word" in
899*1b481fc3SMaciej Żenczykowski			context)
900*1b481fc3SMaciej Żenczykowski				unset 'settings[default]'
901*1b481fc3SMaciej Żenczykowski				;;
902*1b481fc3SMaciej Żenczykowski			default)
903*1b481fc3SMaciej Żenczykowski				unset \
904*1b481fc3SMaciej Żenczykowski					'settings[context]' \
905*1b481fc3SMaciej Żenczykowski					'settings[delete]' \
906*1b481fc3SMaciej Żenczykowski					'settings[equal]' \
907*1b481fc3SMaciej Żenczykowski					'settings[weight]'
908*1b481fc3SMaciej Żenczykowski				;;
909*1b481fc3SMaciej Żenczykowski			delete)
910*1b481fc3SMaciej Żenczykowski				unset \
911*1b481fc3SMaciej Żenczykowski					'settings[default]' \
912*1b481fc3SMaciej Żenczykowski					'settings[equal]' \
913*1b481fc3SMaciej Żenczykowski					'settings[hkey]' \
914*1b481fc3SMaciej Żenczykowski					'settings[weight]'
915*1b481fc3SMaciej Żenczykowski				;;
916*1b481fc3SMaciej Żenczykowski			equal)
917*1b481fc3SMaciej Żenczykowski				unset \
918*1b481fc3SMaciej Żenczykowski					'settings[default]' \
919*1b481fc3SMaciej Żenczykowski					'settings[delete]' \
920*1b481fc3SMaciej Żenczykowski					'settings[weight]'
921*1b481fc3SMaciej Żenczykowski				;;
922*1b481fc3SMaciej Żenczykowski			hkey)
923*1b481fc3SMaciej Żenczykowski				unset 'settings[delete]'
924*1b481fc3SMaciej Żenczykowski				;;
925*1b481fc3SMaciej Żenczykowski			weight)
926*1b481fc3SMaciej Żenczykowski				unset \
927*1b481fc3SMaciej Żenczykowski					'settings[default]' \
928*1b481fc3SMaciej Żenczykowski					'settings[delete]' \
929*1b481fc3SMaciej Żenczykowski					'settings[equal]'
930*1b481fc3SMaciej Żenczykowski				;;
931*1b481fc3SMaciej Żenczykowski		esac
932*1b481fc3SMaciej Żenczykowski	done
933*1b481fc3SMaciej Żenczykowski
934*1b481fc3SMaciej Żenczykowski
935*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
936*1b481fc3SMaciej Żenczykowski}
937*1b481fc3SMaciej Żenczykowski
938*1b481fc3SMaciej Żenczykowski# Completion for ethtool --set-channels
939*1b481fc3SMaciej Żenczykowski_ethtool_set_channels()
940*1b481fc3SMaciej Żenczykowski{
941*1b481fc3SMaciej Żenczykowski	local -A settings=(
942*1b481fc3SMaciej Żenczykowski		[combined]=1
943*1b481fc3SMaciej Żenczykowski		[other]=1
944*1b481fc3SMaciej Żenczykowski		[rx]=1
945*1b481fc3SMaciej Żenczykowski		[tx]=1
946*1b481fc3SMaciej Żenczykowski	)
947*1b481fc3SMaciej Żenczykowski
948*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
949*1b481fc3SMaciej Żenczykowski		# Unsigned integer argument
950*1b481fc3SMaciej Żenczykowski		return
951*1b481fc3SMaciej Żenczykowski	fi
952*1b481fc3SMaciej Żenczykowski
953*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
954*1b481fc3SMaciej Żenczykowski	local word
955*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
956*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
957*1b481fc3SMaciej Żenczykowski	done
958*1b481fc3SMaciej Żenczykowski
959*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
960*1b481fc3SMaciej Żenczykowski}
961*1b481fc3SMaciej Żenczykowski
962*1b481fc3SMaciej Żenczykowski# Completion for ethtool --set-eee
963*1b481fc3SMaciej Żenczykowski_ethtool_set_eee()
964*1b481fc3SMaciej Żenczykowski{
965*1b481fc3SMaciej Żenczykowski	local -A settings=(
966*1b481fc3SMaciej Żenczykowski		[advertise]=1
967*1b481fc3SMaciej Żenczykowski		[eee]=1
968*1b481fc3SMaciej Żenczykowski		[tx-lpi]=1
969*1b481fc3SMaciej Żenczykowski		[tx-timer]=1
970*1b481fc3SMaciej Żenczykowski	)
971*1b481fc3SMaciej Żenczykowski
972*1b481fc3SMaciej Żenczykowski	case "$prev" in
973*1b481fc3SMaciej Żenczykowski		advertise|\
974*1b481fc3SMaciej Żenczykowski		tx-timer)
975*1b481fc3SMaciej Żenczykowski			# Unsigned integer
976*1b481fc3SMaciej Żenczykowski			return ;;
977*1b481fc3SMaciej Żenczykowski		eee|\
978*1b481fc3SMaciej Żenczykowski		tx-lpi)
979*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
980*1b481fc3SMaciej Żenczykowski			return ;;
981*1b481fc3SMaciej Żenczykowski	esac
982*1b481fc3SMaciej Żenczykowski
983*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
984*1b481fc3SMaciej Żenczykowski	local word
985*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
986*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
987*1b481fc3SMaciej Żenczykowski	done
988*1b481fc3SMaciej Żenczykowski
989*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
990*1b481fc3SMaciej Żenczykowski}
991*1b481fc3SMaciej Żenczykowski
992*1b481fc3SMaciej Żenczykowski# Completion for ethtool --set-fec
993*1b481fc3SMaciej Żenczykowski_ethtool_set_fec()
994*1b481fc3SMaciej Żenczykowski{
995*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
996*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W encoding -- "$cur" ) )
997*1b481fc3SMaciej Żenczykowski		return
998*1b481fc3SMaciej Żenczykowski	fi
999*1b481fc3SMaciej Żenczykowski
1000*1b481fc3SMaciej Żenczykowski	local -A modes=(
1001*1b481fc3SMaciej Żenczykowski		[auto]=auto
1002*1b481fc3SMaciej Żenczykowski		[rs]=RS
1003*1b481fc3SMaciej Żenczykowski		[off]=off
1004*1b481fc3SMaciej Żenczykowski		[baser]=BaseR
1005*1b481fc3SMaciej Żenczykowski	)
1006*1b481fc3SMaciej Żenczykowski
1007*1b481fc3SMaciej Żenczykowski	# Remove modes which have been seen
1008*1b481fc3SMaciej Żenczykowski	local word
1009*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
1010*1b481fc3SMaciej Żenczykowski		# ethtool recognizes modes case-insensitively
1011*1b481fc3SMaciej Żenczykowski		unset "modes[${word,,}]"
1012*1b481fc3SMaciej Żenczykowski	done
1013*1b481fc3SMaciej Żenczykowski
1014*1b481fc3SMaciej Żenczykowski	_ethtool_compgen_nocase "${modes[@]}"
1015*1b481fc3SMaciej Żenczykowski}
1016*1b481fc3SMaciej Żenczykowski
1017*1b481fc3SMaciej Żenczykowski# Completion for ethtool --set-phy-tunable
1018*1b481fc3SMaciej Żenczykowski_ethtool_set_phy_tunable()
1019*1b481fc3SMaciej Żenczykowski{
1020*1b481fc3SMaciej Żenczykowski	case "$cword" in
1021*1b481fc3SMaciej Żenczykowski		3)
1022*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W downshift -- "$cur" ) )
1023*1b481fc3SMaciej Żenczykowski			return ;;
1024*1b481fc3SMaciej Żenczykowski		4)
1025*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
1026*1b481fc3SMaciej Żenczykowski			return ;;
1027*1b481fc3SMaciej Żenczykowski		5)
1028*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W count -- "$cur" ) )
1029*1b481fc3SMaciej Żenczykowski			return ;;
1030*1b481fc3SMaciej Żenczykowski	esac
1031*1b481fc3SMaciej Żenczykowski}
1032*1b481fc3SMaciej Żenczykowski
1033*1b481fc3SMaciej Żenczykowski# Completion for ethtool --set-priv-flags
1034*1b481fc3SMaciej Żenczykowski_ethtool_set_priv_flags()
1035*1b481fc3SMaciej Żenczykowski{
1036*1b481fc3SMaciej Żenczykowski	if [ $(( cword % 2 )) -eq 0 ]; then
1037*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'on off' -- "$cur" ) )
1038*1b481fc3SMaciej Żenczykowski		return
1039*1b481fc3SMaciej Żenczykowski	fi
1040*1b481fc3SMaciej Żenczykowski
1041*1b481fc3SMaciej Żenczykowski	# Get available private flags
1042*1b481fc3SMaciej Żenczykowski	local -A flags=()
1043*1b481fc3SMaciej Żenczykowski	local flag
1044*1b481fc3SMaciej Żenczykowski	while IFS= read -r flag; do
1045*1b481fc3SMaciej Żenczykowski		# Ignore blank line from empty here-document
1046*1b481fc3SMaciej Żenczykowski		if [ -n "$flag" ]; then
1047*1b481fc3SMaciej Żenczykowski			flags[$flag]=1
1048*1b481fc3SMaciej Żenczykowski		fi
1049*1b481fc3SMaciej Żenczykowski	done <<ETHTOOL_PRIV_FLAGS
1050*1b481fc3SMaciej Żenczykowski$(_ethtool_get_names_in_section \
1051*1b481fc3SMaciej Żenczykowski	'Private flags for [[:graph:]]*' --show-priv-flags "${words[2]}")
1052*1b481fc3SMaciej ŻenczykowskiETHTOOL_PRIV_FLAGS
1053*1b481fc3SMaciej Żenczykowski
1054*1b481fc3SMaciej Żenczykowski	# Remove flags which have been seen
1055*1b481fc3SMaciej Żenczykowski	local word
1056*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
1057*1b481fc3SMaciej Żenczykowski		unset "flags[$word]"
1058*1b481fc3SMaciej Żenczykowski	done
1059*1b481fc3SMaciej Żenczykowski
1060*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!flags[*]}" -- "$cur" ) )
1061*1b481fc3SMaciej Żenczykowski}
1062*1b481fc3SMaciej Żenczykowski
1063*1b481fc3SMaciej Żenczykowski# Completion for ethtool --set-ring
1064*1b481fc3SMaciej Żenczykowski_ethtool_set_ring()
1065*1b481fc3SMaciej Żenczykowski{
1066*1b481fc3SMaciej Żenczykowski	local -A settings=(
1067*1b481fc3SMaciej Żenczykowski		[rx-jumbo]=1
1068*1b481fc3SMaciej Żenczykowski		[rx-mini]=1
1069*1b481fc3SMaciej Żenczykowski		[rx]=1
1070*1b481fc3SMaciej Żenczykowski		[tx]=1
1071*1b481fc3SMaciej Żenczykowski	)
1072*1b481fc3SMaciej Żenczykowski
1073*1b481fc3SMaciej Żenczykowski	if [ "${settings[$prev]+set}" ]; then
1074*1b481fc3SMaciej Żenczykowski		# Unsigned integer argument
1075*1b481fc3SMaciej Żenczykowski		return
1076*1b481fc3SMaciej Żenczykowski	fi
1077*1b481fc3SMaciej Żenczykowski
1078*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
1079*1b481fc3SMaciej Żenczykowski	local word
1080*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
1081*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
1082*1b481fc3SMaciej Żenczykowski	done
1083*1b481fc3SMaciej Żenczykowski
1084*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
1085*1b481fc3SMaciej Żenczykowski}
1086*1b481fc3SMaciej Żenczykowski
1087*1b481fc3SMaciej Żenczykowski# Completion for ethtool --show-nfc
1088*1b481fc3SMaciej Żenczykowski_ethtool_show_nfc()
1089*1b481fc3SMaciej Żenczykowski{
1090*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
1091*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'rule rx-flow-hash' -- "$cur" ) )
1092*1b481fc3SMaciej Żenczykowski		return
1093*1b481fc3SMaciej Żenczykowski	fi
1094*1b481fc3SMaciej Żenczykowski
1095*1b481fc3SMaciej Żenczykowski	case "${words[3]}" in
1096*1b481fc3SMaciej Żenczykowski		rule)
1097*1b481fc3SMaciej Żenczykowski			if [ "$cword" -eq 4 ]; then
1098*1b481fc3SMaciej Żenczykowski				COMPREPLY=(
1099*1b481fc3SMaciej Żenczykowski					$(PATH="$PATH:/sbin:/usr/sbin:/usr/local/sbin" \
1100*1b481fc3SMaciej Żenczykowski						ethtool --show-nfc "${words[2]}" 2>/dev/null |
1101*1b481fc3SMaciej Żenczykowski						command sed -n 's/^Filter:[[:space:]]*\([0-9]*\)$/\1/p')
1102*1b481fc3SMaciej Żenczykowski				)
1103*1b481fc3SMaciej Żenczykowski			fi
1104*1b481fc3SMaciej Żenczykowski			return ;;
1105*1b481fc3SMaciej Żenczykowski		rx-flow-hash)
1106*1b481fc3SMaciej Żenczykowski			case "$cword" in
1107*1b481fc3SMaciej Żenczykowski				4)
1108*1b481fc3SMaciej Żenczykowski					_ethtool_flow_type --hash
1109*1b481fc3SMaciej Żenczykowski					return ;;
1110*1b481fc3SMaciej Żenczykowski				5)
1111*1b481fc3SMaciej Żenczykowski					COMPREPLY=( $( compgen -W context -- "$cur" ) )
1112*1b481fc3SMaciej Żenczykowski					return ;;
1113*1b481fc3SMaciej Żenczykowski				6)
1114*1b481fc3SMaciej Żenczykowski					_ethtool_context
1115*1b481fc3SMaciej Żenczykowski					return ;;
1116*1b481fc3SMaciej Żenczykowski			esac
1117*1b481fc3SMaciej Żenczykowski			;;
1118*1b481fc3SMaciej Żenczykowski	esac
1119*1b481fc3SMaciej Żenczykowski}
1120*1b481fc3SMaciej Żenczykowski
1121*1b481fc3SMaciej Żenczykowski# Completion for ethtool --show-rxfh
1122*1b481fc3SMaciej Żenczykowski_ethtool_show_rxfh()
1123*1b481fc3SMaciej Żenczykowski{
1124*1b481fc3SMaciej Żenczykowski	case "$cword" in
1125*1b481fc3SMaciej Żenczykowski		3)
1126*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W context -- "$cur" ) )
1127*1b481fc3SMaciej Żenczykowski			return ;;
1128*1b481fc3SMaciej Żenczykowski		4)
1129*1b481fc3SMaciej Żenczykowski			_ethtool_context
1130*1b481fc3SMaciej Żenczykowski			return ;;
1131*1b481fc3SMaciej Żenczykowski	esac
1132*1b481fc3SMaciej Żenczykowski}
1133*1b481fc3SMaciej Żenczykowski
1134*1b481fc3SMaciej Żenczykowski# Completion for ethtool --test
1135*1b481fc3SMaciej Żenczykowski_ethtool_test()
1136*1b481fc3SMaciej Żenczykowski{
1137*1b481fc3SMaciej Żenczykowski	if [ "$cword" -eq 3 ]; then
1138*1b481fc3SMaciej Żenczykowski		COMPREPLY=( $( compgen -W 'external_lb offline online' -- "$cur" ) )
1139*1b481fc3SMaciej Żenczykowski		return
1140*1b481fc3SMaciej Żenczykowski	fi
1141*1b481fc3SMaciej Żenczykowski}
1142*1b481fc3SMaciej Żenczykowski
1143*1b481fc3SMaciej Żenczykowski# Completion for ethtool --set-module
1144*1b481fc3SMaciej Żenczykowski_ethtool_set_module()
1145*1b481fc3SMaciej Żenczykowski{
1146*1b481fc3SMaciej Żenczykowski	local -A settings=(
1147*1b481fc3SMaciej Żenczykowski		[power-mode-policy]=1
1148*1b481fc3SMaciej Żenczykowski	)
1149*1b481fc3SMaciej Żenczykowski
1150*1b481fc3SMaciej Żenczykowski	case "$prev" in
1151*1b481fc3SMaciej Żenczykowski		power-mode-policy)
1152*1b481fc3SMaciej Żenczykowski			COMPREPLY=( $( compgen -W 'high auto' -- "$cur" ) )
1153*1b481fc3SMaciej Żenczykowski			return ;;
1154*1b481fc3SMaciej Żenczykowski	esac
1155*1b481fc3SMaciej Żenczykowski
1156*1b481fc3SMaciej Żenczykowski	# Remove settings which have been seen
1157*1b481fc3SMaciej Żenczykowski	local word
1158*1b481fc3SMaciej Żenczykowski	for word in "${words[@]:3:${#words[@]}-4}"; do
1159*1b481fc3SMaciej Żenczykowski		unset "settings[$word]"
1160*1b481fc3SMaciej Żenczykowski	done
1161*1b481fc3SMaciej Żenczykowski
1162*1b481fc3SMaciej Żenczykowski	COMPREPLY=( $( compgen -W "${!settings[*]}" -- "$cur" ) )
1163*1b481fc3SMaciej Żenczykowski}
1164*1b481fc3SMaciej Żenczykowski
1165*1b481fc3SMaciej Żenczykowski# Complete any ethtool command
1166*1b481fc3SMaciej Żenczykowski_ethtool()
1167*1b481fc3SMaciej Żenczykowski{
1168*1b481fc3SMaciej Żenczykowski	local cur prev words cword
1169*1b481fc3SMaciej Żenczykowski	_init_completion || return
1170*1b481fc3SMaciej Żenczykowski
1171*1b481fc3SMaciej Żenczykowski	# Per "Contributing to bash-completion", complete non-duplicate long opts
1172*1b481fc3SMaciej Żenczykowski	local -A suggested_funcs=(
1173*1b481fc3SMaciej Żenczykowski		[--change-eeprom]=change_eeprom
1174*1b481fc3SMaciej Żenczykowski		[--change]=change
1175*1b481fc3SMaciej Żenczykowski		[--coalesce]=coalesce
1176*1b481fc3SMaciej Żenczykowski		[--config-nfc]=config_nfc
1177*1b481fc3SMaciej Żenczykowski		[--driver]=devname
1178*1b481fc3SMaciej Żenczykowski		[--dump-module-eeprom]=module_info
1179*1b481fc3SMaciej Żenczykowski		[--eeprom-dump]=eeprom_dump
1180*1b481fc3SMaciej Żenczykowski		[--features]=features
1181*1b481fc3SMaciej Żenczykowski		[--flash]=flash
1182*1b481fc3SMaciej Żenczykowski		[--get-dump]=get_dump
1183*1b481fc3SMaciej Żenczykowski		[--get-phy-tunable]=get_phy_tunable
1184*1b481fc3SMaciej Żenczykowski		[--identify]=devname
1185*1b481fc3SMaciej Żenczykowski		[--module-info]=module_info
1186*1b481fc3SMaciej Żenczykowski		[--negotiate]=devname
1187*1b481fc3SMaciej Żenczykowski		[--offload]=features
1188*1b481fc3SMaciej Żenczykowski		[--pause]=pause
1189*1b481fc3SMaciej Żenczykowski		[--per-queue]=per_queue
1190*1b481fc3SMaciej Żenczykowski		[--phy-statistics]=devname
1191*1b481fc3SMaciej Żenczykowski		[--register-dump]=register_dump
1192*1b481fc3SMaciej Żenczykowski		[--reset]=reset
1193*1b481fc3SMaciej Żenczykowski		[--set-channels]=set_channels
1194*1b481fc3SMaciej Żenczykowski		[--set-dump]=devname
1195*1b481fc3SMaciej Żenczykowski		[--set-eee]=set_eee
1196*1b481fc3SMaciej Żenczykowski		[--set-fec]=set_fec
1197*1b481fc3SMaciej Żenczykowski		[--set-phy-tunable]=set_phy_tunable
1198*1b481fc3SMaciej Żenczykowski		[--set-priv-flags]=set_priv_flags
1199*1b481fc3SMaciej Żenczykowski		[--set-ring]=set_ring
1200*1b481fc3SMaciej Żenczykowski		[--set-rxfh-indir]=rxfh
1201*1b481fc3SMaciej Żenczykowski		[--show-channels]=devname
1202*1b481fc3SMaciej Żenczykowski		[--show-coalesce]=devname
1203*1b481fc3SMaciej Żenczykowski		[--show-eee]=devname
1204*1b481fc3SMaciej Żenczykowski		[--show-features]=devname
1205*1b481fc3SMaciej Żenczykowski		[--show-fec]=devname
1206*1b481fc3SMaciej Żenczykowski		[--show-nfc]=show_nfc
1207*1b481fc3SMaciej Żenczykowski		[--show-offload]=devname
1208*1b481fc3SMaciej Żenczykowski		[--show-pause]=devname
1209*1b481fc3SMaciej Żenczykowski		[--show-permaddr]=devname
1210*1b481fc3SMaciej Żenczykowski		[--show-priv-flags]=devname
1211*1b481fc3SMaciej Żenczykowski		[--show-ring]=devname
1212*1b481fc3SMaciej Żenczykowski		[--show-rxfh]=show_rxfh
1213*1b481fc3SMaciej Żenczykowski		[--show-time-stamping]=devname
1214*1b481fc3SMaciej Żenczykowski		[--statistics]=devname
1215*1b481fc3SMaciej Żenczykowski		[--test]=test
1216*1b481fc3SMaciej Żenczykowski		[--set-module]=set_module
1217*1b481fc3SMaciej Żenczykowski		[--show-module]=devname
1218*1b481fc3SMaciej Żenczykowski	)
1219*1b481fc3SMaciej Żenczykowski	local -A other_funcs=(
1220*1b481fc3SMaciej Żenczykowski		[--config-ntuple]=config_nfc
1221*1b481fc3SMaciej Żenczykowski		[--rxfh]=rxfh
1222*1b481fc3SMaciej Żenczykowski		[--show-ntuple]=show_nfc
1223*1b481fc3SMaciej Żenczykowski		[--show-rxfh-indir]=devname
1224*1b481fc3SMaciej Żenczykowski		[-A]=pause
1225*1b481fc3SMaciej Żenczykowski		[-C]=coalesce
1226*1b481fc3SMaciej Żenczykowski		[-E]=change_eeprom
1227*1b481fc3SMaciej Żenczykowski		[-G]=set_ring
1228*1b481fc3SMaciej Żenczykowski		[-K]=features
1229*1b481fc3SMaciej Żenczykowski		[-L]=set_channels
1230*1b481fc3SMaciej Żenczykowski		[-N]=config_nfc
1231*1b481fc3SMaciej Żenczykowski		[-P]=devname
1232*1b481fc3SMaciej Żenczykowski		[-Q]=per_queue
1233*1b481fc3SMaciej Żenczykowski		[-S]=devname
1234*1b481fc3SMaciej Żenczykowski		[-T]=devname
1235*1b481fc3SMaciej Żenczykowski		[-U]=config_nfc
1236*1b481fc3SMaciej Żenczykowski		[-W]=devname
1237*1b481fc3SMaciej Żenczykowski		[-X]=rxfh
1238*1b481fc3SMaciej Żenczykowski		[-a]=devname
1239*1b481fc3SMaciej Żenczykowski		[-c]=devname
1240*1b481fc3SMaciej Żenczykowski		[-d]=register_dump
1241*1b481fc3SMaciej Żenczykowski		[-e]=eeprom_dump
1242*1b481fc3SMaciej Żenczykowski		[-f]=flash
1243*1b481fc3SMaciej Żenczykowski		[-g]=devname
1244*1b481fc3SMaciej Żenczykowski		[-i]=devname
1245*1b481fc3SMaciej Żenczykowski		[-k]=devname
1246*1b481fc3SMaciej Żenczykowski		[-l]=devname
1247*1b481fc3SMaciej Żenczykowski		[-m]=module_info
1248*1b481fc3SMaciej Żenczykowski		[-n]=show_nfc
1249*1b481fc3SMaciej Żenczykowski		[-p]=devname
1250*1b481fc3SMaciej Żenczykowski		[-r]=devname
1251*1b481fc3SMaciej Żenczykowski		[-s]=change
1252*1b481fc3SMaciej Żenczykowski		[-t]=test
1253*1b481fc3SMaciej Żenczykowski		[-u]=show_nfc
1254*1b481fc3SMaciej Żenczykowski		[-w]=get_dump
1255*1b481fc3SMaciej Żenczykowski		[-x]=devname
1256*1b481fc3SMaciej Żenczykowski	)
1257*1b481fc3SMaciej Żenczykowski
1258*1b481fc3SMaciej Żenczykowski	if [ "$cword" -le 1 ]; then
1259*1b481fc3SMaciej Żenczykowski		_available_interfaces
1260*1b481fc3SMaciej Żenczykowski		COMPREPLY+=(
1261*1b481fc3SMaciej Żenczykowski			$( compgen -W "--help --version ${!suggested_funcs[*]}" -- "$cur" )
1262*1b481fc3SMaciej Żenczykowski		)
1263*1b481fc3SMaciej Żenczykowski		return
1264*1b481fc3SMaciej Żenczykowski	fi
1265*1b481fc3SMaciej Żenczykowski
1266*1b481fc3SMaciej Żenczykowski	local func=${suggested_funcs[${words[1]}]-${other_funcs[${words[1]}]-}}
1267*1b481fc3SMaciej Żenczykowski	if [ "$func" ]; then
1268*1b481fc3SMaciej Żenczykowski		# All sub-commands have devname as their first argument
1269*1b481fc3SMaciej Żenczykowski		if [ "$cword" -eq 2 ]; then
1270*1b481fc3SMaciej Żenczykowski			_available_interfaces
1271*1b481fc3SMaciej Żenczykowski			return
1272*1b481fc3SMaciej Żenczykowski		fi
1273*1b481fc3SMaciej Żenczykowski
1274*1b481fc3SMaciej Żenczykowski		if [ "$func" != devname ]; then
1275*1b481fc3SMaciej Żenczykowski			"_ethtool_$func"
1276*1b481fc3SMaciej Żenczykowski		fi
1277*1b481fc3SMaciej Żenczykowski	fi
1278*1b481fc3SMaciej Żenczykowski} &&
1279*1b481fc3SMaciej Żenczykowskicomplete -F _ethtool ethtool
1280*1b481fc3SMaciej Żenczykowski
1281*1b481fc3SMaciej Żenczykowski# ex: filetype=sh sts=8 sw=8 ts=8 noet
1282