mirror of
https://github.com/opnsense/src.git
synced 2026-06-11 09:41:03 -04:00
rpcsec_gss.c: Avoid panics in clnt_nl_call()
When rpc_gss_init() calls gssd upcall functions like gssd_import_name(), clnt_nl_call() gets calls. clnt_nl_call() requires that the currect vnet be set up. The calling sequence looks something like: rpc_gss_init()->gssd_import_name()->gssd_import_name_1()-> clnt_call_private()->clnt_nl_call() (The call to rpc_gss_init() can happen from various places, such as nfs_getauth() and clnt_vc_call().) rpc_gss_init() does not know what socket is being used for NFS client->server RPCs and may be called from various places when any VOP_xxx()->RPC call is made. As such, the calling thread might be running within a jail. However, the gssd upcalls for the NFS client must always be done to the gssd running outside of any jails. This patch sets the CURVNET to vnet0 in rpc_gss_init() to fix the problem, since that is the vnet that always should be used. This must somehow be changed if NFS mounts in vnet jails is enabled. Reviewed by: glebius Differential Revision: https://reviews.freebsd.org/D51086
This commit is contained in:
parent
e46c15a0f8
commit
a28a65140f
1 changed files with 14 additions and 0 deletions
|
|
@ -67,6 +67,7 @@
|
|||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/hash.h>
|
||||
#include <sys/jail.h>
|
||||
#include <sys/kernel.h>
|
||||
#include <sys/kobj.h>
|
||||
#include <sys/lock.h>
|
||||
|
|
@ -771,6 +772,17 @@ rpc_gss_init(AUTH *auth, rpc_gss_options_ret_t *options_ret)
|
|||
gd->gd_cred.gc_proc = RPCSEC_GSS_INIT;
|
||||
gd->gd_cred.gc_seq = 0;
|
||||
|
||||
/*
|
||||
* XXX Threads from inside jails can get here via calls
|
||||
* to clnt_vc_call()->AUTH_REFRESH()->rpc_gss_refresh()
|
||||
* but the NFS mount is always done outside of the
|
||||
* jails in vnet0. Since the thread credentials won't
|
||||
* necessarily have cr_prison == vnet0 and this function
|
||||
* has no access to the socket, using vnet0 seems the
|
||||
* only option. This is broken if NFS mounts are enabled
|
||||
* within vnet prisons.
|
||||
*/
|
||||
KGSS_CURVNET_SET_QUIET(vnet0);
|
||||
/*
|
||||
* For KerberosV, if there is a client principal name, that implies
|
||||
* that this is a host based initiator credential in the default
|
||||
|
|
@ -994,12 +1006,14 @@ out:
|
|||
gss_delete_sec_context(&min_stat, &gd->gd_ctx,
|
||||
GSS_C_NO_BUFFER);
|
||||
}
|
||||
KGSS_CURVNET_RESTORE();
|
||||
mtx_lock(&gd->gd_lock);
|
||||
gd->gd_state = RPCSEC_GSS_START;
|
||||
wakeup(gd);
|
||||
mtx_unlock(&gd->gd_lock);
|
||||
return (FALSE);
|
||||
}
|
||||
KGSS_CURVNET_RESTORE();
|
||||
|
||||
mtx_lock(&gd->gd_lock);
|
||||
gd->gd_state = RPCSEC_GSS_ESTABLISHED;
|
||||
|
|
|
|||
Loading…
Reference in a new issue