svc_auth.c revision 156090
174462Salfred/* $NetBSD: svc_auth.c,v 1.12 2000/07/06 03:10:35 christos Exp $ */ 274462Salfred 31901Swollman/* 41901Swollman * Sun RPC is a product of Sun Microsystems, Inc. and is provided for 51901Swollman * unrestricted use provided that this legend is included on all tape 61901Swollman * media and as a part of the software program in whole or part. Users 71901Swollman * may copy or modify Sun RPC without charge, but are not authorized 81901Swollman * to license or distribute it to anyone else except as part of a product or 91901Swollman * program developed by the user. 1026221Swpaul * 111901Swollman * SUN RPC IS PROVIDED AS IS WITH NO WARRANTIES OF ANY KIND INCLUDING THE 121901Swollman * WARRANTIES OF DESIGN, MERCHANTIBILITY AND FITNESS FOR A PARTICULAR 131901Swollman * PURPOSE, OR ARISING FROM A COURSE OF DEALING, USAGE OR TRADE PRACTICE. 1426221Swpaul * 151901Swollman * Sun RPC is provided with no support and without any obligation on the 161901Swollman * part of Sun Microsystems, Inc. to assist in its use, correction, 171901Swollman * modification or enhancement. 1826221Swpaul * 191901Swollman * SUN MICROSYSTEMS, INC. SHALL HAVE NO LIABILITY WITH RESPECT TO THE 201901Swollman * INFRINGEMENT OF COPYRIGHTS, TRADE SECRETS OR ANY PATENTS BY SUN RPC 211901Swollman * OR ANY PART THEREOF. 2226221Swpaul * 231901Swollman * In no event will Sun Microsystems, Inc. be liable for any lost revenue 241901Swollman * or profits or other special, indirect and consequential damages, even if 251901Swollman * Sun has been advised of the possibility of such damages. 2626221Swpaul * 271901Swollman * Sun Microsystems, Inc. 281901Swollman * 2550 Garcia Avenue 291901Swollman * Mountain View, California 94043 301901Swollman */ 3126221Swpaul/* 3226221Swpaul * Copyright (c) 1986-1991 by Sun Microsystems Inc. 3326221Swpaul */ 341901Swollman 35136581Sobrien#if defined(LIBC_SCCS) && !defined(lint) 36136581Sobrien#ident "@(#)svc_auth.c 1.16 94/04/24 SMI" 3726221Swpaulstatic char sccsid[] = "@(#)svc_auth.c 1.26 89/02/07 Copyr 1984 Sun Micro"; 381901Swollman#endif 3992990Sobrien#include <sys/cdefs.h> 4092990Sobrien__FBSDID("$FreeBSD: head/lib/libc/rpc/svc_auth.c 156090 2006-02-27 22:10:59Z deischen $"); 411901Swollman 421901Swollman/* 4326221Swpaul * svc_auth.c, Server-side rpc authenticator interface. 441901Swollman * 451901Swollman */ 461901Swollman 4775094Siedowse#include "namespace.h" 4874462Salfred#include "reentrant.h" 4974462Salfred#include <sys/types.h> 5074462Salfred#include <rpc/rpc.h> 5126221Swpaul#include <stdlib.h> 5274462Salfred#include "un-namespace.h" 53156090Sdeischen#include "mt_misc.h" 541901Swollman 551901Swollman/* 568870Srgrimes * svcauthsw is the bdevsw of server side authentication. 578870Srgrimes * 581901Swollman * Server side authenticators are called from authenticate by 591901Swollman * using the client auth struct flavor field to index into svcauthsw. 608870Srgrimes * The server auth flavors must implement a routine that looks 618870Srgrimes * like: 628870Srgrimes * 631901Swollman * enum auth_stat 641901Swollman * flavorx_auth(rqst, msg) 6574462Salfred * struct svc_req *rqst; 6674462Salfred * struct rpc_msg *msg; 671901Swollman * 681901Swollman */ 691901Swollman 7026221Swpaul/* declarations to allow servers to specify new authentication flavors */ 7126221Swpaulstruct authsvc { 7226221Swpaul int flavor; 7392905Sobrien enum auth_stat (*handler)(struct svc_req *, struct rpc_msg *); 7426221Swpaul struct authsvc *next; 751901Swollman}; 7626221Swpaulstatic struct authsvc *Auths = NULL; 771901Swollman 781901Swollman/* 791901Swollman * The call rpc message, msg has been obtained from the wire. The msg contains 801901Swollman * the raw form of credentials and verifiers. authenticate returns AUTH_OK 811901Swollman * if the msg is successfully authenticated. If AUTH_OK then the routine also 821901Swollman * does the following things: 831901Swollman * set rqst->rq_xprt->verf to the appropriate response verifier; 841901Swollman * sets rqst->rq_client_cred to the "cooked" form of the credentials. 851901Swollman * 861901Swollman * NB: rqst->rq_cxprt->verf must be pre-alloctaed; 871901Swollman * its length is set appropriately. 881901Swollman * 891901Swollman * The caller still owns and is responsible for msg->u.cmb.cred and 901901Swollman * msg->u.cmb.verf. The authentication system retains ownership of 911901Swollman * rqst->rq_client_cred, the cooked credentials. 921901Swollman * 931901Swollman * There is an assumption that any flavour less than AUTH_NULL is 941901Swollman * invalid. 951901Swollman */ 961901Swollmanenum auth_stat 971901Swollman_authenticate(rqst, msg) 9874462Salfred struct svc_req *rqst; 991901Swollman struct rpc_msg *msg; 1001901Swollman{ 10174462Salfred int cred_flavor; 10274462Salfred struct authsvc *asp; 10374462Salfred enum auth_stat dummy; 1041901Swollman 10574462Salfred/* VARIABLES PROTECTED BY authsvc_lock: asp, Auths */ 10674462Salfred 1071901Swollman rqst->rq_cred = msg->rm_call.cb_cred; 1081901Swollman rqst->rq_xprt->xp_verf.oa_flavor = _null_auth.oa_flavor; 1091901Swollman rqst->rq_xprt->xp_verf.oa_length = 0; 1101901Swollman cred_flavor = rqst->rq_cred.oa_flavor; 11126221Swpaul switch (cred_flavor) { 11226221Swpaul case AUTH_NULL: 11374462Salfred dummy = _svcauth_null(rqst, msg); 11474462Salfred return (dummy); 11574462Salfred case AUTH_SYS: 11674462Salfred dummy = _svcauth_unix(rqst, msg); 11774462Salfred return (dummy); 11826221Swpaul case AUTH_SHORT: 11974462Salfred dummy = _svcauth_short(rqst, msg); 12074462Salfred return (dummy); 12126221Swpaul#ifdef DES_BUILTIN 12226221Swpaul case AUTH_DES: 12374462Salfred dummy = _svcauth_des(rqst, msg); 12474462Salfred return (dummy); 12526221Swpaul#endif 12674462Salfred default: 12774462Salfred break; 1281901Swollman } 1291901Swollman 13026221Swpaul /* flavor doesn't match any of the builtin types, so try new ones */ 13174462Salfred mutex_lock(&authsvc_lock); 13226221Swpaul for (asp = Auths; asp; asp = asp->next) { 13326221Swpaul if (asp->flavor == cred_flavor) { 13426221Swpaul enum auth_stat as; 13526221Swpaul 13626221Swpaul as = (*asp->handler)(rqst, msg); 13774462Salfred mutex_unlock(&authsvc_lock); 13826221Swpaul return (as); 13926221Swpaul } 14026221Swpaul } 14174462Salfred mutex_unlock(&authsvc_lock); 14226221Swpaul 1431901Swollman return (AUTH_REJECTEDCRED); 1441901Swollman} 1451901Swollman 14626221Swpaul/*ARGSUSED*/ 1471901Swollmanenum auth_stat 14826221Swpaul_svcauth_null(rqst, msg) 14926221Swpaul struct svc_req *rqst; 15026221Swpaul struct rpc_msg *msg; 1511901Swollman{ 1521901Swollman return (AUTH_OK); 1531901Swollman} 15426221Swpaul 15526221Swpaul/* 15626221Swpaul * Allow the rpc service to register new authentication types that it is 15726221Swpaul * prepared to handle. When an authentication flavor is registered, 15826221Swpaul * the flavor is checked against already registered values. If not 15926221Swpaul * registered, then a new Auths entry is added on the list. 16026221Swpaul * 16126221Swpaul * There is no provision to delete a registration once registered. 16226221Swpaul * 16326221Swpaul * This routine returns: 16426221Swpaul * 0 if registration successful 16526221Swpaul * 1 if flavor already registered 16626221Swpaul * -1 if can't register (errno set) 16726221Swpaul */ 16826221Swpaul 16926221Swpaulint 17026221Swpaulsvc_auth_reg(cred_flavor, handler) 17174462Salfred int cred_flavor; 17292905Sobrien enum auth_stat (*handler)(struct svc_req *, struct rpc_msg *); 17326221Swpaul{ 17474462Salfred struct authsvc *asp; 17526221Swpaul 17626221Swpaul switch (cred_flavor) { 17726221Swpaul case AUTH_NULL: 17874462Salfred case AUTH_SYS: 17926221Swpaul case AUTH_SHORT: 18026221Swpaul#ifdef DES_BUILTIN 18126221Swpaul case AUTH_DES: 18226221Swpaul#endif 18326221Swpaul /* already registered */ 18426221Swpaul return (1); 18526221Swpaul 18626221Swpaul default: 18774462Salfred mutex_lock(&authsvc_lock); 18826221Swpaul for (asp = Auths; asp; asp = asp->next) { 18926221Swpaul if (asp->flavor == cred_flavor) { 19026221Swpaul /* already registered */ 19174462Salfred mutex_unlock(&authsvc_lock); 19226221Swpaul return (1); 19326221Swpaul } 19426221Swpaul } 19526221Swpaul 19626221Swpaul /* this is a new one, so go ahead and register it */ 19774462Salfred asp = mem_alloc(sizeof (*asp)); 19826221Swpaul if (asp == NULL) { 19974462Salfred mutex_unlock(&authsvc_lock); 20026221Swpaul return (-1); 20126221Swpaul } 20226221Swpaul asp->flavor = cred_flavor; 20326221Swpaul asp->handler = handler; 20426221Swpaul asp->next = Auths; 20526221Swpaul Auths = asp; 20674462Salfred mutex_unlock(&authsvc_lock); 20726221Swpaul break; 20826221Swpaul } 20926221Swpaul return (0); 21026221Swpaul} 211