2003-08-13 05:53:07 +04:00
/*
Unix SMB / CIFS implementation .
Password and authentication handling
Copyright ( C ) Andrew Tridgell 1992 - 1998
This program is free software ; you can redistribute it and / or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation ; either version 2 of the License , or
( at your option ) any later version .
This program is distributed in the hope that it will be useful ,
but WITHOUT ANY WARRANTY ; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
GNU General Public License for more details .
You should have received a copy of the GNU General Public License
along with this program ; if not , write to the Free Software
Foundation , Inc . , 675 Mass Ave , Cambridge , MA 0213 9 , USA .
*/
# include "includes.h"
/****************************************************************************
check if a uid has been validated , and return an pointer to the user_struct
if it has . NULL if not . vuid is biased by an offset . This allows us to
tell random client vuid ' s ( normally zero ) from valid vuids .
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2004-07-14 16:44:31 +04:00
struct smbsrv_session * smbsrv_session_find ( struct smbsrv_connection * smb_conn , uint16_t vuid )
2003-08-13 05:53:07 +04:00
{
2004-07-14 16:44:31 +04:00
struct smbsrv_session * sess ;
2003-08-13 05:53:07 +04:00
int count = 0 ;
if ( vuid = = UID_FIELD_INVALID )
return NULL ;
2004-07-14 16:44:31 +04:00
for ( sess = smb_conn - > sessions . session_list ; sess ; sess = sess - > next , count + + ) {
if ( vuid = = sess - > vuid ) {
2003-08-13 05:53:07 +04:00
if ( count > 10 ) {
2004-07-14 16:44:31 +04:00
DLIST_PROMOTE ( smb_conn - > sessions . session_list , sess ) ;
2003-08-13 05:53:07 +04:00
}
2004-07-14 16:44:31 +04:00
return sess ;
2003-08-13 05:53:07 +04:00
}
}
return NULL ;
}
/****************************************************************************
invalidate a uid
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2004-07-14 16:44:31 +04:00
void smbsrv_invalidate_vuid ( struct smbsrv_connection * smb_conn , uint16_t vuid )
2003-08-13 05:53:07 +04:00
{
2004-07-14 16:44:31 +04:00
struct smbsrv_session * sess = smbsrv_session_find ( smb_conn , vuid ) ;
2003-08-13 05:53:07 +04:00
2004-07-14 16:44:31 +04:00
if ( sess = = NULL )
2003-08-13 05:53:07 +04:00
return ;
2004-05-02 12:45:00 +04:00
2004-07-14 16:44:31 +04:00
DLIST_REMOVE ( smb_conn - > sessions . session_list , sess ) ;
2003-08-13 05:53:07 +04:00
/* clear the vuid from the 'cache' on each connection, and
from the vuid ' owner ' of connections */
/* REWRITE: conn_clear_vuid_cache(smb, vuid); */
2004-07-14 16:44:31 +04:00
smb_conn - > sessions . num_validated_vuids - - ;
2003-08-13 05:53:07 +04:00
}
/****************************************************************************
invalidate all vuid entries for this process
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
2004-07-14 16:44:31 +04:00
void smbsrv_invalidate_all_vuids ( struct smbsrv_connection * smb_conn )
2003-08-13 05:53:07 +04:00
{
2004-07-14 16:44:31 +04:00
struct smbsrv_session * sess , * next = NULL ;
2003-08-13 05:53:07 +04:00
2004-07-14 16:44:31 +04:00
for ( sess = smb_conn - > sessions . session_list ; sess ; sess = next ) {
next = sess - > next ;
2003-08-13 05:53:07 +04:00
2004-07-14 16:44:31 +04:00
smbsrv_invalidate_vuid ( smb_conn , sess - > vuid ) ;
2003-08-13 05:53:07 +04:00
}
}
/**
* register that a valid login has been performed , establish ' session ' .
2004-08-11 20:16:28 +04:00
* @ param session_info The token returned from the authentication process ( if the authentication has completed )
2003-08-13 05:53:07 +04:00
* ( now ' owned ' by register_vuid )
*
2004-05-02 12:45:00 +04:00
* @ param smb_name The untranslated name of the user
*
2003-08-13 05:53:07 +04:00
* @ return Newly allocated vuid , biased by an offset . ( This allows us to
* tell random client vuid ' s ( normally zero ) from valid vuids . )
*
*/
2004-07-14 16:44:31 +04:00
uint16_t smbsrv_register_session ( struct smbsrv_connection * smb_conn ,
2004-08-11 20:16:28 +04:00
struct auth_session_info * session_info ,
struct gensec_security * gensec_ctx )
2003-08-13 05:53:07 +04:00
{
2004-07-14 16:44:31 +04:00
struct smbsrv_session * sess = NULL ;
2003-08-13 05:53:07 +04:00
2004-09-08 09:39:06 +04:00
sess = talloc_p ( smb_conn , struct smbsrv_session ) ;
2004-07-14 16:44:31 +04:00
if ( sess = = NULL ) {
DEBUG ( 0 , ( " talloc_p(smb_conn->mem_ctx, struct smbsrv_session) failed \n " ) ) ;
2003-08-13 05:53:07 +04:00
return UID_FIELD_INVALID ;
2004-07-14 16:44:31 +04:00
}
2003-08-13 05:53:07 +04:00
2004-07-14 16:44:31 +04:00
ZERO_STRUCTP ( sess ) ;
sess - > vuid = UID_FIELD_INVALID ;
2003-08-13 05:53:07 +04:00
2004-07-14 16:44:31 +04:00
/* Ensure no vuid gets registered in share level security. */
/* TODO: replace lp_security with a flag in smbsrv_connection */
if ( lp_security ( ) = = SEC_SHARE )
return sess - > vuid ;
2003-08-13 05:53:07 +04:00
2004-07-14 16:44:31 +04:00
/* Limit allowed vuids to 16bits - VUID_OFFSET. */
if ( smb_conn - > sessions . num_validated_vuids > = 0xFFFF - VUID_OFFSET )
return sess - > vuid ;
2003-08-13 05:53:07 +04:00
/* Allocate a free vuid. Yes this is a linear search... :-) */
2004-07-14 16:44:31 +04:00
while ( smbsrv_session_find ( smb_conn , smb_conn - > sessions . next_vuid ) ! = NULL ) {
smb_conn - > sessions . next_vuid + + ;
2003-08-13 05:53:07 +04:00
/* Check for vuid wrap. */
2004-07-14 16:44:31 +04:00
if ( smb_conn - > sessions . next_vuid = = UID_FIELD_INVALID )
smb_conn - > sessions . next_vuid = VUID_OFFSET ;
2003-08-13 05:53:07 +04:00
}
DEBUG ( 10 , ( " register_vuid: allocated vuid = %u \n " ,
2004-07-14 16:44:31 +04:00
( uint_t ) smb_conn - > sessions . next_vuid ) ) ;
2003-08-13 05:53:07 +04:00
2004-07-14 16:44:31 +04:00
sess - > vuid = smb_conn - > sessions . next_vuid ;
smb_conn - > sessions . next_vuid + + ;
smb_conn - > sessions . num_validated_vuids + + ;
2003-08-13 05:53:07 +04:00
/* use this to keep tabs on all our info from the authentication */
2004-10-25 08:19:02 +04:00
if ( session_info ) {
sess - > session_info = talloc_reference ( sess , session_info ) ;
}
if ( gensec_ctx ) {
sess - > gensec_ctx = talloc_reference ( sess , gensec_ctx ) ;
}
2004-07-14 16:44:31 +04:00
sess - > smb_conn = smb_conn ;
DLIST_ADD ( smb_conn - > sessions . session_list , sess ) ;
return sess - > vuid ;
2003-08-13 05:53:07 +04:00
}