xref: /plan9/sys/src/cmd/fossil/Ccli.c (revision 5e96a66c77eb9140492ca53f857cbbf108e128ed)
1*5e96a66cSDavid du Colombier #include "stdinc.h"
2*5e96a66cSDavid du Colombier 
3*5e96a66cSDavid du Colombier #include "9.h"
4*5e96a66cSDavid du Colombier 
5*5e96a66cSDavid du Colombier typedef struct {
6*5e96a66cSDavid du Colombier 	char*	argv0;
7*5e96a66cSDavid du Colombier 	int	(*cmd)(int, char*[]);
8*5e96a66cSDavid du Colombier } Cmd;
9*5e96a66cSDavid du Colombier 
10*5e96a66cSDavid du Colombier static struct {
11*5e96a66cSDavid du Colombier 	VtLock*	lock;
12*5e96a66cSDavid du Colombier 	Cmd*	cmd;
13*5e96a66cSDavid du Colombier 	int	ncmd;
14*5e96a66cSDavid du Colombier 	int	hi;
15*5e96a66cSDavid du Colombier } cbox;
16*5e96a66cSDavid du Colombier 
17*5e96a66cSDavid du Colombier enum {
18*5e96a66cSDavid du Colombier 	NCmdIncr	= 20,
19*5e96a66cSDavid du Colombier };
20*5e96a66cSDavid du Colombier 
21*5e96a66cSDavid du Colombier int
cliError(char * fmt,...)22*5e96a66cSDavid du Colombier cliError(char* fmt, ...)
23*5e96a66cSDavid du Colombier {
24*5e96a66cSDavid du Colombier 	char *p;
25*5e96a66cSDavid du Colombier 	va_list arg;
26*5e96a66cSDavid du Colombier 
27*5e96a66cSDavid du Colombier 	va_start(arg, fmt);
28*5e96a66cSDavid du Colombier 	p = vsmprint(fmt, arg);
29*5e96a66cSDavid du Colombier 	vtSetError("%s", p);
30*5e96a66cSDavid du Colombier 	free(p);
31*5e96a66cSDavid du Colombier 	va_end(arg);
32*5e96a66cSDavid du Colombier 
33*5e96a66cSDavid du Colombier 	return 0;
34*5e96a66cSDavid du Colombier }
35*5e96a66cSDavid du Colombier 
36*5e96a66cSDavid du Colombier int
cliExec(char * buf)37*5e96a66cSDavid du Colombier cliExec(char* buf)
38*5e96a66cSDavid du Colombier {
39*5e96a66cSDavid du Colombier 	int argc, i, r;
40*5e96a66cSDavid du Colombier 	char *argv[20], *p;
41*5e96a66cSDavid du Colombier 
42*5e96a66cSDavid du Colombier 	p = vtStrDup(buf);
43*5e96a66cSDavid du Colombier 	if((argc = tokenize(p, argv, nelem(argv)-1)) == 0){
44*5e96a66cSDavid du Colombier 		vtMemFree(p);
45*5e96a66cSDavid du Colombier 		return 1;
46*5e96a66cSDavid du Colombier 	}
47*5e96a66cSDavid du Colombier 	argv[argc] = 0;
48*5e96a66cSDavid du Colombier 
49*5e96a66cSDavid du Colombier 	if(argv[0][0] == '#'){
50*5e96a66cSDavid du Colombier 		vtMemFree(p);
51*5e96a66cSDavid du Colombier 		return 1;
52*5e96a66cSDavid du Colombier 	}
53*5e96a66cSDavid du Colombier 
54*5e96a66cSDavid du Colombier 	vtLock(cbox.lock);
55*5e96a66cSDavid du Colombier 	for(i = 0; i < cbox.hi; i++){
56*5e96a66cSDavid du Colombier 		if(strcmp(cbox.cmd[i].argv0, argv[0]) == 0){
57*5e96a66cSDavid du Colombier 			vtUnlock(cbox.lock);
58*5e96a66cSDavid du Colombier 			if(!(r = cbox.cmd[i].cmd(argc, argv)))
59*5e96a66cSDavid du Colombier 				consPrint("%s\n", vtGetError());
60*5e96a66cSDavid du Colombier 			vtMemFree(p);
61*5e96a66cSDavid du Colombier 			return r;
62*5e96a66cSDavid du Colombier 		}
63*5e96a66cSDavid du Colombier 	}
64*5e96a66cSDavid du Colombier 	vtUnlock(cbox.lock);
65*5e96a66cSDavid du Colombier 
66*5e96a66cSDavid du Colombier 	consPrint("%s: - eh?\n", argv[0]);
67*5e96a66cSDavid du Colombier 	vtMemFree(p);
68*5e96a66cSDavid du Colombier 
69*5e96a66cSDavid du Colombier 	return 0;
70*5e96a66cSDavid du Colombier }
71*5e96a66cSDavid du Colombier 
72*5e96a66cSDavid du Colombier int
cliAddCmd(char * argv0,int (* cmd)(int,char * []))73*5e96a66cSDavid du Colombier cliAddCmd(char* argv0, int (*cmd)(int, char*[]))
74*5e96a66cSDavid du Colombier {
75*5e96a66cSDavid du Colombier 	int i;
76*5e96a66cSDavid du Colombier 	Cmd *opt;
77*5e96a66cSDavid du Colombier 
78*5e96a66cSDavid du Colombier 	vtLock(cbox.lock);
79*5e96a66cSDavid du Colombier 	for(i = 0; i < cbox.hi; i++){
80*5e96a66cSDavid du Colombier 		if(strcmp(argv0, cbox.cmd[i].argv0) == 0){
81*5e96a66cSDavid du Colombier 			vtUnlock(cbox.lock);
82*5e96a66cSDavid du Colombier 			return 0;
83*5e96a66cSDavid du Colombier 		}
84*5e96a66cSDavid du Colombier 	}
85*5e96a66cSDavid du Colombier 	if(i >= cbox.hi){
86*5e96a66cSDavid du Colombier 		if(cbox.hi >= cbox.ncmd){
87*5e96a66cSDavid du Colombier 			cbox.cmd = vtMemRealloc(cbox.cmd,
88*5e96a66cSDavid du Colombier 					(cbox.ncmd+NCmdIncr)*sizeof(Cmd));
89*5e96a66cSDavid du Colombier 			memset(&cbox.cmd[cbox.ncmd], 0, NCmdIncr*sizeof(Cmd));
90*5e96a66cSDavid du Colombier 			cbox.ncmd += NCmdIncr;
91*5e96a66cSDavid du Colombier 		}
92*5e96a66cSDavid du Colombier 	}
93*5e96a66cSDavid du Colombier 
94*5e96a66cSDavid du Colombier 	opt = &cbox.cmd[cbox.hi];
95*5e96a66cSDavid du Colombier 	opt->argv0 = argv0;
96*5e96a66cSDavid du Colombier 	opt->cmd = cmd;
97*5e96a66cSDavid du Colombier 	cbox.hi++;
98*5e96a66cSDavid du Colombier 	vtUnlock(cbox.lock);
99*5e96a66cSDavid du Colombier 
100*5e96a66cSDavid du Colombier 	return 1;
101*5e96a66cSDavid du Colombier }
102*5e96a66cSDavid du Colombier 
103*5e96a66cSDavid du Colombier int
cliInit(void)104*5e96a66cSDavid du Colombier cliInit(void)
105*5e96a66cSDavid du Colombier {
106*5e96a66cSDavid du Colombier 	cbox.lock = vtLockAlloc();
107*5e96a66cSDavid du Colombier 	cbox.cmd = vtMemAllocZ(NCmdIncr*sizeof(Cmd));
108*5e96a66cSDavid du Colombier 	cbox.ncmd = NCmdIncr;
109*5e96a66cSDavid du Colombier 	cbox.hi = 0;
110*5e96a66cSDavid du Colombier 
111*5e96a66cSDavid du Colombier 	return 1;
112*5e96a66cSDavid du Colombier }
113