Initial commit of OpenSPARC T2 architecture model.
[OpenSPARC-T2-SAM] / sam-t2 / devtools / v9 / bin / mkpasswd
CommitLineData
920dae64
AT
1#!/bin/sh
2# \
3exec expect -- "$0" ${1+"$@"}
4# mkpasswd - make a password, if username given, set it.
5# Author: Don Libes, NIST
6
7# defaults
8set length 9
9set minnum 2
10set minlower 2
11set minupper 2
12set minspecial 1
13set verbose 0
14set distribute 0
15
16if {[file executable /bin/nispasswd]} {
17 set defaultprog /bin/nispasswd
18} elseif {[file executable /bin/yppasswd]} {
19 set defaultprog /bin/yppasswd
20} elseif {[file executable /bin/passwd]} {
21 set defaultprog /bin/passwd
22} else {
23 set defaultprog passwd
24}
25set prog $defaultprog
26
27while {[llength $argv]>0} {
28 set flag [lindex $argv 0]
29 switch -- $flag \
30 "-l" {
31 set length [lindex $argv 1]
32 set argv [lrange $argv 2 end]
33 } "-d" {
34 set minnum [lindex $argv 1]
35 set argv [lrange $argv 2 end]
36 } "-c" {
37 set minlower [lindex $argv 1]
38 set argv [lrange $argv 2 end]
39 } "-C" {
40 set minupper [lindex $argv 1]
41 set argv [lrange $argv 2 end]
42 } "-s" {
43 set minspecial [lindex $argv 1]
44 set argv [lrange $argv 2 end]
45 } "-v" {
46 set verbose 1
47 set argv [lrange $argv 1 end]
48 } "-p" {
49 set prog [lindex $argv 1]
50 set argv [lrange $argv 2 end]
51 } "-2" {
52 set distribute 1
53 set argv [lrange $argv 1 end]
54 } default {
55 set user [lindex $argv 0]
56 set argv [lrange $argv 1 end]
57 break
58 }
59}
60
61if {[llength $argv]} {
62 puts "usage: mkpasswd \[args] \[user]"
63 puts " where arguments are:"
64 puts " -l # (length of password, default = $length)"
65 puts " -d # (min # of digits, default = $minnum)"
66 puts " -c # (min # of lowercase chars, default = $minlower)"
67 puts " -C # (min # of uppercase chars, default = $minupper)"
68 puts " -s # (min # of special chars, default = $minspecial)"
69 puts " -v (verbose, show passwd interaction)"
70 puts " -p prog (program to set password, default = $defaultprog)"
71 exit 1
72}
73
74if {$minnum + $minlower + $minupper + $minspecial > $length} {
75 puts "impossible to generate $length-character password\
76 with $minnum numbers, $minlower lowercase letters,\
77 $minupper uppercase letters and\
78 $minspecial special characters."
79 exit 1
80}
81
82# if there is any underspecification, use additional lowercase letters
83set minlower [expr {$length - ($minnum + $minupper + $minspecial)}]
84
85set lpass "" ;# password chars typed by left hand
86set rpass "" ;# password chars typed by right hand
87
88# insert char into password at a random position, thereby spreading
89# the different kinds of characters throughout the password
90proc insert {pvar char} {
91 upvar $pvar p
92
93 set p [linsert $p [rand [expr {(1+[llength $p])}]] $char]
94}
95
96proc rand {m} {
97 expr {int($m*rand())}
98}
99
100# choose left or right starting hand
101set initially_left [set isleft [rand 2]]
102
103# given a size, distribute between left and right hands
104# taking into account where we left off
105proc psplit {max lvar rvar} {
106 upvar $lvar left $rvar right
107 global isleft
108
109 if {$isleft} {
110 set right [expr $max/2]
111 set left [expr $max-$right]
112 set isleft [expr !($max%2)]
113 } else {
114 set left [expr $max/2]
115 set right [expr $max-$left]
116 set isleft [expr $max%2]
117 }
118}
119
120if {$distribute} {
121 set lkeys {q w e r t a s d f g z x c v b}
122 set rkeys {y u i o p h j k l n m}
123 set lnums {1 2 3 4 5 6}
124 set rnums {7 8 9 0}
125 set lspec {! @ # \$ %}
126 set rspec {^ & * ( ) - = _ + [ ] "{" "}" \\ | ; : ' \" < > , . ? /}
127} else {
128 set lkeys {a b c d e f g h i j k l m n o p q r s t u v w x y z}
129 set rkeys {a b c d e f g h i j k l m n o p q r s t u v w x y z}
130 set lnums {0 1 2 3 4 5 6 7 8 9}
131 set rnums {0 1 2 3 4 5 6 7 8 9}
132 set lspec {! @ # \$ % ~ ^ & * ( ) - = _ + [ ] "{" "}" \\ | ; : ' \" < > , . ? /}
133 set rspec {! @ # \$ % ~ ^ & * ( ) - = _ + [ ] "{" "}" \\ | ; : ' \" < > , . ? /}
134}
135
136set lkeys_length [llength $lkeys]
137set rkeys_length [llength $rkeys]
138set lnums_length [llength $lnums]
139set rnums_length [llength $rnums]
140set lspec_length [llength $lspec]
141set rspec_length [llength $rspec]
142
143psplit $minnum left right
144for {set i 0} {$i<$left} {incr i} {
145 insert lpass [lindex $lnums [rand $lnums_length]]
146}
147for {set i 0} {$i<$right} {incr i} {
148 insert rpass [lindex $rnums [rand $rnums_length]]
149}
150
151psplit $minlower left right
152for {set i 0} {$i<$left} {incr i} {
153 insert lpass [lindex $lkeys [rand $lkeys_length]]
154}
155for {set i 0} {$i<$right} {incr i} {
156 insert rpass [lindex $rkeys [rand $rkeys_length]]
157}
158
159psplit $minupper left right
160for {set i 0} {$i<$left} {incr i} {
161 insert lpass [string toupper [lindex $lkeys [rand $lkeys_length]]]
162}
163for {set i 0} {$i<$right} {incr i} {
164 insert rpass [string toupper [lindex $rkeys [rand $rkeys_length]]]
165}
166
167psplit $minspecial left right
168for {set i 0} {$i<$left} {incr i} {
169 insert lpass [lindex $lspec [rand $lspec_length]]
170}
171for {set i 0} {$i<$right} {incr i} {
172 insert rpass [lindex $rspec [rand $rspec_length]]
173}
174
175# merge results together
176foreach l $lpass r $rpass {
177 if {$initially_left} {
178 append password $l $r
179 } else {
180 append password $r $l
181 }
182}
183
184if {[info exists user]} {
185 if {!$verbose} {
186 log_user 0
187 }
188
189 spawn $prog $user
190 expect {
191 "assword*:" {
192 # some systems say "Password (again):"
193 send "$password\r"
194 exp_continue
195 }
196 }
197
198 # if user isn't watching, check status
199 if {!$verbose} {
200 if {[lindex [wait] 3]} {
201 puts -nonewline "$expect_out(buffer)"
202 exit 1
203 }
204 }
205
206 if {$verbose} {
207 puts -nonewline "password for $user is "
208 }
209}
210
211puts "$password"