2003-08-13 01:53:07 +00:00
/*
Unix SMB / CIFS implementation .
basic raw test suite for oplocks
Copyright ( C ) Andrew Tridgell 2003
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"
2006-01-03 13:41:17 +00:00
# include "torture/torture.h"
2006-03-16 00:23:11 +00:00
# include "librpc/gen_ndr/security.h"
2005-12-28 15:38:36 +00:00
# include "libcli/raw/libcliraw.h"
2006-01-03 15:40:05 +00:00
# include "libcli/libcli.h"
2003-08-13 01:53:07 +00:00
# define CHECK_VAL(v, correct) do { \
if ( ( v ) ! = ( correct ) ) { \
2004-05-30 08:12:17 +00:00
printf ( " (%d) wrong value for %s got 0x%x - should be 0x%x \n " , \
2003-08-13 01:53:07 +00:00
__LINE__ , # v , ( int ) v , ( int ) correct ) ; \
ret = False ; \
} } while ( 0 )
# define CHECK_STATUS(status, correct) do { \
if ( ! NT_STATUS_EQUAL ( status , correct ) ) { \
printf ( " (%d) Incorrect status %s - should be %s \n " , \
__LINE__ , nt_errstr ( status ) , nt_errstr ( correct ) ) ; \
ret = False ; \
goto done ; \
} } while ( 0 )
static struct {
int fnum ;
2004-05-29 08:11:46 +00:00
uint8_t level ;
2003-08-13 01:53:07 +00:00
int count ;
2005-12-28 22:18:45 +00:00
int failures ;
2003-08-13 01:53:07 +00:00
} break_info ;
/*
a handler function for oplock break requests
*/
2004-08-04 13:23:35 +00:00
static BOOL oplock_handler_ack ( struct smbcli_transport * transport , uint16_t tid , uint16_t fnum , uint8_t level , void * private )
2003-08-13 01:53:07 +00:00
{
2004-08-04 13:23:35 +00:00
struct smbcli_tree * tree = private ;
2003-08-13 01:53:07 +00:00
break_info . fnum = fnum ;
break_info . level = level ;
break_info . count + + ;
printf ( " Acking in oplock handler \n " ) ;
2004-08-04 13:23:35 +00:00
return smbcli_oplock_ack ( tree , fnum , level ) ;
2003-08-13 01:53:07 +00:00
}
2005-12-28 22:18:45 +00:00
static void oplock_handler_close_recv ( struct smbcli_request * req )
{
NTSTATUS status ;
status = smbcli_request_simple_recv ( req ) ;
if ( ! NT_STATUS_IS_OK ( status ) ) {
printf ( " close failed in oplock_handler_close \n " ) ;
break_info . failures + + ;
}
}
2003-08-13 01:53:07 +00:00
/*
a handler function for oplock break requests - close the file
*/
2004-08-04 13:23:35 +00:00
static BOOL oplock_handler_close ( struct smbcli_transport * transport , uint16_t tid , uint16_t fnum , uint8_t level , void * private )
2003-08-13 01:53:07 +00:00
{
union smb_close io ;
2004-08-04 13:23:35 +00:00
struct smbcli_tree * tree = private ;
2005-12-28 22:18:45 +00:00
struct smbcli_request * req ;
2003-08-13 01:53:07 +00:00
break_info . fnum = fnum ;
break_info . level = level ;
break_info . count + + ;
2005-12-28 22:18:45 +00:00
printf ( " Closing in oplock handler \n " ) ;
2003-08-13 01:53:07 +00:00
io . close . level = RAW_CLOSE_CLOSE ;
2006-03-12 22:48:25 +00:00
io . close . in . file . fnum = fnum ;
2003-08-13 01:53:07 +00:00
io . close . in . write_time = 0 ;
2005-12-28 22:18:45 +00:00
req = smb_raw_close_send ( tree , & io ) ;
if ( req = = NULL ) {
printf ( " failed to send close in oplock_handler_close \n " ) ;
2003-08-13 01:53:07 +00:00
return False ;
}
2005-12-28 22:18:45 +00:00
req - > async . fn = oplock_handler_close_recv ;
req - > async . private = NULL ;
2003-08-13 01:53:07 +00:00
return True ;
}
/*
test oplock ops
*/
2004-08-04 13:23:35 +00:00
static BOOL test_oplock ( struct smbcli_state * cli , TALLOC_CTX * mem_ctx )
2003-08-13 01:53:07 +00:00
{
const char * fname = " \\ test_oplock.dat " ;
NTSTATUS status ;
BOOL ret = True ;
union smb_open io ;
2006-03-10 20:49:20 +00:00
union smb_unlink unl ;
2003-08-13 01:53:07 +00:00
union smb_read rd ;
2004-08-03 06:50:58 +00:00
uint16_t fnum = 0 , fnum2 = 0 ;
2003-08-13 01:53:07 +00:00
/* cleanup */
2004-08-04 13:23:35 +00:00
smbcli_unlink ( cli - > tree , fname ) ;
2003-08-13 01:53:07 +00:00
2004-08-04 13:23:35 +00:00
smbcli_oplock_handler ( cli - > transport , oplock_handler_ack , cli - > tree ) ;
2003-08-13 01:53:07 +00:00
/*
base ntcreatex parms
*/
io . generic . level = RAW_OPEN_NTCREATEX ;
io . ntcreatex . in . root_fid = 0 ;
2004-12-02 04:37:36 +00:00
io . ntcreatex . in . access_mask = SEC_RIGHTS_FILE_ALL ;
2003-08-13 01:53:07 +00:00
io . ntcreatex . in . alloc_size = 0 ;
io . ntcreatex . in . file_attr = FILE_ATTRIBUTE_NORMAL ;
io . ntcreatex . in . share_access = NTCREATEX_SHARE_ACCESS_NONE ;
io . ntcreatex . in . open_disposition = NTCREATEX_DISP_OPEN_IF ;
io . ntcreatex . in . create_options = 0 ;
io . ntcreatex . in . impersonation = NTCREATEX_IMPERSONATION_ANONYMOUS ;
io . ntcreatex . in . security_flags = 0 ;
io . ntcreatex . in . fname = fname ;
printf ( " open a file with a normal oplock \n " ) ;
ZERO_STRUCT ( break_info ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED | NTCREATEX_FLAGS_REQUEST_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , EXCLUSIVE_OPLOCK_RETURN ) ;
printf ( " unlink it - should be no break \n " ) ;
2006-03-10 20:49:20 +00:00
unl . unlink . in . pattern = fname ;
unl . unlink . in . attrib = 0 ;
2003-08-13 01:53:07 +00:00
status = smb_raw_unlink ( cli - > tree , & unl ) ;
CHECK_STATUS ( status , NT_STATUS_SHARING_VIOLATION ) ;
CHECK_VAL ( break_info . count , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2003-08-13 01:53:07 +00:00
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
2003-08-13 01:53:07 +00:00
/*
with a batch oplock we get a break
*/
printf ( " open with batch oplock \n " ) ;
ZERO_STRUCT ( break_info ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
printf ( " unlink should generate a break \n " ) ;
2006-03-10 20:49:20 +00:00
unl . unlink . in . pattern = fname ;
unl . unlink . in . attrib = 0 ;
2003-08-13 01:53:07 +00:00
status = smb_raw_unlink ( cli - > tree , & unl ) ;
CHECK_STATUS ( status , NT_STATUS_SHARING_VIOLATION ) ;
CHECK_VAL ( break_info . fnum , fnum ) ;
2004-05-30 08:12:17 +00:00
CHECK_VAL ( break_info . level , 1 ) ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( break_info . count , 1 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2003-08-13 01:53:07 +00:00
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
2003-08-13 01:53:07 +00:00
printf ( " if we close on break then the unlink can succeed \n " ) ;
ZERO_STRUCT ( break_info ) ;
2004-08-04 13:23:35 +00:00
smbcli_oplock_handler ( cli - > transport , oplock_handler_close , cli - > tree ) ;
2003-08-13 01:53:07 +00:00
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
2006-03-10 20:49:20 +00:00
unl . unlink . in . pattern = fname ;
unl . unlink . in . attrib = 0 ;
2003-08-13 01:53:07 +00:00
ZERO_STRUCT ( break_info ) ;
status = smb_raw_unlink ( cli - > tree , & unl ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
CHECK_VAL ( break_info . fnum , fnum ) ;
2004-05-30 08:12:17 +00:00
CHECK_VAL ( break_info . level , 1 ) ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( break_info . count , 1 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2003-08-13 01:53:07 +00:00
printf ( " a self read should not cause a break \n " ) ;
ZERO_STRUCT ( break_info ) ;
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
smbcli_oplock_handler ( cli - > transport , oplock_handler_ack , cli - > tree ) ;
2003-08-13 01:53:07 +00:00
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
rd . read . level = RAW_READ_READ ;
2006-03-12 22:48:25 +00:00
rd . read . in . file . fnum = fnum ;
2003-08-13 01:53:07 +00:00
rd . read . in . count = 1 ;
rd . read . in . offset = 0 ;
rd . read . in . remaining = 0 ;
status = smb_raw_read ( cli - > tree , & rd ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
CHECK_VAL ( break_info . count , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2003-08-13 01:53:07 +00:00
printf ( " a 2nd open should give a break \n " ) ;
ZERO_STRUCT ( break_info ) ;
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
smbcli_oplock_handler ( cli - > transport , oplock_handler_ack , cli - > tree ) ;
2003-08-13 01:53:07 +00:00
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
ZERO_STRUCT ( break_info ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_SHARING_VIOLATION ) ;
CHECK_VAL ( break_info . count , 1 ) ;
CHECK_VAL ( break_info . fnum , fnum ) ;
2004-05-30 08:12:17 +00:00
CHECK_VAL ( break_info . level , 1 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2003-08-13 01:53:07 +00:00
printf ( " a 2nd open should get an oplock when we close instead of ack \n " ) ;
ZERO_STRUCT ( break_info ) ;
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
smbcli_oplock_handler ( cli - > transport , oplock_handler_close , cli - > tree ) ;
2003-08-13 01:53:07 +00:00
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum2 = io . ntcreatex . out . file . fnum ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
ZERO_STRUCT ( break_info ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2003-08-13 01:53:07 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
CHECK_VAL ( break_info . count , 1 ) ;
CHECK_VAL ( break_info . fnum , fnum2 ) ;
2004-05-30 08:12:17 +00:00
CHECK_VAL ( break_info . level , 1 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2003-08-13 01:53:07 +00:00
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
2004-05-25 00:05:51 +00:00
printf ( " open with batch oplock \n " ) ;
ZERO_STRUCT ( break_info ) ;
2004-08-04 13:23:35 +00:00
smbcli_oplock_handler ( cli - > transport , oplock_handler_ack , cli - > tree ) ;
2004-05-25 00:05:51 +00:00
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2004-05-25 00:05:51 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
ZERO_STRUCT ( break_info ) ;
printf ( " second open with attributes only shouldn't cause oplock break \n " ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
2004-11-30 04:33:27 +00:00
io . ntcreatex . in . access_mask = SEC_FILE_READ_ATTRIBUTE | SEC_FILE_WRITE_ATTRIBUTE | SEC_STD_SYNCHRONIZE ;
2004-05-25 00:05:51 +00:00
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum2 = io . ntcreatex . out . file . fnum ;
2004-05-25 00:05:51 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , NO_OPLOCK_RETURN ) ;
CHECK_VAL ( break_info . count , 0 ) ;
CHECK_VAL ( break_info . fnum , 0 ) ;
CHECK_VAL ( break_info . level , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2003-08-13 01:53:07 +00:00
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
smbcli_close ( cli - > tree , fnum2 ) ;
smbcli_unlink ( cli - > tree , fname ) ;
2004-05-30 08:12:17 +00:00
printf ( " open with attributes only can create file \n " ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
2004-11-30 04:33:27 +00:00
io . ntcreatex . in . access_mask = SEC_FILE_READ_ATTRIBUTE | SEC_FILE_WRITE_ATTRIBUTE | SEC_STD_SYNCHRONIZE ;
2004-05-30 08:12:17 +00:00
io . ntcreatex . in . open_disposition = NTCREATEX_DISP_CREATE ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2004-05-30 08:12:17 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , BATCH_OPLOCK_RETURN ) ;
printf ( " Subsequent normal open should break oplock on attribute only open to level II \n " ) ;
ZERO_STRUCT ( break_info ) ;
2004-08-04 13:23:35 +00:00
smbcli_oplock_handler ( cli - > transport , oplock_handler_ack , cli - > tree ) ;
2004-05-30 08:12:17 +00:00
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
2004-12-02 04:37:36 +00:00
io . ntcreatex . in . access_mask = SEC_RIGHTS_FILE_ALL ;
2004-05-30 08:12:17 +00:00
io . ntcreatex . in . open_disposition = NTCREATEX_DISP_OPEN ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum2 = io . ntcreatex . out . file . fnum ;
2004-05-30 08:12:17 +00:00
CHECK_VAL ( break_info . count , 1 ) ;
CHECK_VAL ( break_info . fnum , fnum ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2004-05-30 08:12:17 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , LEVEL_II_OPLOCK_RETURN ) ;
2005-07-08 06:29:06 +00:00
smbcli_close ( cli - > tree , fnum2 ) ;
printf ( " third oplocked open should grant level2 without break \n " ) ;
ZERO_STRUCT ( break_info ) ;
smbcli_oplock_handler ( cli - > transport , oplock_handler_ack , cli - > tree ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
io . ntcreatex . in . access_mask = SEC_RIGHTS_FILE_ALL ;
io . ntcreatex . in . open_disposition = NTCREATEX_DISP_OPEN ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum2 = io . ntcreatex . out . file . fnum ;
2005-07-08 06:29:06 +00:00
CHECK_VAL ( break_info . count , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2005-07-08 06:29:06 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , LEVEL_II_OPLOCK_RETURN ) ;
ZERO_STRUCT ( break_info ) ;
printf ( " write should trigger a break to none on both \n " ) ;
{
union smb_write wr ;
wr . write . level = RAW_WRITE_WRITE ;
2006-03-12 22:48:25 +00:00
wr . write . in . file . fnum = fnum2 ;
2005-07-08 06:29:06 +00:00
wr . write . in . count = 1 ;
wr . write . in . offset = 0 ;
wr . write . in . remaining = 0 ;
2006-01-18 16:20:33 +00:00
wr . write . in . data = ( const uint8_t * ) " x " ;
2005-07-08 06:29:06 +00:00
status = smb_raw_write ( cli - > tree , & wr ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
}
/* Now the oplock break request comes in. But right now we can't
* answer it . Do another write */
msleep ( 100 ) ;
{
union smb_write wr ;
wr . write . level = RAW_WRITE_WRITE ;
2006-03-12 22:48:25 +00:00
wr . write . in . file . fnum = fnum2 ;
2005-07-08 06:29:06 +00:00
wr . write . in . count = 1 ;
wr . write . in . offset = 0 ;
wr . write . in . remaining = 0 ;
2006-01-18 16:20:33 +00:00
wr . write . in . data = ( const uint8_t * ) " x " ;
2005-07-08 06:29:06 +00:00
status = smb_raw_write ( cli - > tree , & wr ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
}
CHECK_VAL ( break_info . count , 2 ) ;
CHECK_VAL ( break_info . level , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2005-07-08 06:29:06 +00:00
smbcli_close ( cli - > tree , fnum ) ;
smbcli_close ( cli - > tree , fnum2 ) ;
ZERO_STRUCT ( break_info ) ;
smbcli_oplock_handler ( cli - > transport , oplock_handler_ack , cli - > tree ) ;
printf ( " Open with oplock after a on-oplock open should grant level2 \n " ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED ;
io . ntcreatex . in . access_mask = SEC_RIGHTS_FILE_ALL ;
io . ntcreatex . in . share_access = NTCREATEX_SHARE_ACCESS_READ |
NTCREATEX_SHARE_ACCESS_WRITE |
NTCREATEX_SHARE_ACCESS_DELETE ;
io . ntcreatex . in . open_disposition = NTCREATEX_DISP_OPEN ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum = io . ntcreatex . out . file . fnum ;
2005-07-08 06:29:06 +00:00
CHECK_VAL ( break_info . count , 0 ) ;
CHECK_VAL ( break_info . fnum , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2005-07-08 06:29:06 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , 0 ) ;
io . ntcreatex . in . flags = NTCREATEX_FLAGS_EXTENDED |
NTCREATEX_FLAGS_REQUEST_OPLOCK |
NTCREATEX_FLAGS_REQUEST_BATCH_OPLOCK ;
io . ntcreatex . in . access_mask = SEC_RIGHTS_FILE_ALL ;
io . ntcreatex . in . share_access = NTCREATEX_SHARE_ACCESS_READ |
NTCREATEX_SHARE_ACCESS_WRITE |
NTCREATEX_SHARE_ACCESS_DELETE ;
io . ntcreatex . in . open_disposition = NTCREATEX_DISP_OPEN ;
status = smb_raw_open ( cli - > tree , mem_ctx , & io ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
2006-03-12 22:48:25 +00:00
fnum2 = io . ntcreatex . out . file . fnum ;
2005-07-08 06:29:06 +00:00
CHECK_VAL ( break_info . count , 0 ) ;
CHECK_VAL ( break_info . fnum , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2005-07-08 06:29:06 +00:00
CHECK_VAL ( io . ntcreatex . out . oplock_level , LEVEL_II_OPLOCK_RETURN ) ;
printf ( " write should trigger a break to none \n " ) ;
{
union smb_write wr ;
wr . write . level = RAW_WRITE_WRITE ;
2006-03-12 22:48:25 +00:00
wr . write . in . file . fnum = fnum ;
2005-07-08 06:29:06 +00:00
wr . write . in . count = 1 ;
wr . write . in . offset = 0 ;
wr . write . in . remaining = 0 ;
2006-01-18 16:20:33 +00:00
wr . write . in . data = ( const uint8_t * ) " x " ;
2005-07-08 06:29:06 +00:00
status = smb_raw_write ( cli - > tree , & wr ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
}
/* Now the oplock break request comes in. But right now we can't
* answer it . Do another write */
msleep ( 100 ) ;
{
union smb_write wr ;
wr . write . level = RAW_WRITE_WRITE ;
2006-03-12 22:48:25 +00:00
wr . write . in . file . fnum = fnum ;
2005-07-08 06:29:06 +00:00
wr . write . in . count = 1 ;
wr . write . in . offset = 0 ;
wr . write . in . remaining = 0 ;
2006-01-18 16:20:33 +00:00
wr . write . in . data = ( const uint8_t * ) " x " ;
2005-07-08 06:29:06 +00:00
status = smb_raw_write ( cli - > tree , & wr ) ;
CHECK_STATUS ( status , NT_STATUS_OK ) ;
}
CHECK_VAL ( break_info . count , 1 ) ;
CHECK_VAL ( break_info . fnum , fnum2 ) ;
CHECK_VAL ( break_info . level , 0 ) ;
2005-12-28 22:18:45 +00:00
CHECK_VAL ( break_info . failures , 0 ) ;
2004-05-30 08:12:17 +00:00
2003-08-13 01:53:07 +00:00
done :
2004-08-04 13:23:35 +00:00
smbcli_close ( cli - > tree , fnum ) ;
smbcli_close ( cli - > tree , fnum2 ) ;
smbcli_unlink ( cli - > tree , fname ) ;
2003-08-13 01:53:07 +00:00
return ret ;
}
/*
basic testing of oplocks
*/
2004-10-28 13:40:50 +00:00
BOOL torture_raw_oplock ( void )
2003-08-13 01:53:07 +00:00
{
2006-01-08 12:31:06 +00:00
struct smbcli_state * cli1 ;
2003-08-13 01:53:07 +00:00
BOOL ret = True ;
TALLOC_CTX * mem_ctx ;
if ( ! torture_open_connection ( & cli1 ) ) {
return False ;
}
mem_ctx = talloc_init ( " torture_raw_oplock " ) ;
if ( ! test_oplock ( cli1 , mem_ctx ) ) {
ret = False ;
}
torture_close_connection ( cli1 ) ;
2005-01-27 07:08:20 +00:00
talloc_free ( mem_ctx ) ;
2003-08-13 01:53:07 +00:00
return ret ;
}