xref: /plan9/sys/src/libauth/auth_respond.c (revision 2ebbfa15057a80d5ffc355d10c2a61bb0ac12c16)
19a747e4fSDavid du Colombier #include <u.h>
29a747e4fSDavid du Colombier #include <libc.h>
39a747e4fSDavid du Colombier #include <auth.h>
49a747e4fSDavid du Colombier #include <authsrv.h>
59a747e4fSDavid du Colombier #include "authlocal.h"
69a747e4fSDavid du Colombier 
79a747e4fSDavid du Colombier enum {
89a747e4fSDavid du Colombier 	ARgiveup = 100,
99a747e4fSDavid du Colombier };
109a747e4fSDavid du Colombier 
119a747e4fSDavid du Colombier static int
dorpc(AuthRpc * rpc,char * verb,char * val,int len,AuthGetkey * getkey)129a747e4fSDavid du Colombier dorpc(AuthRpc *rpc, char *verb, char *val, int len, AuthGetkey *getkey)
139a747e4fSDavid du Colombier {
149a747e4fSDavid du Colombier 	int ret;
159a747e4fSDavid du Colombier 
169a747e4fSDavid du Colombier 	for(;;){
179a747e4fSDavid du Colombier 		if((ret = auth_rpc(rpc, verb, val, len)) != ARneedkey && ret != ARbadkey)
189a747e4fSDavid du Colombier 			return ret;
199a747e4fSDavid du Colombier 		if(getkey == nil)
209a747e4fSDavid du Colombier 			return ARgiveup;	/* don't know how */
219a747e4fSDavid du Colombier 		if((*getkey)(rpc->arg) < 0)
229a747e4fSDavid du Colombier 			return ARgiveup;	/* user punted */
239a747e4fSDavid du Colombier 	}
249a747e4fSDavid du Colombier }
259a747e4fSDavid du Colombier 
269a747e4fSDavid du Colombier int
auth_respond(void * chal,uint nchal,char * user,uint nuser,void * resp,uint nresp,AuthGetkey * getkey,char * fmt,...)279a747e4fSDavid du Colombier auth_respond(void *chal, uint nchal, char *user, uint nuser, void *resp, uint nresp, AuthGetkey *getkey, char *fmt, ...)
289a747e4fSDavid du Colombier {
299a747e4fSDavid du Colombier 	char *p, *s;
309a747e4fSDavid du Colombier 	va_list arg;
319a747e4fSDavid du Colombier 	int afd;
329a747e4fSDavid du Colombier 	AuthRpc *rpc;
339a747e4fSDavid du Colombier 	Attr *a;
349a747e4fSDavid du Colombier 
359a747e4fSDavid du Colombier 	if((afd = open("/mnt/factotum/rpc", ORDWR)) < 0)
369a747e4fSDavid du Colombier 		return -1;
379a747e4fSDavid du Colombier 
389a747e4fSDavid du Colombier 	if((rpc = auth_allocrpc(afd)) == nil){
399a747e4fSDavid du Colombier 		close(afd);
409a747e4fSDavid du Colombier 		return -1;
419a747e4fSDavid du Colombier 	}
429a747e4fSDavid du Colombier 
439a747e4fSDavid du Colombier 	quotefmtinstall();	/* just in case */
449a747e4fSDavid du Colombier 	va_start(arg, fmt);
459a747e4fSDavid du Colombier 	p = vsmprint(fmt, arg);
469a747e4fSDavid du Colombier 	va_end(arg);
479a747e4fSDavid du Colombier 
489a747e4fSDavid du Colombier 	if(p==nil
499a747e4fSDavid du Colombier 	|| dorpc(rpc, "start", p, strlen(p), getkey) != ARok
509a747e4fSDavid du Colombier 	|| dorpc(rpc, "write", chal, nchal, getkey) != ARok
519a747e4fSDavid du Colombier 	|| dorpc(rpc, "read", nil, 0, getkey) != ARok){
529a747e4fSDavid du Colombier 		free(p);
539a747e4fSDavid du Colombier 		close(afd);
549a747e4fSDavid du Colombier 		auth_freerpc(rpc);
559a747e4fSDavid du Colombier 		return -1;
569a747e4fSDavid du Colombier 	}
579a747e4fSDavid du Colombier 	free(p);
589a747e4fSDavid du Colombier 
599a747e4fSDavid du Colombier 	if(rpc->narg < nresp)
609a747e4fSDavid du Colombier 		nresp = rpc->narg;
619a747e4fSDavid du Colombier 	memmove(resp, rpc->arg, nresp);
629a747e4fSDavid du Colombier 
639a747e4fSDavid du Colombier 	if((a = auth_attr(rpc)) != nil
64*2ebbfa15SDavid du Colombier 	&& (s = _strfindattr(a, "user")) != nil && strlen(s) < nuser)
659a747e4fSDavid du Colombier 		strcpy(user, s);
669a747e4fSDavid du Colombier 	else if(nuser > 0)
679a747e4fSDavid du Colombier 		user[0] = '\0';
689a747e4fSDavid du Colombier 
699a747e4fSDavid du Colombier 	_freeattr(a);
709a747e4fSDavid du Colombier 	close(afd);
719a747e4fSDavid du Colombier 	auth_freerpc(rpc);
729a747e4fSDavid du Colombier 	return nresp;
739a747e4fSDavid du Colombier }
74