Ignore:
Timestamp:
Sep 30, 2007, 3:42:50 AM (18 years ago)
Author:
Paul Smedley
Message:

Update trunk to 3.2.0pre1

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/samba/source/smbd/session.c

    r1 r77  
    99   This program is free software; you can redistribute it and/or modify
    1010   it under the terms of the GNU General Public License as published by
    11    the Free Software Foundation; either version 2 of the License, or
     11   the Free Software Foundation; either version 3 of the License, or
    1212   (at your option) any later version.
    1313   
     
    1818   
    1919   You should have received a copy of the GNU General Public License
    20    along with this program; if not, write to the Free Software
    21    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
     20   along with this program.  If not, see <http://www.gnu.org/licenses/>.
    2221*/
    2322
     
    3029#include "includes.h"
    3130
    32 static TDB_CONTEXT *tdb;
    33 
    34 /********************************************************************
    35 ********************************************************************/
     31/********************************************************************
     32********************************************************************/
     33
     34static struct db_context *session_db_ctx(void)
     35{
     36        static struct db_context *ctx;
     37
     38        if (ctx)
     39                return ctx;
     40
     41        ctx = db_open(NULL, lock_path("sessionid.tdb"), 0,
     42                      TDB_CLEAR_IF_FIRST|TDB_DEFAULT,
     43                      O_RDWR | O_CREAT, 0644);
     44        return ctx;
     45}
    3646
    3747BOOL session_init(void)
    3848{
    39         if (tdb)
    40                 return True;
    41 
    42         tdb = tdb_open_log(lock_path("sessionid.tdb"), 0, TDB_CLEAR_IF_FIRST|TDB_DEFAULT,
    43                        O_RDWR | O_CREAT, 0644);
    44         if (!tdb) {
     49        if (session_db_ctx() == NULL) {
    4550                DEBUG(1,("session_init: failed to open sessionid tdb\n"));
    4651                return False;
     
    5661BOOL session_claim(user_struct *vuser)
    5762{
     63        TDB_DATA key, data;
    5864        int i = 0;
    59         TDB_DATA data;
    6065        struct sockaddr sa;
    6166        struct in_addr *client_ip;
    6267        struct sessionid sessionid;
    63         uint32 pid = (uint32)sys_getpid();
    64         TDB_DATA key;           
     68        struct server_id pid = procid_self();
    6569        fstring keystr;
    6670        char * hostname;
    67         int tdb_store_flag;  /* If using utmp, we do an inital 'lock hold' store,
    68                                 but we don't need this if we are just using the
    69                                 (unique) pid/vuid combination */
     71        struct db_context *ctx;
     72        struct db_record *rec;
     73        NTSTATUS status;
    7074
    7175        vuser->session_keystr = NULL;
     
    7781        }
    7882
    79         if (!session_init())
    80                 return False;
     83        if (!(ctx = session_db_ctx())) {
     84                return False;
     85        }
    8186
    8287        ZERO_STRUCT(sessionid);
     
    8691
    8792        if (lp_utmp()) {
     93
    8894                for (i=1;i<MAX_SESSION_ID;i++) {
    89                         slprintf(keystr, sizeof(keystr)-1, "ID/%d", i);
    90                         key.dptr = keystr;
    91                         key.dsize = strlen(keystr)+1;
    92                        
    93                         if (tdb_store(tdb, key, data, TDB_INSERT) == 0) break;
     95
     96                        /*
     97                         * This is very inefficient and needs fixing -- vl
     98                         */
     99
     100                        struct server_id sess_pid;
     101
     102                        snprintf(keystr, sizeof(keystr), "ID/%d", i);
     103                        key = string_term_tdb_data(keystr);
     104
     105                        rec = ctx->fetch_locked(ctx, NULL, key);
     106
     107                        if (rec == NULL) {
     108                                DEBUG(1, ("Could not lock \"%s\"\n", keystr));
     109                                return False;
     110                        }
     111
     112                        if (rec->value.dsize != sizeof(sessionid)) {
     113                                DEBUG(1, ("Re-using invalid record\n"));
     114                                break;
     115                        }
     116
     117                        sess_pid = ((struct sessionid *)rec->value.dptr)->pid;
     118
     119                        if (!process_exists(sess_pid)) {
     120                                DEBUG(5, ("%s has died -- re-using session\n",
     121                                          procid_str_static(&sess_pid)));
     122                                break;
     123                        }
     124
     125                        TALLOC_FREE(rec);
    94126                }
    95127               
    96128                if (i == MAX_SESSION_ID) {
    97                         DEBUG(1,("session_claim: out of session IDs (max is %d)\n",
    98                                  MAX_SESSION_ID));
     129                        SMB_ASSERT(rec == NULL);
     130                        DEBUG(1,("session_claim: out of session IDs "
     131                                 "(max is %d)\n", MAX_SESSION_ID));
    99132                        return False;
    100133                }
    101                 slprintf(sessionid.id_str, sizeof(sessionid.id_str)-1, SESSION_UTMP_TEMPLATE, i);
    102                 tdb_store_flag = TDB_MODIFY;
     134
     135                snprintf(sessionid.id_str, sizeof(sessionid.id_str),
     136                         SESSION_UTMP_TEMPLATE, i);
    103137        } else
    104138        {
    105                 slprintf(keystr, sizeof(keystr)-1, "ID/%lu/%u",
    106                          (long unsigned int)sys_getpid(),
    107                          vuser->vuid);
    108                 slprintf(sessionid.id_str, sizeof(sessionid.id_str)-1,
     139                snprintf(keystr, sizeof(keystr), "ID/%s/%u",
     140                         procid_str_static(&pid), vuser->vuid);
     141                key = string_term_tdb_data(keystr);
     142
     143                rec = ctx->fetch_locked(ctx, NULL, key);
     144
     145                if (rec == NULL) {
     146                        DEBUG(1, ("Could not lock \"%s\"\n", keystr));
     147                        return False;
     148                }
     149
     150                snprintf(sessionid.id_str, sizeof(sessionid.id_str),
    109151                         SESSION_TEMPLATE, (long unsigned int)sys_getpid(),
    110152                         vuser->vuid);
    111 
    112                 key.dptr = keystr;
    113                 key.dsize = strlen(keystr)+1;
    114                        
    115                 tdb_store_flag = TDB_REPLACE;
    116         }
     153        }
     154
     155        SMB_ASSERT(rec != NULL);
    117156
    118157        /* If 'hostname lookup' == yes, then do the DNS lookup.  This is
     
    139178        client_ip = client_inaddr(&sa);
    140179
    141         if (!smb_pam_claim_session(sessionid.username, sessionid.id_str, sessionid.hostname)) {
     180        if (!smb_pam_claim_session(sessionid.username, sessionid.id_str,
     181                                   sessionid.hostname)) {
    142182                DEBUG(1,("pam_session rejected the session for %s [%s]\n",
    143183                                sessionid.username, sessionid.id_str));
    144                 if (tdb_store_flag == TDB_MODIFY) {
    145                         tdb_delete(tdb, key);
    146                 }
    147                 return False;
    148         }
    149 
    150         data.dptr = (char *)&sessionid;
     184
     185                TALLOC_FREE(rec);
     186                return False;
     187        }
     188
     189        data.dptr = (uint8 *)&sessionid;
    151190        data.dsize = sizeof(sessionid);
    152         if (tdb_store(tdb, key, data, tdb_store_flag) != 0) {
    153                 DEBUG(1,("session_claim: unable to create session id record\n"));
     191
     192        status = rec->store(rec, data, TDB_REPLACE);
     193
     194        TALLOC_FREE(rec);
     195
     196        if (!NT_STATUS_IS_OK(status)) {
     197                DEBUG(1,("session_claim: unable to create session id "
     198                         "record: %s\n", nt_errstr(status)));
    154199                return False;
    155200        }
     
    161206        }
    162207
    163         vuser->session_keystr = SMB_STRDUP(keystr);
     208        vuser->session_keystr = talloc_strdup(vuser, keystr);
    164209        if (!vuser->session_keystr) {
    165                 DEBUG(0, ("session_claim:  strdup() failed for session_keystr\n"));
     210                DEBUG(0, ("session_claim:  talloc_strdup() failed for session_keystr\n"));
    166211                return False;
    167212        }
     
    175220void session_yield(user_struct *vuser)
    176221{
    177         TDB_DATA dbuf;
     222        TDB_DATA key;
    178223        struct sessionid sessionid;
    179224        struct in_addr *client_ip;
    180         TDB_DATA key;
    181 
    182         if (!tdb) return;
     225        struct db_context *ctx;
     226        struct db_record *rec;
     227
     228        if (!(ctx = session_db_ctx())) return;
    183229
    184230        if (!vuser->session_keystr) {
     
    186232        }
    187233
    188         key.dptr = vuser->session_keystr;
    189         key.dsize = strlen(vuser->session_keystr)+1;
    190 
    191         dbuf = tdb_fetch(tdb, key);
    192 
    193         if (dbuf.dsize != sizeof(sessionid))
     234        key = string_term_tdb_data(vuser->session_keystr);
     235
     236        if (!(rec = ctx->fetch_locked(ctx, NULL, key))) {
    194237                return;
    195 
    196         memcpy(&sessionid, dbuf.dptr, sizeof(sessionid));
     238        }
     239
     240        if (rec->value.dsize != sizeof(sessionid))
     241                return;
     242
     243        memcpy(&sessionid, rec->value.dptr, sizeof(sessionid));
    197244
    198245        client_ip = interpret_addr2(sessionid.ip_addr);
    199 
    200         SAFE_FREE(dbuf.dptr);
    201246
    202247        if (lp_utmp()) {
     
    206251        }
    207252
    208         smb_pam_close_session(sessionid.username, sessionid.id_str, sessionid.hostname);
    209 
    210         tdb_delete(tdb, key);
    211 }
    212 
    213 /********************************************************************
    214 ********************************************************************/
    215 
    216 BOOL session_traverse(int (*fn)(TDB_CONTEXT *, TDB_DATA, TDB_DATA, void *),
    217                       void *state)
    218 {
    219         if (!session_init()) {
     253        smb_pam_close_session(sessionid.username, sessionid.id_str,
     254                              sessionid.hostname);
     255
     256        rec->delete_rec(rec);
     257
     258        TALLOC_FREE(rec);
     259}
     260
     261/********************************************************************
     262********************************************************************/
     263
     264static BOOL session_traverse(int (*fn)(struct db_record *db,
     265                                       void *private_data),
     266                             void *private_data)
     267{
     268        struct db_context *ctx;
     269
     270        if (!(ctx = session_db_ctx())) {
    220271                DEBUG(3, ("No tdb opened\n"));
    221272                return False;
    222273        }
    223274
    224         tdb_traverse(tdb, fn, state);
     275        ctx->traverse_read(ctx, fn, private_data);
    225276        return True;
    226277}
     
    230281
    231282struct session_list {
     283        TALLOC_CTX *mem_ctx;
    232284        int count;
    233285        struct sessionid *sessions;
    234286};
    235287
    236 static int gather_sessioninfo(TDB_CONTEXT *stdb, TDB_DATA kbuf, TDB_DATA dbuf, void *state)
    237 {
    238         uint32 i;       
     288static int gather_sessioninfo(struct db_record *rec, void *state)
     289{
    239290        struct session_list *sesslist = (struct session_list *) state;
    240         const struct sessionid *current = (const struct sessionid *) dbuf.dptr;
    241 
    242         i = sesslist->count;
    243        
    244         sesslist->sessions = SMB_REALLOC_ARRAY(sesslist->sessions, struct sessionid, i+1);
     291        const struct sessionid *current =
     292                (const struct sessionid *) rec->value.dptr;
     293
     294        sesslist->sessions = TALLOC_REALLOC_ARRAY(
     295                sesslist->mem_ctx, sesslist->sessions, struct sessionid,
     296                sesslist->count+1);
     297
    245298        if (!sesslist->sessions) {
    246299                sesslist->count = 0;
     
    248301        }
    249302
    250         memcpy(&sesslist->sessions[i], current, sizeof(struct sessionid));
     303        memcpy(&sesslist->sessions[sesslist->count], current,
     304               sizeof(struct sessionid));
     305
    251306        sesslist->count++;
    252307
     
    260315********************************************************************/
    261316
    262 int list_sessions(struct sessionid **session_list)
     317int list_sessions(TALLOC_CTX *mem_ctx, struct sessionid **session_list)
    263318{
    264319        struct session_list sesslist;
    265320
     321        sesslist.mem_ctx = mem_ctx;
    266322        sesslist.count = 0;
    267323        sesslist.sessions = NULL;
Note: See TracChangeset for help on using the changeset viewer.