summaryrefslogtreecommitdiff
path: root/appl/cmd/auth/rsagen.b
blob: c553d102509e4887a6222a3c5b0dca236e48cefe (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
implement Rsagen;

include "sys.m";
	sys: Sys;

include "draw.m";

include "keyring.m";
	kr: Keyring;

include "arg.m";

Rsagen: module
{
	init:	fn(nil: ref Draw->Context, nil: list of string);
};

init(nil: ref Draw->Context, args: list of string)
{
	sys = load Sys Sys->PATH;
	kr = load Keyring Keyring->PATH;

	arg := load Arg Arg->PATH;
	arg->init(args);
	arg->setusage("auth/rsagen [-b bits] [-t 'attr=value attr=value ...']");
	tag: string;
	nbits := 1024;
	while((o := arg->opt()) != 0)
		case o {
		'b' =>
			nbits = int arg->earg();
			if(nbits <= 0)
				arg->usage();
			if(nbits > 4096)
				error("bits must be no greater than 4096");
		't' =>
			tag = arg->earg();
		* =>
			arg->usage();
		}
	args = arg->argv();
	if(args != nil)
		arg->usage();
	arg = nil;

	sk := kr->genSK("rsa", "", nbits);
	if(sk == nil)
		error("unable to generate key");
	s := kr->sktoattr(sk);
	# need to fix the attr interface so the following isn't needed:
	s = skip(s, "alg");
	s = skip(s, "owner");
	if(tag != nil)
		s = tag+" "+s;
	a := sys->aprint("key proto=rsa size=%d %s\n", nbits, s);
	if(sys->write(sys->fildes(1), a, len a) != len a)
		error(sys->sprint("error writing key: %r"));
}

skip(s: string, attr: string): string
{
	for(i := 0; i < len s && s[i] != ' '; i++)
		{}
	if(i >= len s)
		return s;
	(nf, fld) := sys->tokenize(s[0:i], "=");
	if(nf == 2 && hd fld == attr)
		s = s[i+1:];
	return s;
}

error(s: string)
{
	sys->fprint(sys->fildes(2), "rsagen: %s\n", s);
	raise "fail:error";
}