8c686e105f785cd5a56438bd36caf8f7e879f3f5
[hashcat.git] / extra / tab_completion / hashcat.sh
1 ## Authors.....: Jens Steube <jens.steube@gmail.com>
2 ## magnum <john.magnum@hushmail.com>
3 ##
4 ## License.....: MIT
5 ##
6
7 HASHCAT_ROOT="."
8
9 # helper functions
10 _hashcat_get_permutations ()
11 {
12 local num_devices=${1}
13 hashcat_devices_permutation=""
14
15 # Formula: Sum (k=1...num_devices) (num_devices! / (k! * (num_devices - k)!))
16 # or ofc (2 ^ num_devices) - 1
17 if [ "${num_devices}" -gt 0 ]; then
18
19 hashcat_devices_permutation=$(seq 1 $num_devices)
20
21 local k
22
23 for k in $(seq 2 $num_devices); do
24
25 if [ "${k}" -eq ${num_devices} ];then
26
27 hashcat_devices_permutation="${hashcat_devices_permutation} $(seq 1 $num_devices | tr '\n' ',' | sed 's/, *$//')"
28
29 else
30
31 local j
32 local max_pos=$((num_devices - ${k} + 1))
33
34 for j in $(seq 1 ${max_pos}); do
35
36 local max_value=$((j + ${k} - 1))
37
38 # init
39 local out_str=""
40
41 local l
42 for l in $(seq ${j} ${max_value}); do
43
44 if [ ${l} -gt ${j} ]; then
45 out_str=${out_str},
46 fi
47
48 out_str=${out_str}${l}
49
50 done
51
52 local chg_len=0
53 local last=$((k - 1))
54 local max_device=$((num_devices + 1))
55 local pos_changed=0
56
57 while [ "${chg_len}" -lt ${last} ]; do
58
59 local had_pos_changed=${pos_changed}
60 local old_chg_len=${chg_len}
61
62 local idx=$(((k - chg_len)))
63 local cur_num=$(echo ${out_str} | cut -d, -f ${idx})
64 local next_num=$((cur_num + 1))
65
66 if [ "${pos_changed}" -eq 0 ]; then
67
68 hashcat_devices_permutation="${hashcat_devices_permutation} ${out_str}"
69
70 else
71
72 pos_changed=0
73
74 fi
75
76 if [ "${next_num}" -lt ${max_device} -a "${next_num}" -le "${num_devices}" ]; then
77
78 out_str=$(echo ${out_str} | sed "s/,${cur_num},/,${next_num},/;s/,${cur_num}\$/,${next_num}/")
79
80 else
81
82 pos_changed=1
83 max_device=${cur_num}
84 chg_len=$((chg_len + 1))
85
86 fi
87
88 if [ "${had_pos_changed}" -eq 1 ];then
89
90 local changed=0
91 local m
92
93 for m in $(seq 1 ${old_chg_len}); do
94
95 local reset_idx=$((k - ${old_chg_len} + ${m}))
96 local last_num=$(echo ${out_str} | cut -d, -f ${reset_idx})
97 next_num=$((next_num + 1))
98
99 if [ "${next_num}" -lt ${max_device} -a "${next_num}" -le "${num_devices}" ]; then
100
101 out_str=$(echo ${out_str} | sed "s/,${last_num},/,${next_num},/;s/,${last_num}\$/,${next_num}/")
102 max_device=$((next_num + 2))
103 changed=$((changed + 1))
104
105 else
106 break
107 fi
108
109 done
110
111 if [ "${changed}" -gt 0 ]; then
112
113 max_device=$((num_devices + 1))
114 chg_len=0
115
116 fi
117
118 fi
119
120 done
121
122 done
123
124 fi
125
126 done
127 fi
128 }
129
130 _hashcat_opencl_devices ()
131 {
132 local num_devices=0
133
134 if which clinfo &> /dev/null; then
135
136 num_devices=$(clinfo 2>/dev/null 2> /dev/null)
137
138 elif which nvidia-smi &> /dev/null; then
139
140 num_devices=$(nvidia-smi --list-gpus | wc -l)
141
142 fi
143
144 return ${num_devices}
145 }
146
147 _hashcat_cpu_devices ()
148 {
149 local num_devices=0
150
151 if [ -f "/proc/cpuinfo" ]; then
152
153 num_devices=$(cat /proc/cpuinfo | grep -c processor 2> /dev/null)
154
155 fi
156
157 return ${num_devices}
158 }
159
160 _hashcat_contains ()
161 {
162 local haystack=${1}
163 local needle="${2}"
164
165 if echo "${haystack}" | grep -q " ${needle} " 2> /dev/null; then
166 return 0
167 elif echo "${haystack}" | grep -q "^${needle} " 2> /dev/null; then
168 return 0
169 elif echo "${haystack}" | grep -q " ${needle}\$" 2> /dev/null; then
170 return 0
171 fi
172
173 return 1
174 }
175
176 _hashcat ()
177 {
178 local VERSION=2.10
179
180 local HASH_MODES="0 10 11 12 20 21 22 23 30 40 50 60 100 101 110 111 112 120 121 122 124 130 131 132 133 140 141 150 160 190 200 300 400 500 501 900 1000 1100 1400 1410 1420 1421 1430 1440 1441 1450 1460 1500 1600 1700 1710 1711 1720 1722 1730 1731 1740 1750 1760 1800 2100 2400 2410 2500 2600 2611 2612 2711 2811 3000 3100 3200 3710 3711 3800 4300 4400 4500 4700 4800 4900 5000 5100 5200 5300 5400 5500 5600 5700 5800 6000 6100 6211 6212 6213 6221 6222 6223 6231 6232 6233 6241 6242 6243 6300 6400 6500 6600 6700 6800 6900 7100 7200 7300 7400 7500 7600 7700 7800 7900 8000 8100 8200 8300 8400 8500 8600 8700 8800 8900 9000 9100 9200 9300 9400 9500 9600 9700 9710 9720 9800 9810 9820 9900 10000 10100 10200 10300 10400 10410 10420 10500 10600 10700 10800 10900 11000 11100 11200 11300 11400 11500 11600 11700 11800 11900 12000 12100 12200 12300 12400 12500 12600 12700 12800 12900 13000"
181 local ATTACK_MODES="0 1 3 6 7"
182 local OUTFILE_FORMATS="1 2 3 4 5 6 7 8 9 10 11 12 13 14 15"
183 local OPENCL_DEVICE_TYPES="1 2 3"
184 local OPENCL_VECTOR_WIDTH="1 2 4 8 16"
185 local DEBUG_MODE="1 2 3 4"
186 local WORKLOAD_PROFILE="1 2 3"
187 local HIDDEN_FILES="exe|bin|pot|hcstat|dictstat|accepted|sh|cmd|bat|restore"
188 local HIDDEN_FILES_AGGRESIVE="exe|bin|pot|hcstat|dictstat|hcmask|hcchr|accepted|sh|cmd|restore"
189 local BUILD_IN_CHARSETS='?l ?u ?d ?a ?b ?s'
190
191 local SHORT_OPTS="-m -a -V -v -h -b -t -o -p -c -d -w -n -u -j -k -r -g -1 -2 -3 -4 -i -s -l"
192 local LONG_OPTS="--hash-type --attack-mode --version --help --eula --quiet --benchmark --benchmark-repeats --hex-salt --hex-wordlist --hex-charset --force --status --status-timer --machine-readable --loopback --weak-hash-threshold --markov-hcstat --markov-disable --markov-classic --markov-threshold --runtime --session --restore --restore-disable --outfile --outfile-format --outfile-autohex-disable --outfile-check-timer --outfile-check-dir --separator --show --left --username --remove --remove-timer --potfile-disable --potfile-path --debug-mode --debug-file --induction-dir --segment-size --bitmap-min --bitmap-max --cpu-affinity --opencl-devices --opencl-platforms --opencl-device-types --opencl-vector-width --workload-profile --kernel-accel --kernel-loops --gpu-temp-disable --gpu-temp-abort --gpu-temp-retain --powertune-enable --skip --limit --keyspace --rule-left --rule-right --rules-file --generate-rules --generate-rules-func-min --generate-rules-func-max --generate-rules-seed --rules-cleanup --custom-charset1 --custom-charset2 --custom-charset3 --custom-charset4 --increment --increment-min --increment-max --logfile-disable --scrypt-tmto --truecrypt-keyfiles"
193 local OPTIONS="-m -a -t -o -p -c -d -w -n -u -j -k -r -g -1 -2 -3 -4 -s -l --hash-type --attack-mode --benchmark-repeats --status-timer --weak-hash-threshold --markov-hcstat --markov-threshold --runtime --session --timer --outfile --outfile-format --outfile-check-timer --outfile-check-dir --separator --remove-timer --potfile-path --debug-mode --debug-file --induction-dir --segment-size --bitmap-min --bitmap-max --cpu-affinity --opencl-devices --opencl-platforms --opencl-device-types --opencl-vector-width --workload-profile --kernel-accel --kernel-loops --gpu-temp-abort --gpu-temp-retain -disable --skip --limit --rule-left --rule-right --rules-file --generate-rules --generate-rules-func-min --generate-rules-func-max --generate-rules-seed --custom-charset1 --custom-charset2 --custom-charset3 --custom-charset4 --increment-min --increment-max --scrypt-tmto --truecrypt-keyfiles"
194
195 COMPREPLY=()
196 local cur="${COMP_WORDS[COMP_CWORD]}"
197 local prev="${COMP_WORDS[COMP_CWORD-1]}"
198
199 # if cur is just '=', ignore the '=' and treat it as only the prev was provided
200 if [[ "${cur}" == '=' ]]; then
201
202 cur=""
203
204 elif [[ "${prev}" == '=' ]]; then
205
206 if [ "${COMP_CWORD}" -gt 2 ]; then
207
208 prev="${COMP_WORDS[COMP_CWORD-2]}"
209
210 fi
211
212 fi
213
214 case "${prev}" in
215
216 -m|--hash-type)
217 COMPREPLY=($(compgen -W "${HASH_MODES}" -- ${cur}))
218 return 0
219 ;;
220
221 -a|--attack-mode)
222 COMPREPLY=($(compgen -W "${ATTACK_MODES}" -- ${cur}))
223 return 0
224 ;;
225
226 --outfile-format)
227 COMPREPLY=($(compgen -W "${OUTFILE_FORMATS}" -- ${cur}))
228 return 0
229 ;;
230
231 -w|--workload-profile)
232 COMPREPLY=($(compgen -W "${WORKLOAD_PROFILE}" -- ${cur}))
233 return 0
234 ;;
235
236 -o|--outfile|-r|--rules-file|--debug-file|--potfile-path)
237 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
238 COMPREPLY=($(compgen -W "${files}" -- ${cur})) # or $(compgen -f -X '*.+('${HIDDEN_FILES_AGGRESIVE}')' -- ${cur})
239 return 0
240 ;;
241
242 --markov-hcstat)
243 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES}')' 2> /dev/null)
244 COMPREPLY=($(compgen -W "${files}" -- ${cur})) # or $(compgen -f -X '*.+('${HIDDEN_FILES_AGGRESIVE}')' -- ${cur})
245 return 0
246 ;;
247
248 -d|--opencl-devices)
249 _hashcat_opencl_devices
250 local num_devices=${?}
251
252 _hashcat_get_permutations ${num_devices}
253
254 COMPREPLY=($(compgen -W "${hashcat_devices_permutation}" -- ${cur}))
255 return 0
256 ;;
257
258 --opencl-device-types)
259 COMPREPLY=($(compgen -W "${OPENCL_DEVICE_TYPES}" -- ${cur}))
260 return 0
261 ;;
262
263 --opencl-vector-width)
264 COMPREPLY=($(compgen -W "${OPENCL_VECTOR_WIDTH}" -- ${cur}))
265 return 0
266 ;;
267
268 --opencl-platforms)
269 local icd_list=$(ls -1 /etc/OpenCL/vendors/*.icd 2> /dev/null)
270
271 local architecture=$(getconf LONG_BIT 2> /dev/null)
272
273 if [ -z "${architecture}" ]; then
274 return 0
275 fi
276
277 # filter the icd_list (do not show 32 bit on 64bit systems and vice versa)
278
279 if [ "${architecture}" -eq 64 ]; then
280
281 icd_list=$(echo "${icd_list}" | grep -v "32.icd")
282
283 else
284
285 icd_list=$(echo "${icd_list}" | grep -v "64.icd")
286
287 fi
288
289 local number_icds=$(seq 1 $(echo "${icd_list}" | wc -l))
290
291 COMPREPLY=($(compgen -W "${number_icds}" -- ${cur}))
292
293 return 0
294 ;;
295
296 --cpu-affinity)
297 _hashcat_cpu_devices
298 local num_devices=${?}
299
300 _hashcat_get_permutations ${num_devices}
301
302 COMPREPLY=($(compgen -W "${hashcat_devices_permutation}" -- ${cur}))
303 return 0
304 ;;
305
306 -1|-2|-3|-4|--custom-charset1|--custom-charset2|--custom-charset3|--custom-charset4)
307 local mask=${BUILD_IN_CHARSETS}
308
309 if [ -e "${cur}" ]; then # should be hcchr file (but not enforced)
310
311 COMPREPLY=($(compgen -W "${cur}" -- ${cur}))
312 return 0
313
314 fi
315
316 if [ -n "${cur}" ]; then
317
318 local cur_var=$(echo "${cur}" | sed 's/\?$//')
319
320 mask="${mask} ${cur_var}"
321 local h
322 for h in ${mask}; do
323
324 if ! echo ${cur} | grep -q ${h} 2> /dev/null; then
325
326 if echo ${cur} | grep -q '?a' 2> /dev/null; then
327
328 if [[ "${h}" == "?l" ]] ; then
329 continue
330 elif [[ "${h}" == "?u" ]] ; then
331 continue
332 elif [[ "${h}" == "?d" ]] ; then
333 continue
334 elif [[ "${h}" == "?s" ]] ; then
335 continue
336 elif [[ "${h}" == "?b" ]] ; then
337 continue
338 fi
339
340 fi
341
342 mask="${mask} ${cur_var}${h}"
343
344 fi
345
346 done
347 fi
348
349 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES}')' 2> /dev/null)
350
351 mask="${mask} ${files}"
352
353 COMPREPLY=($(compgen -W "${mask}" -- ${cur}))
354 return 0
355 ;;
356
357 -t|-p|-c|-j|-k|-g| \
358 --status-timer|--markov-threshold|--runtime|--session|--separator|--segment-size|--rule-left|--rule-right| \
359 --gpu-temp-abort|--gpu-temp-retain|--generate-rules|--generate-rules-func-min|--generate-rules-func-max| \
360 --increment-min|--increment-max|--remove-timer|--bitmap-min|--bitmap-max|--skip|--limit|--generate-rules-seed| \
361 --weak-hash-threshold|--outfile-check-timer|--outfile-check-dir|--induction-dir|--scrypt-tmto)
362 return 0
363 ;;
364
365 --debug-mode)
366 COMPREPLY=($(compgen -W "${DEBUG_MODE}" -- ${cur}))
367 return 0
368 ;;
369
370 --truecrypt-keyfiles)
371 # first: remove the quotes such that file matching is possible
372
373 local cur_part0=$(echo "${cur}" | grep -Eo '^("|'"'"')')
374
375 local cur_mod=$(echo "${cur}" | sed 's/^["'"'"']//')
376 local cur_part1=$(echo "${cur_mod}" | grep ',' 2> /dev/null | sed 's/^\(.*, *\)[^,]*$/\1/')
377 local cur_part2=$(echo "${cur_mod}" | sed 's/^.*, *\([^,]*\)$/\1/')
378
379 # generate lines with the file name and a duplicate of it with a comma at the end
380
381 local files=$(ls -d ${cur_part2}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null | sed 's/^\(.*\)$/\1\n\1,\n/' | sed "s/^/${cur_part0}${cur_part1}/" | sed "s/$/${cur_part0}/")
382 COMPREPLY=($(compgen -W "${files}" -- ${cur}))
383 return 0
384
385 esac
386
387 # allow also the VARIANTS w/o spaces
388 # we could use compgen -P prefix, but for some reason it doesn't seem to work always
389
390 case "$cur" in
391
392 -m*)
393 local hash_modes_var="$(echo -n "-m ${HASH_MODES}" | sed 's/ / -m/g')"
394 COMPREPLY=($(compgen -W "${hash_modes_var}" -- ${cur}))
395 return 0
396 ;;
397
398 -a*)
399 local attack_modes_var="$(echo -n "-a ${ATTACK_MODES}" | sed 's/ / -a/g')"
400 COMPREPLY=($(compgen -W "${attack_modes_var}" -- ${cur}))
401 return 0
402 ;;
403
404 -w*)
405 local workload_profile_var="$(echo -n "-w ${WORKLOAD_PROFILE}" | sed 's/ / -w/g')"
406 COMPREPLY=($(compgen -W "${workload_profile_var}" -- ${cur}))
407 return 0
408 ;;
409
410 -o*)
411 local outfile_var=$(ls -d ${cur:2}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
412 outfile_var="$(echo -e "\n${outfile_var}" | sed 's/^/-o/g')"
413 COMPREPLY=($(compgen -W "${outfile_var}" -- ${cur}))
414 return 0
415 ;;
416
417 -r*)
418 local outfile_var=$(ls -d ${cur:2}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
419 outfile_var="$(echo -e "\n${outfile_var}" | sed 's/^/-r/g')"
420 COMPREPLY=($(compgen -W "${outfile_var}" -- ${cur}))
421 return 0
422 ;;
423
424 -d*)
425 _hashcat_opencl_devices
426 local num_devices=${?}
427
428 _hashcat_get_permutations ${num_devices}
429
430 local opencl_devices_var="$(echo " "${hashcat_devices_permutation} | sed 's/ / -d/g')"
431 COMPREPLY=($(compgen -W "${opencl_devices_var}" -- ${cur}))
432 return 0
433 ;;
434 esac
435
436 # Complete options/switches (not the arguments)
437
438 if [[ "${cur}" == -* ]]; then
439
440 COMPREPLY=($(compgen -W "${SHORT_OPTS} ${LONG_OPTS}" -- ${cur}))
441 return 0
442
443 fi
444
445 # additional parameter, no switch nor option but maybe hash file, dictionary, mask, directory
446
447 # check if first option out of (hash.txt and dictionary|mask|directory)
448 # is first option iff: here
449 # is second option iff: COMP_CWORD > 2 and no switch before (-*) if no option afterwards (for mask -a 3, -a 6, -a 7 - but possible for dicts!)
450
451 local h=1
452 local no_opts=0
453 local attack_mode=0 # also default of hashcat
454 local has_charset_1=0
455 local has_charset_2=0
456 local has_charset_3=0
457 local has_charset_4=0
458
459 while [ ${h} -le ${COMP_CWORD} ]; do
460
461 if [[ "${COMP_WORDS[h]}" == "-a" ]]; then
462
463 attack_mode=${COMP_WORDS[$((h + 1))]}
464
465 elif [[ "${COMP_WORDS[h]}" == -a* ]]; then
466
467 attack_mode=${COMP_WORDS[h]:2}
468
469 elif [[ "${COMP_WORDS[h]}" == "--attack-mode" ]]; then
470
471 attack_mode=${COMP_WORDS[$((h + 1))]}
472
473 elif [[ "${COMP_WORDS[h]}" == "-1" ]]; then
474
475 has_charset_1=1
476
477 elif [[ "${COMP_WORDS[h]}" == "--custom-charset1" ]]; then
478
479 has_charset_1=1
480
481 elif [[ "${COMP_WORDS[h]}" == "-2" ]]; then
482
483 has_charset_2=1
484
485 elif [[ "${COMP_WORDS[h]}" == "--custom-charset2" ]]; then
486
487 has_charset_2=1
488
489 elif [[ "${COMP_WORDS[h]}" == "-3" ]]; then
490
491 has_charset_3=1
492
493 elif [[ "${COMP_WORDS[h]}" == "--custom-charset3" ]]; then
494
495 has_charset_3=1
496
497 elif [[ "${COMP_WORDS[h]}" == "-4" ]]; then
498
499 has_charset_4=1
500
501 elif [[ "${COMP_WORDS[h]}" == "--custom-charset4" ]]; then
502
503 has_charset_4=1
504
505 fi
506
507 if _hashcat_contains "${OPTIONS}" "${COMP_WORDS[h]}"; then
508
509 h=$((h + 2))
510
511 else
512
513 if ! _hashcat_contains "${LONG_OPTS}${SHORT_OPTS}" "${COMP_WORDS[h]}"; then
514 local variants="-m -a -w -n -u -o -r -d"
515 local skip=0
516 local v
517 for v in ${variants}; do
518
519 if [[ "${COMP_WORDS[h]:0:2}" == "${v}" ]]; then
520 skip=1
521 fi
522
523 done
524
525 if [ "${skip}" -eq 0 ]; then
526
527 no_opts=$((no_opts + 1))
528
529 fi
530 fi
531
532 h=$((h + 1))
533
534 fi
535
536 done
537
538 case "${no_opts}" in
539
540 0)
541 return 0
542 ;;
543
544 1)
545 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
546 COMPREPLY=($(compgen -W "${files}" -- ${cur}))
547 return 0
548 ;;
549
550 *)
551 case "${attack_mode}" in
552
553 0)
554 # dict/directory are files here
555 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
556 COMPREPLY=($(compgen -W "${files}" -- ${cur}))
557 return 0
558 ;;
559
560 1)
561 if [ "${no_opts}" -gt 4 ]; then
562 return 0
563 fi
564
565 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
566 COMPREPLY=($(compgen -W "${files}" -- ${cur}))
567 return 0
568 ;;
569
570 3)
571 if [ "${no_opts}" -eq 2 ]; then
572 local mask=${BUILD_IN_CHARSETS}
573
574 if [ "${has_charset_1}" -eq 1 ]; then
575
576 mask="${mask} ?1"
577
578 fi
579
580 if [ "${has_charset_2}" -eq 1 ]; then
581
582 mask="${mask} ?2"
583
584 fi
585
586 if [ "${has_charset_3}" -eq 1 ]; then
587
588 mask="${mask} ?3"
589
590 fi
591
592 if [ "${has_charset_4}" -eq 1 ]; then
593
594 mask="${mask} ?4"
595
596 fi
597
598 if [ -e "${cur}" ]; then # should be hcmask file (but not enforced)
599
600 COMPREPLY=($(compgen -W "${cur}" -- ${cur}))
601 return 0
602
603 fi
604
605 if [ -n "${cur}" ]; then
606
607 local cur_var=$(echo "${cur}" | sed 's/\?$//')
608
609 mask="${mask} ${cur_var}"
610
611 local h
612 for h in ${mask}; do
613
614 mask="${mask} ${cur_var}${h}"
615
616 done
617 fi
618
619 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES}')' 2> /dev/null)
620
621 mask="${mask} ${files}"
622
623 COMPREPLY=($(compgen -W "${mask}" -- ${cur}))
624 return 0
625 fi
626 ;;
627
628 6)
629 if [ "${no_opts}" -eq 2 ]; then
630
631 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
632 COMPREPLY=($(compgen -W "${files}" -- ${cur}))
633
634 elif [ "${no_opts}" -eq 3 ]; then
635 local mask=${BUILD_IN_CHARSETS}
636
637 if [ "${has_charset_1}" -eq 1 ]; then
638
639 mask="${mask} ?1"
640
641 fi
642
643 if [ "${has_charset_2}" -eq 1 ]; then
644
645 mask="${mask} ?2"
646
647 fi
648
649 if [ "${has_charset_3}" -eq 1 ]; then
650
651 mask="${mask} ?3"
652
653 fi
654
655 if [ "${has_charset_4}" -eq 1 ]; then
656
657 mask="${mask} ?4"
658
659 fi
660
661 if [ -e "${cur}" ]; then # should be hcmask file (but not enforced)
662
663 COMPREPLY=($(compgen -W "${cur}" -- ${cur}))
664 return 0
665
666 fi
667
668 if [ -n "${cur}" ]; then
669
670 local cur_var=$(echo "${cur}" | sed 's/\?$//')
671
672 mask="${mask} ${cur_var}"
673
674 local h
675 for h in ${mask}; do
676
677 mask="${mask} ${cur_var}${h}"
678
679 done
680 fi
681
682 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES}')' 2> /dev/null)
683
684 mask="${mask} ${files}"
685
686 COMPREPLY=($(compgen -W "${mask}" -- ${cur}))
687 return 0
688
689 fi
690 ;;
691
692 7)
693 if [ "${no_opts}" -eq 2 ]; then
694 local mask=${BUILD_IN_CHARSETS}
695
696 if [ "${has_charset_1}" -eq 1 ]; then
697
698 mask="${mask} ?1"
699
700 fi
701
702 if [ "${has_charset_2}" -eq 1 ]; then
703
704 mask="${mask} ?2"
705
706 fi
707
708 if [ "${has_charset_3}" -eq 1 ]; then
709
710 mask="${mask} ?3"
711
712 fi
713
714 if [ "${has_charset_4}" -eq 1 ]; then
715
716 mask="${mask} ?4"
717
718 fi
719
720 if [ -e "${cur}" ]; then # should be hcmask file (but not enforced)
721
722 COMPREPLY=($(compgen -W "${cur}" -- ${cur}))
723 return 0
724
725 fi
726
727 if [ -n "${cur}" ]; then
728
729 local cur_var=$(echo "${cur}" | sed 's/\?$//')
730
731 mask="${mask} ${cur_var}"
732
733 local h
734 for h in ${mask}; do
735
736 mask="${mask} ${cur_var}${h}"
737
738 done
739 fi
740
741 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES}')' 2> /dev/null)
742
743 mask="${mask} ${files}"
744
745 COMPREPLY=($(compgen -W "${mask}" -- ${cur}))
746 return 0
747
748 elif [ "${no_opts}" -eq 3 ]; then
749
750 local files=$(ls -d ${cur}* 2> /dev/null | grep -Eiv '*\.('${HIDDEN_FILES_AGGRESIVE}')' 2> /dev/null)
751 COMPREPLY=($(compgen -W "${files}" -- ${cur}))
752 return
753
754 fi
755 ;;
756
757 esac
758
759 esac
760 }
761
762 complete -F _hashcat -o filenames "${HASHCAT_ROOT}"/hashcat64.bin "${HASHCAT_ROOT}"/hashcat32.bin "${HASHCAT_ROOT}"/hashcat hashcat