Differences From
Artifact [293667feb7]:
27 27 { 'db extract (<artifact>|<post>/<attachment number>)', 'extracts an attachment artifact from the database and prints it to standard out' };
28 28 { 'db excise <artifact>', 'extracts an attachment artifact from the database and prints it to standard out' };
29 29 { 'db obliterate', 'completely purge all parsav-related content and structure from the database, destroying all user content (requires confirmation)' };
30 30 { 'db insert', 'reads a file from standard in and inserts it into the attachment database, printing the resulting ID' };
31 31 { 'mkroot <handle>', 'establish a new root user with the given handle' };
32 32 { 'user <handle> auth <type> new', '(where applicable, managed auth only) create a new authentication token of the given type for a user' };
33 33 { 'user <handle> auth <type> reset', '(where applicable, managed auth only) delete all of a user\'s authentication tokens of the given type and issue a new one' };
34 - { 'user <handle> auth purge-credentials [<type>]', 'delete all credentials that would allow this user to log in (where possible)' };
34 + { 'user <handle> auth (<type>|all) purge', 'delete all credentials that would allow this user to log in (where possible)' };
35 35 { 'user <handle> (grant|revoke) (<priv>|all)', 'grant or revoke a specific power to or from a user' };
36 36 { 'user <handle> emasculate', 'strip all administrative powers from a user' };
37 37 { 'user <handle> suspend [<timespec>]', '(e.g. \27[1muser jokester suspend 5d 6h 7m 3s\27[m to suspend "jokester" for five days, six hours, seven minutes, and three seconds) suspend a user'};
38 - { 'actor <xid> purge-all', 'remove all traces of a user from the database (except local user credentials -- use \27[1mauth purge-credentials\27[m to prevent a user from accessing the instance)' };
38 + { 'actor <xid> purge-all', 'remove all traces of a user from the database (except local user credentials -- use \27[1mauth all purge\27[m to prevent a user from accessing the instance)' };
39 39 { 'actor <xid> create', 'instantiate a new actor' };
40 40 { 'actor <xid> bestow <epithet>', 'bestow an epithet upon an actor' };
41 41 { 'conf set <setting> <value>', 'add or a change a server configuration parameter to the database' };
42 42 { 'conf get <setting>', 'report the value of a server setting' };
43 43 { 'conf reset <setting>', 'reset a server setting to its default value' };
44 44 { 'conf refresh', 'instruct an instance to refresh its configuration cache' };
45 45 { 'conf chsec', 'reset the server secret, invalidating all authentication cookies' };
................................................................................
81 81
82 82 local terra gensec(sdest: rawstring)
83 83 var dest = [&uint8](sdest)
84 84 lib.crypt.spray(dest,64)
85 85 for i=0,64 do dest[i] = dest[i] % (0x7e - 0x20) + 0x20 end
86 86 dest[64] = 0
87 87 end
88 +
89 +local terra pwset(dlg: idelegate, buf: &(int8[33]), uid: uint64, reset: bool)
90 + lib.dbg('generating temporary password')
91 + var tmppw = [&uint8](&(buf[0]))
92 + lib.crypt.spray(tmppw,32) tmppw[32] = 0
93 + for i=0,32 do
94 + tmppw[i] = tmppw[i] % (10 + 26*2)
95 + if tmppw[i] >= 36 then
96 + tmppw[i] = tmppw[i] + (0x61 - 36)
97 + elseif tmppw[i] >= 10 then
98 + tmppw[i] = tmppw[i] + (0x41 - 10)
99 + else tmppw[i] = tmppw[i] + 0x30 end
100 + end
101 + lib.dbg('assigning temporary password')
102 + dlg:auth_create_pw(uid, reset, pstr {
103 + ptr = [rawstring](tmppw), ct = 32
104 + })
105 +end
88 106
89 107 local terra entry_mgtool(argc: int, argv: &rawstring): int
90 108 if argc < 1 then lib.bail('bad invocation!') end
91 109
92 110 lib.noise_init(2)
93 111 [lib.init]
94 112
................................................................................
219 237 root.epithet = epithets[lib.crypt.random(intptr,0,[epithets.type.N])]
220 238 root.rights.powers:fill() -- grant omnipotence
221 239 root.rights.rank = 1
222 240 var ruid = dlg:actor_create(&root)
223 241 dlg:conf_set('master',root.handle)
224 242 lib.report('created new administrator')
225 243 if mg then
226 - lib.dbg('generating temporary password')
227 - var tmppw: uint8[33]
228 - lib.crypt.spray(&tmppw[0],32) tmppw[32] = 0
229 - for i=0,32 do
230 - tmppw[i] = tmppw[i] % (10 + 26*2)
231 - if tmppw[i] >= 36 then
232 - tmppw[i] = tmppw[i] + (0x61 - 36)
233 - elseif tmppw[i] >= 10 then
234 - tmppw[i] = tmppw[i] + (0x41 - 10)
235 - else tmppw[i] = tmppw[i] + 0x30 end
236 - end
237 - lib.dbg('assigning temporary password')
238 - dlg:auth_create_pw(ruid, false, pstr {
239 - ptr = [rawstring](&tmppw[0]), ct = 32
240 - })
241 - lib.report('temporary root pw: ', {[rawstring](&tmppw[0]), 32})
244 + var tmppw: int8[33]
245 + pwset(dlg, &tmppw, ruid, false)
246 + lib.report('temporary root pw: ', {&tmppw[0], 32})
242 247 end
243 248 else goto cmderr end
244 249 elseif lib.str.cmp(mode.arglist(0),'user') == 0 then
250 + var umode: pbasic umode:parse(mode.arglist.ct, &mode.arglist(0))
251 + if umode.help then
252 + [ lib.emit(false, 1, 'usage: ', `argv[0], ' user ', umode.type.helptxt.flags, ' <handle> <cmd> [<args>…]', umode.type.helptxt.opts) ]
253 + return 1
254 + end
255 + if umode.arglist.ct >= 3 then
256 + var grant = lib.str.cmp(umode.arglist(1),'grant') == 0
257 + var handle = umode.arglist(0)
258 + var usr = dlg:actor_fetch_xid(pstr {ptr=handle, ct=lib.str.sz(handle)})
259 + if not usr then lib.bail('unknown handle') end
260 + if grant or lib.str.cmp(umode.arglist(1),'revoke') == 0 then
261 + var newprivs = usr.ptr.rights.powers
262 + var map = array([lib.store.privmap])
263 + if umode.arglist.ct == 3 and lib.str.cmp(umode.arglist(2),'all') == 0 then
264 + if grant
265 + then newprivs:fill()
266 + else newprivs:clear()
267 + end
268 + else
269 + for i=2,umode.arglist.ct do
270 + var priv = umode.arglist(i)
271 + for j=0,[map.type.N] do
272 + var p = map[j]
273 + if p.name:cmp_raw(priv) then
274 + if grant then
275 + lib.dbg('enabling power ', {p.name.ptr,p.name.ct})
276 + newprivs = newprivs + p.priv
277 + else
278 + lib.dbg('disabling power ', {p.name.ptr,p.name.ct})
279 + newprivs = newprivs - p.priv
280 + end
281 + break
282 + end
283 + end
284 + end
285 + end
286 +
287 + usr.ptr.rights.powers = newprivs
288 + dlg:actor_save_privs(usr.ptr)
289 + elseif lib.str.cmp(umode.arglist(1),'auth') == 0 and umode.arglist.ct == 4 then
290 + var reset = lib.str.cmp(umode.arglist(3),'reset') == 0
291 + if reset or lib.str.cmp(umode.arglist(3),'new') == 0 then
292 + if lib.str.cmp(umode.arglist(2),'pw') == 0 then
293 + var tmppw: int8[33]
294 + pwset(dlg, &tmppw, usr.ptr.id, reset)
295 + lib.report('new temporary password for ',usr.ptr.handle,': ', {&tmppw[0], 32})
296 + else lib.bail('unknown credential type') end
297 + elseif lib.str.cmp(umode.arglist(3),'purge') == 0 then
298 + else goto cmderr end
299 + else goto cmderr end
300 + else goto cmderr end
245 301 elseif lib.str.cmp(mode.arglist(0),'actor') == 0 then
246 302 elseif lib.str.cmp(mode.arglist(0),'tl') == 0 then
247 303 elseif lib.str.cmp(mode.arglist(0),'serv') == 0 then
248 304 else goto cmderr end
249 305 end
250 306 end
251 307
252 308 do return 0 end
253 - ::cmderr:: lib.bail('invalid command') return 2
309 + ::cmderr:: lib.bail('invalid command')
254 310 end
255 311
256 312 return entry_mgtool