Ignore:
Timestamp:
Nov 24, 2016, 1:14:11 PM (9 years ago)
Author:
Silvan Scherrer
Message:

Samba Server: update vendor to version 4.4.3

File:
1 edited

Legend:

Unmodified
Added
Removed
  • vendor/current/source3/smbd/blocking.c

    r746 r988  
    2525#undef DBGC_CLASS
    2626#define DBGC_CLASS DBGC_LOCKING
    27 
    28 /****************************************************************************
    29  Determine if this is a secondary element of a chained SMB.
    30   **************************************************************************/
    3127
    3228static void received_unlock_msg(struct messaging_context *msg,
     
    3632                                DATA_BLOB *data);
    3733
    38 void brl_timeout_fn(struct event_context *event_ctx,
    39                            struct timed_event *te,
     34void brl_timeout_fn(struct tevent_context *event_ctx,
     35                           struct tevent_timer *te,
    4036                           struct timeval now,
    4137                           void *private_data)
     
    112108        }
    113109
    114         /* 
     110        /*
    115111         to account for unclean shutdowns by clients we need a
    116112         maximum timeout that we use for checking pending locks. If
     
    140136        }
    141137
    142         sconn->smb1.locks.brl_timeout = event_add_timed(smbd_event_context(),
    143                                                         NULL, next_timeout,
    144                                                         brl_timeout_fn, sconn);
     138        sconn->smb1.locks.brl_timeout = tevent_add_timer(sconn->ev_ctx,
     139                                                         NULL, next_timeout,
     140                                                         brl_timeout_fn, sconn);
    145141        if (sconn->smb1.locks.brl_timeout == NULL) {
    146142                return False;
     
    209205                blr->expire_time.tv_usec = 0; /* Never expire. */
    210206        } else {
    211                 blr->expire_time = timeval_current_ofs(lock_timeout/1000,
    212                                         (lock_timeout % 1000) * 1000);
     207                blr->expire_time = timeval_current_ofs_msec(lock_timeout);
    213208        }
    214209        blr->lock_num = lock_num;
     
    219214        blr->offset = offset;
    220215        blr->count = count;
    221      
     216
    222217        /* Specific brl_lock() implementations can fill this in. */
    223218        blr->blr_private = NULL;
     
    227222                        br_lck,
    228223                        smblctx,
    229                         sconn_server_id(req->sconn),
     224                        messaging_server_id(req->sconn->msg_ctx),
    230225                        offset,
    231226                        count,
     
    233228                        blr->lock_flav,
    234229                        True,
    235                         NULL,
    236                         blr);
     230                        NULL);
    237231
    238232        if (!NT_STATUS_IS_OK(status)) {
     
    245239        blr->req = talloc_move(blr, &req);
    246240
    247         DLIST_ADD_END(sconn->smb1.locks.blocking_lock_queue, blr, struct blocking_lock_record *);
     241        DLIST_ADD_END(sconn->smb1.locks.blocking_lock_queue, blr);
    248242        recalc_brl_timeout(sconn);
    249243
    250244        /* Ensure we'll receive messages when this is unlocked. */
    251245        if (!sconn->smb1.locks.blocking_lock_unlock_state) {
    252                 messaging_register(sconn->msg_ctx, NULL,
     246                messaging_register(sconn->msg_ctx, sconn,
    253247                                   MSG_SMB_UNLOCK, received_unlock_msg);
    254248                sconn->smb1.locks.blocking_lock_unlock_state = true;
     
    256250
    257251        DEBUG(3,("push_blocking_lock_request: lock request blocked with "
    258                 "expiry time (%u sec. %u usec) (+%d msec) for fnum = %d, name = %s\n",
     252                "expiry time (%u sec. %u usec) (+%d msec) for %s, name = %s\n",
    259253                (unsigned int)blr->expire_time.tv_sec,
    260254                (unsigned int)blr->expire_time.tv_usec, lock_timeout,
    261                 blr->fsp->fnum, fsp_str_dbg(blr->fsp)));
     255                fsp_fnum_dbg(blr->fsp), fsp_str_dbg(blr->fsp)));
    262256
    263257        return True;
     
    270264static void reply_lockingX_success(struct blocking_lock_record *blr)
    271265{
    272         reply_outbuf(blr->req, 2, 0);
     266        struct smb_request *req = blr->req;
     267
     268        reply_outbuf(req, 2, 0);
     269        SSVAL(req->outbuf, smb_vwv0, 0xff); /* andx chain ends */
     270        SSVAL(req->outbuf, smb_vwv1, 0);    /* no andx offset */
    273271
    274272        /*
     
    280278         */
    281279
    282         chain_reply(blr->req);
    283         TALLOC_FREE(blr->req->outbuf);
     280        if (!srv_send_smb(req->xconn,
     281                        (char *)req->outbuf,
     282                        true, req->seqnum+1,
     283                        IS_CONN_ENCRYPTED(req->conn)||req->encrypted,
     284                        &req->pcd)) {
     285                exit_server_cleanly("construct_reply: srv_send_smb failed.");
     286        }
     287
     288        TALLOC_FREE(req->outbuf);
    284289}
    285290
     
    304309                        fsp->last_lock_failure.context.tid = fsp->conn->cnum;
    305310                        fsp->last_lock_failure.context.pid =
    306                                 sconn_server_id(fsp->conn->sconn);
     311                                messaging_server_id(fsp->conn->sconn->msg_ctx);
    307312                        fsp->last_lock_failure.start = blr->offset;
    308313                        fsp->last_lock_failure.size = blr->count;
     
    314319
    315320        reply_nterror(blr->req, status);
    316         if (!srv_send_smb(blr->req->sconn, (char *)blr->req->outbuf,
     321        if (!srv_send_smb(blr->req->xconn, (char *)blr->req->outbuf,
    317322                          true, blr->req->seqnum+1,
    318323                          blr->req->encrypted, NULL)) {
     
    323328
    324329/****************************************************************************
    325  Return a lock fail error for a lockingX call. Undo all the locks we have 
     330 Return a lock fail error for a lockingX call. Undo all the locks we have
    326331 obtained first.
    327332*****************************************************************************/
     
    330335{
    331336        files_struct *fsp = blr->fsp;
    332         uint16 num_ulocks = SVAL(blr->req->vwv+6, 0);
     337        uint16_t num_ulocks = SVAL(blr->req->vwv+6, 0);
    333338        uint64_t count = (uint64_t)0, offset = (uint64_t) 0;
    334339        uint64_t smblctx;
     
    338343        int i;
    339344
    340         data = (uint8_t *)blr->req->buf
     345        data = discard_const_p(uint8_t, blr->req->buf)
    341346                + ((large_file_format ? 20 : 10)*num_ulocks);
    342347
    343         /* 
     348        /*
    344349         * Data now points at the beginning of the list
    345350         * of smb_lkrng structs.
     
    353358
    354359        for(i = blr->lock_num - 1; i >= 0; i--) {
    355                 bool err;
    356360
    357361                smblctx = get_lock_pid( data, i, large_file_format);
    358362                count = get_lock_count( data, i, large_file_format);
    359                 offset = get_lock_offset( data, i, large_file_format, &err);
     363                offset = get_lock_offset( data, i, large_file_format);
    360364
    361365                /*
     
    393397                }
    394398                generic_blocking_lock_error(blr, status);
    395                 break;
     399                break;
    396400        case SMBtrans2:
    397401        case SMBtranss2:
     
    404408                SCVAL(blr->req->outbuf,smb_com,SMBtrans2);
    405409
    406                 if (!srv_send_smb(blr->req->sconn,
     410                if (!srv_send_smb(blr->req->xconn,
    407411                                  (char *)blr->req->outbuf,
    408412                                  true, blr->req->seqnum+1,
     
    421425
    422426/****************************************************************************
     427 Utility function that returns true if a lock timed out.
     428*****************************************************************************/
     429
     430static bool lock_timed_out(const struct blocking_lock_record *blr)
     431{
     432        struct timeval tv_curr;
     433
     434        if (timeval_is_zero(&blr->expire_time)) {
     435                return false; /* Never times out. */
     436        }
     437
     438        tv_curr = timeval_current();
     439        if (timeval_compare(&blr->expire_time, &tv_curr) <= 0) {
     440                return true;
     441        }
     442        return false;
     443}
     444
     445/****************************************************************************
    423446 Attempt to finish off getting all pending blocking locks for a lockingX call.
    424447 Returns True if we want to be removed from the list.
     
    429452        unsigned char locktype = CVAL(blr->req->vwv+3, 0);
    430453        files_struct *fsp = blr->fsp;
    431         uint16 num_ulocks = SVAL(blr->req->vwv+6, 0);
    432         uint16 num_locks = SVAL(blr->req->vwv+7, 0);
    433         uint64_t count = (uint64_t)0, offset = (uint64_t)0;
    434         uint64_t smblctx;
     454        uint16_t num_ulocks = SVAL(blr->req->vwv+6, 0);
     455        uint16_t num_locks = SVAL(blr->req->vwv+7, 0);
    435456        bool large_file_format = (locktype & LOCKING_ANDX_LARGE_FILES);
    436457        uint8_t *data;
    437458        NTSTATUS status = NT_STATUS_OK;
    438 
    439         data = (uint8_t *)blr->req->buf
     459        bool lock_timeout = lock_timed_out(blr);
     460
     461        data = discard_const_p(uint8_t, blr->req->buf)
    440462                + ((large_file_format ? 20 : 10)*num_ulocks);
    441463
    442         /* 
     464        /*
    443465         * Data now points at the beginning of the list
    444466         * of smb_lkrng structs.
     
    447469        for(; blr->lock_num < num_locks; blr->lock_num++) {
    448470                struct byte_range_lock *br_lck = NULL;
    449                 bool err;
    450 
    451                 smblctx = get_lock_pid( data, blr->lock_num, large_file_format);
    452                 count = get_lock_count( data, blr->lock_num, large_file_format);
    453                 offset = get_lock_offset( data, blr->lock_num, large_file_format, &err);
     471
     472                /*
     473                 * Ensure the blr record gets updated with
     474                 * any lock we might end up blocked on.
     475                 */
     476
     477                blr->smblctx = get_lock_pid( data, blr->lock_num, large_file_format);
     478                blr->count = get_lock_count( data, blr->lock_num, large_file_format);
     479                blr->offset = get_lock_offset( data, blr->lock_num, large_file_format);
    454480
    455481                /*
     
    460486                br_lck = do_lock(fsp->conn->sconn->msg_ctx,
    461487                                fsp,
    462                                 smblctx,
    463                                 count,
    464                                 offset,
     488                                blr->smblctx,
     489                                blr->count,
     490                                blr->offset,
    465491                                ((locktype & LOCKING_ANDX_SHARED_LOCK) ?
    466492                                        READ_LOCK : WRITE_LOCK),
     
    468494                                True,
    469495                                &status,
    470                                 &blr->blocking_smblctx,
    471                                 blr);
     496                                &blr->blocking_smblctx);
     497
     498                if (ERROR_WAS_LOCK_DENIED(status) && !lock_timeout) {
     499                        /*
     500                         * If we didn't timeout, but still need to wait,
     501                         * re-add the pending lock entry whilst holding
     502                         * the brlock db lock.
     503                         */
     504                        NTSTATUS status1 =
     505                                brl_lock(blr->fsp->conn->sconn->msg_ctx,
     506                                        br_lck,
     507                                        blr->smblctx,
     508                                        messaging_server_id(
     509                                                blr->fsp->conn->sconn->msg_ctx),
     510                                        blr->offset,
     511                                        blr->count,
     512                                        blr->lock_type == READ_LOCK ?
     513                                                PENDING_READ_LOCK :
     514                                                PENDING_WRITE_LOCK,
     515                                                blr->lock_flav,
     516                                        true, /* Blocking lock. */
     517                                        NULL);
     518
     519                        if (!NT_STATUS_IS_OK(status1)) {
     520                                DEBUG(0,("failed to add PENDING_LOCK "
     521                                        "record.\n"));
     522                        }
     523                }
    472524
    473525                TALLOC_FREE(br_lck);
     
    483535                 */
    484536
    485                 DEBUG(3,("process_lockingX file = %s, fnum=%d type=%d "
    486                          "num_locks=%d\n", fsp_str_dbg(fsp), fsp->fnum,
     537                DEBUG(3,("process_lockingX file = %s, %s, type=%d "
     538                         "num_locks=%d\n", fsp_str_dbg(fsp), fsp_fnum_dbg(fsp),
    487539                         (unsigned int)locktype, num_locks));
    488540
     
    491543        }
    492544
    493         if (!NT_STATUS_EQUAL(status,NT_STATUS_LOCK_NOT_GRANTED) &&
    494             !NT_STATUS_EQUAL(status,NT_STATUS_FILE_LOCK_CONFLICT)) {
     545        if (!ERROR_WAS_LOCK_DENIED(status)) {
    495546                /*
    496547                 * We have other than a "can't get lock"
     
    503554
    504555        /*
     556         * Return an error to the client if we timed out.
     557         */
     558        if (lock_timeout) {
     559                blocking_lock_reply_error(blr,NT_STATUS_FILE_LOCK_CONFLICT);
     560                return true;
     561        }
     562
     563        /*
    505564         * Still can't get all the locks - keep waiting.
    506565         */
    507566
    508         DEBUG(10,("process_lockingX: only got %d locks of %d needed for file %s, fnum = %d. \
    509 Waiting....\n",
    510                  blr->lock_num, num_locks, fsp_str_dbg(fsp), fsp->fnum));
     567        DEBUG(10, ("process_lockingX: only got %d locks of %d needed for "
     568                   "file %s, %s. Waiting....\n",
     569                   blr->lock_num, num_locks, fsp_str_dbg(fsp),
     570                   fsp_fnum_dbg(fsp)));
    511571
    512572        return False;
     
    522582        char params[2];
    523583        NTSTATUS status;
     584        bool lock_timeout = lock_timed_out(blr);
     585
    524586        struct byte_range_lock *br_lck = do_lock(
    525587                                                blr->fsp->conn->sconn->msg_ctx,
     
    532594                                                True,
    533595                                                &status,
    534                                                 &blr->blocking_smblctx,
    535                                                 blr);
     596                                                &blr->blocking_smblctx);
     597        if (ERROR_WAS_LOCK_DENIED(status) && !lock_timeout) {
     598                /*
     599                 * If we didn't timeout, but still need to wait,
     600                 * re-add the pending lock entry whilst holding
     601                 * the brlock db lock.
     602                 */
     603                NTSTATUS status1 =
     604                        brl_lock(blr->fsp->conn->sconn->msg_ctx,
     605                                br_lck,
     606                                blr->smblctx,
     607                                messaging_server_id(
     608                                        blr->fsp->conn->sconn->msg_ctx),
     609                                blr->offset,
     610                                blr->count,
     611                                blr->lock_type == READ_LOCK ?
     612                                        PENDING_READ_LOCK :
     613                                        PENDING_WRITE_LOCK,
     614                                blr->lock_flav,
     615                                true, /* Blocking lock. */
     616                                NULL);
     617
     618                if (!NT_STATUS_IS_OK(status1)) {
     619                        DEBUG(0,("failed to add PENDING_LOCK record.\n"));
     620                }
     621        }
     622
    536623        TALLOC_FREE(br_lck);
    537624
    538625        if (!NT_STATUS_IS_OK(status)) {
    539626                if (ERROR_WAS_LOCK_DENIED(status)) {
     627                        if (lock_timeout) {
     628                                /*
     629                                 * Return an error if we timed out
     630                                 * and return true to get dequeued.
     631                                 */
     632                                blocking_lock_reply_error(blr,
     633                                        NT_STATUS_FILE_LOCK_CONFLICT);
     634                                return true;
     635                        }
    540636                        /* Still can't get the lock, just keep waiting. */
    541637                        return False;
    542                 }       
     638                }
    543639                /*
    544640                 * We have other than a "can't get lock"
     
    553649        SSVAL(params,0,0);
    554650        /* Fake up max_data_bytes here - we know it fits. */
    555         send_trans2_replies(blr->fsp->conn, blr->req, params, 2, NULL, 0, 0xffff);
     651        send_trans2_replies(blr->fsp->conn, blr->req, NT_STATUS_OK, params, 2, NULL, 0, 0xffff);
    556652        return True;
    557653}
     
    583679*****************************************************************************/
    584680
    585 void cancel_pending_lock_requests_by_fid(files_struct *fsp,
    586                         struct byte_range_lock *br_lck,
    587                         enum file_close_type close_type)
     681void smbd_cancel_pending_lock_requests_by_fid(files_struct *fsp,
     682                                              struct byte_range_lock *br_lck,
     683                                              enum file_close_type close_type)
    588684{
    589685        struct smbd_server_connection *sconn = fsp->conn->sconn;
     
    610706
    611707                DEBUG(10, ("remove_pending_lock_requests_by_fid - removing "
    612                            "request type %d for file %s fnum = %d\n",
    613                            blr->req->cmd, fsp_str_dbg(fsp), fsp->fnum));
     708                           "request type %d for file %s, %s\n",
     709                           blr->req->cmd, fsp_str_dbg(fsp), fsp_fnum_dbg(fsp)));
    614710
    615711                blr_cancelled = blocking_lock_cancel_smb1(fsp,
     
    625721                brl_lock_cancel(br_lck,
    626722                                blr->smblctx,
    627                                 sconn_server_id(sconn),
     723                                messaging_server_id(sconn->msg_ctx),
    628724                                blr->offset,
    629725                                blr->count,
    630                                 blr->lock_flav,
    631                                 blr);
     726                                blr->lock_flav);
    632727
    633728                /* We're closing the file fsp here, so ensure
     
    662757                if (br_lck) {
    663758                        DEBUG(10, ("remove_pending_lock_requests_by_mid_smb1 - "
    664                                    "removing request type %d for file %s fnum "
    665                                    "= %d\n", blr->req->cmd, fsp_str_dbg(fsp),
    666                                    fsp->fnum ));
     759                                   "removing request type %d for file %s, %s\n",
     760                                   blr->req->cmd, fsp_str_dbg(fsp),
     761                                   fsp_fnum_dbg(fsp)));
    667762
    668763                        brl_lock_cancel(br_lck,
    669764                                        blr->smblctx,
    670                                         sconn_server_id(sconn),
     765                                        messaging_server_id(sconn->msg_ctx),
    671766                                        blr->offset,
    672767                                        blr->count,
    673                                         blr->lock_flav,
    674                                         blr);
     768                                        blr->lock_flav);
    675769                        TALLOC_FREE(br_lck);
    676770                }
     
    711805                                DATA_BLOB *data)
    712806{
    713         struct smbd_server_connection *sconn;
    714 
    715         sconn = msg_ctx_to_sconn(msg);
    716         if (sconn == NULL) {
    717                 DEBUG(1, ("could not find sconn\n"));
    718                 return;
    719         }
     807        struct smbd_server_connection *sconn =
     808                talloc_get_type_abort(private_data,
     809                struct smbd_server_connection);
    720810
    721811        DEBUG(10,("received_unlock_msg\n"));
     
    729819void process_blocking_lock_queue(struct smbd_server_connection *sconn)
    730820{
    731         struct timeval tv_curr = timeval_current();
    732821        struct blocking_lock_record *blr, *next = NULL;
    733822
    734823        if (sconn->using_smb2) {
    735                 process_blocking_lock_queue_smb2(sconn, tv_curr);
     824                process_blocking_lock_queue_smb2(sconn, timeval_current());
    736825                return;
    737826        }
     
    742831
    743832        for (blr = sconn->smb1.locks.blocking_lock_queue; blr; blr = next) {
     833                struct byte_range_lock *br_lck = NULL;
    744834
    745835                next = blr->next;
     
    761851                                false);
    762852
    763                 if(blocking_lock_record_process(blr)) {
    764                         struct byte_range_lock *br_lck = brl_get_locks(
    765                                 talloc_tos(), blr->fsp);
    766 
    767                         DEBUG(10, ("BLR_process returned true: cancelling and "
    768                             "removing lock. BLR = %p\n", blr));
    769 
    770                         if (br_lck) {
    771                                 brl_lock_cancel(br_lck,
    772                                         blr->smblctx,
    773                                         sconn_server_id(sconn),
    774                                         blr->offset,
    775                                         blr->count,
    776                                         blr->lock_flav,
    777                                         blr);
    778                                 TALLOC_FREE(br_lck);
    779                         }
    780 
    781                         DLIST_REMOVE(sconn->smb1.locks.blocking_lock_queue, blr);
    782                         TALLOC_FREE(blr);
     853                /*
     854                 * Remove the pending lock we're waiting on.
     855                 * If we need to keep waiting blocking_lock_record_process()
     856                 * will re-add it.
     857                 */
     858
     859                br_lck = brl_get_locks(talloc_tos(), blr->fsp);
     860                if (br_lck) {
     861                        brl_lock_cancel(br_lck,
     862                                blr->smblctx,
     863                                messaging_server_id(sconn->msg_ctx),
     864                                blr->offset,
     865                                blr->count,
     866                                blr->lock_flav);
     867                }
     868                TALLOC_FREE(br_lck);
     869
     870                if(!blocking_lock_record_process(blr)) {
     871                        DEBUG(10, ("still waiting for lock. BLR = %p\n", blr));
    783872                        continue;
    784873                }
    785874
    786                 /*
    787                  * We couldn't get the locks for this record on the list.
    788                  * If the time has expired, return a lock error.
    789                  */
    790 
    791                 if (!timeval_is_zero(&blr->expire_time) && timeval_compare(&blr->expire_time, &tv_curr) <= 0) {
    792                         struct byte_range_lock *br_lck = brl_get_locks(
    793                                 talloc_tos(), blr->fsp);
    794 
    795                         DEBUG(10, ("Lock timed out! BLR = %p\n", blr));
    796 
    797                         /*
    798                          * Lock expired - throw away all previously
    799                          * obtained locks and return lock error.
    800                          */
    801 
    802                         if (br_lck) {
    803                                 DEBUG(5,("process_blocking_lock_queue: "
    804                                          "pending lock fnum = %d for file %s "
    805                                          "timed out.\n", blr->fsp->fnum,
    806                                          fsp_str_dbg(blr->fsp)));
    807 
    808                                 brl_lock_cancel(br_lck,
    809                                         blr->smblctx,
    810                                         sconn_server_id(sconn),
    811                                         blr->offset,
    812                                         blr->count,
    813                                         blr->lock_flav,
    814                                         blr);
    815                                 TALLOC_FREE(br_lck);
    816                         }
    817 
    818                         blocking_lock_reply_error(blr,NT_STATUS_FILE_LOCK_CONFLICT);
    819                         DLIST_REMOVE(sconn->smb1.locks.blocking_lock_queue, blr);
    820                         TALLOC_FREE(blr);
    821                 }
     875                DEBUG(10, ("BLR_process returned true: removing BLR = %p\n",
     876                        blr));
     877
     878                DLIST_REMOVE(sconn->smb1.locks.blocking_lock_queue, blr);
     879                TALLOC_FREE(blr);
    822880        }
    823881
     
    837895                                                 DATA_BLOB *data)
    838896{
    839         struct smbd_server_connection *sconn;
    840897        NTSTATUS err;
    841898        const char *msg = (const char *)data->data;
    842899        struct blocking_lock_record *blr;
     900        struct smbd_server_connection *sconn =
     901                talloc_get_type_abort(private_data,
     902                struct smbd_server_connection);
    843903
    844904        if (data->data == NULL) {
     
    851911                smb_panic("process_blocking_lock_cancel_message: bad msg");
    852912        }
    853 
    854         sconn = msg_ctx_to_sconn(ctx);
    855         if (sconn == NULL) {
    856                 DEBUG(1, ("could not find sconn\n"));
    857                 return;
    858         }
    859913
    860914        memcpy(&blr, msg, sizeof(blr));
     
    889943        if (!sconn->smb1.locks.blocking_lock_cancel_state) {
    890944                /* Register our message. */
    891                 messaging_register(sconn->msg_ctx, NULL,
     945                messaging_register(sconn->msg_ctx, sconn,
    892946                                   MSG_SMB_BLOCKING_LOCK_CANCEL,
    893947                                   process_blocking_lock_cancel_message);
     
    925979        memcpy(&msg[sizeof(blr)], &err, sizeof(NTSTATUS));
    926980
    927         messaging_send_buf(sconn->msg_ctx, sconn_server_id(sconn),
     981        messaging_send_buf(sconn->msg_ctx, messaging_server_id(sconn->msg_ctx),
    928982                           MSG_SMB_BLOCKING_LOCK_CANCEL,
    929                            (uint8 *)&msg, sizeof(msg));
     983                           (uint8_t *)&msg, sizeof(msg));
    930984
    931985        return blr;
Note: See TracChangeset for help on using the changeset viewer.