5 from catacomb
.pwsafe
import *
8 from sys
import argv
, exit
, stdin
, stdout
, stderr
9 from getopt
import getopt
, GetoptError
10 from fnmatch
import fnmatch
13 prog
= re
.sub(r
'^.*[/\\]', '', argv
[0])
15 print >>stderr
, '%s: %s' %
(prog
, msg
)
20 if 'PWSAFE' in environ
:
21 file = environ
['PWSAFE']
23 file = '%s/.pwsafe' % environ
['HOME']
26 cipher
= 'blowfish-cbc'
30 opts
, args
= getopt(av
, 'c:h:m:', ['cipher=', 'mac=', 'hash='])
34 if o
in ('-c', '--cipher'):
36 elif o
in ('-m', '--mac'):
38 elif o
in ('-h', '--hash'):
48 db
= G
.open(file, 'n', 0600)
49 pp
= C
.ppread(tag
, C
.PMODE_VERIFY
)
50 if not mac
: mac
= hash + '-hmac'
51 c
= C
.gcciphers
[cipher
]
54 ppk
= PW
.PPK(pp
, c
, h
, m
)
55 ck
= C
.rand
.block(c
.keysz
.default
)
56 mk
= C
.rand
.block(m
.keysz
.default
)
57 k
= Crypto(c
, h
, m
, ck
, mk
)
63 db
['key'] = ppk
.encrypt(wrapstr(ck
) + wrapstr(mk
))
64 db
['magic'] = k
.encrypt(C
.rand
.block(h
.hashsz
))
67 if len(pp
) > 0 and pp
[-1] == '\n':
84 die('Password `%s\' not found.' % exc
.args
[0])
87 if len(av
) < 1 or len(av
) > 2:
91 pp
= C
.getpass("Enter passphrase `%s': " % tag
)
92 vpp
= C
.getpass("Confirm passphrase `%s': " % tag
)
94 raise ValueError, "passphrases don't match"
100 pw
[av
[0]] = chomp(pp
)
103 if len(av
) < 1 or len(av
) > 2:
106 pw_out
= PW(av
[0], 'w')
112 if pat
is None or fnmatch(k
, pat
):
124 if pat
is None or fnmatch(k
, pat
):
134 pix
.set(tag
, pw
[tag
])
141 pix
.set(pptag
, pw
[tag
])
150 except KeyError, exc
:
151 die('Password `%s\' not found.' % exc
.args
[0])
155 if ch
< ' ' or ch
> '~': return False
158 if asciip(s
): return s
159 return C
.ByteString(s
)
161 db
= gdbm
.open(file, 'r')
165 print '%r: %r' %
(present(k
), present(db
[k
]))
168 commands
= { 'create': [cmd_create
,
169 '[-c CIPHER] [-h HASH] [-m MAC] [PP-TAG]'],
170 'find' : [cmd_find
, 'LABEL'],
171 'store' : [cmd_store
, 'LABEL [VALUE]'],
172 'list' : [cmd_list
, '[GLOB-PATTERN]'],
173 'changepp' : [cmd_changepp
, ''],
174 'copy' : [cmd_copy
, 'DEST-FILE [GLOB-PATTERN]'],
175 'to-pixie' : [cmd_topixie
, '[TAG [PIXIE-TAG]]'],
176 'delete' : [cmd_del
, 'TAG'],
177 'dump' : [cmd_dump
, '']}
180 print '%s 1.0.0' % prog
182 print >>fp
, 'Usage: %s COMMAND [ARGS...]' % prog
188 Maintains passwords or other short secrets securely.
192 -h, --help Show this help text.
193 -v, --version Show program version number.
194 -u, --usage Show short usage message.
196 -f, --file=FILE Where to find the password-safe file.
201 print '%s %s' %
(c
, commands
[c
][1])
204 opts
, argv
= getopt(argv
[1:],
206 ['help', 'version', 'usage', 'file='])
211 if o
in ('-h', '--help'):
214 elif o
in ('-v', '--version'):
217 elif o
in ('-u', '--usage'):
220 elif o
in ('-f', '--file'):
228 if argv
[0] in commands
:
233 if commands
[c
][0](argv
):
234 print >>stderr
, 'Usage: %s %s %s' %
(prog
, c
, commands
[c
][1])