#include "includes.h"
#include "torture/torture.h"
#include "libcli/raw/libcliraw.h"
+#include "libcli/raw/raw_proto.h"
#include "system/time.h"
#include "system/filesys.h"
#include "libcli/libcli.h"
if (!NT_STATUS_EQUAL(status, correct)) { \
printf("(%s) Incorrect status %s - should be %s\n", \
__location__, nt_errstr(status), nt_errstr(correct)); \
- ret = False; \
+ ret = false; \
} \
} while (0)
const char *dirname = "testdir";
int fnum;
NTSTATUS status;
- BOOL ret = True;
+ bool ret = true;
TALLOC_CTX *mem_ctx;
ssize_t nread;
char buf[16];
if ((mem_ctx = talloc_init("torture_samba3_checkfsp")) == NULL) {
d_printf("talloc_init failed\n");
- return False;
+ return false;
}
if (!torture_open_connection_share(
- torture, &cli, torture_setting_string(torture, "host", NULL),
- torture_setting_string(torture, "share", NULL), NULL)) {
+ torture, &cli, torture, torture_setting_string(torture, "host", NULL),
+ torture_setting_string(torture, "share", NULL), torture->ev)) {
d_printf("torture_open_connection_share failed\n");
- ret = False;
+ ret = false;
goto done;
}
status = smbcli_mkdir(cli->tree, dirname);
if (!NT_STATUS_IS_OK(status)) {
d_printf("smbcli_mkdir failed: %s\n", nt_errstr(status));
- ret = False;
+ ret = false;
goto done;
}
io.ntcreatex.in.share_access = NTCREATEX_SHARE_ACCESS_NONE;
io.ntcreatex.in.open_disposition = NTCREATEX_DISP_OPEN;
io.ntcreatex.in.create_options = 0;
+ io.ntcreatex.in.impersonation = NTCREATEX_IMPERSONATION_ANONYMOUS;
io.ntcreatex.in.fname = dirname;
status = smb_raw_open(cli->tree, mem_ctx, &io);
if (!NT_STATUS_IS_OK(status)) {
d_printf("smb_open on the directory failed: %s\n",
nt_errstr(status));
- ret = False;
+ ret = false;
goto done;
}
fnum = io.ntcreatex.out.file.fnum;
if (nread >= 0) {
d_printf("smbcli_read on a directory succeeded, expected "
"failure\n");
- ret = False;
+ ret = false;
}
CHECK_STATUS(smbcli_nt_error(cli->tree),
if (nread >= 0) {
d_printf("smbcli_read on a directory succeeded, expected "
"failure\n");
- ret = False;
+ ret = false;
}
CHECK_STATUS(smbcli_nt_error(tree2), NT_STATUS_INVALID_HANDLE);
if (fnum == -1) {
d_printf("Failed to create %s - %s\n", fname,
smbcli_errstr(cli->tree));
- ret = False;
+ ret = false;
goto done;
}
char *fpath1;
int fnum;
NTSTATUS status;
- BOOL ret = True;
+ bool ret = true;
TALLOC_CTX *mem_ctx;
- BOOL nt_status_support;
+ bool nt_status_support;
if (!(mem_ctx = talloc_init("torture_samba3_badpath"))) {
d_printf("talloc_init failed\n");
- return False;
+ return false;
}
- nt_status_support = lp_nt_status_support();
+ nt_status_support = lp_nt_status_support(torture->lp_ctx);
- if (!lp_set_cmdline("nt status support", "yes")) {
+ if (!lp_set_cmdline(torture->lp_ctx, "nt status support", "yes")) {
printf("Could not set 'nt status support = yes'\n");
goto fail;
}
- if (!torture_open_connection(&cli_nt, 0)) {
+ if (!torture_open_connection(&cli_nt, torture, 0)) {
goto fail;
}
- if (!lp_set_cmdline("nt status support", "no")) {
+ if (!lp_set_cmdline(torture->lp_ctx, "nt status support", "no")) {
printf("Could not set 'nt status support = yes'\n");
goto fail;
}
- if (!torture_open_connection(&cli_dos, 1)) {
+ if (!torture_open_connection(&cli_dos, torture, 1)) {
goto fail;
}
- if (!lp_set_cmdline("nt status support",
+ if (!lp_set_cmdline(torture->lp_ctx, "nt status support",
nt_status_support ? "yes":"no")) {
printf("Could not reset 'nt status support = yes'");
goto fail;
status = smbcli_mkdir(cli_nt->tree, dirname);
if (!NT_STATUS_IS_OK(status)) {
d_printf("smbcli_mkdir failed: %s\n", nt_errstr(status));
- ret = False;
+ ret = false;
goto done;
}
goto done;
fail:
- ret = False;
+ ret = false;
done:
if (cli_nt != NULL) {
char *fpath;
int fnum;
int counter = 0;
- BOOL ret = True;
+ bool ret = true;
if (!(mem_ctx = talloc_init("torture_samba3_caseinsensitive"))) {
d_printf("talloc_init failed\n");
- return False;
+ return false;
}
- if (!torture_open_connection(&cli, 0)) {
+ if (!torture_open_connection(&cli, torture, 0)) {
goto done;
}
count_fn, (void *)&counter);
if (counter == 3) {
- ret = True;
+ ret = true;
}
else {
d_fprintf(stderr, "expected 3 entries, got %d\n", counter);
- ret = False;
+ ret = false;
}
done:
return ret;
}
+static void close_locked_file(struct tevent_context *ev,
+ struct tevent_timer *te,
+ struct timeval now,
+ void *private_data)
+{
+ int *pfd = (int *)private_data;
+
+ TALLOC_FREE(te);
+
+ if (*pfd != -1) {
+ close(*pfd);
+ *pfd = -1;
+ }
+}
+
+struct lock_result_state {
+ NTSTATUS status;
+ bool done;
+};
+
+static void receive_lock_result(struct smbcli_request *req)
+{
+ struct lock_result_state *state =
+ (struct lock_result_state *)req->async.private_data;
+
+ state->status = smbcli_request_simple_recv(req);
+ state->done = true;
+}
+
/*
* Check that Samba3 correctly deals with conflicting posix byte range locks
* on an underlying file
+ *
+ * Note: This test depends on "posix locking = yes".
+ * Note: To run this test, use "--option=torture:localdir=<LOCALDIR>"
*/
bool torture_samba3_posixtimedlock(struct torture_context *tctx)
{
struct smbcli_state *cli;
NTSTATUS status;
- BOOL ret = True;
+ bool ret = true;
const char *dirname = "posixlock";
const char *fname = "locked";
const char *fpath;
union smb_lock io;
struct smb_lock_entry lock_entry;
struct smbcli_request *req;
+ struct lock_result_state lock_result;
- if (!torture_open_connection(&cli, 0)) {
- ret = False;
+ struct tevent_timer *te;
+
+ if (!torture_open_connection(&cli, tctx, 0)) {
+ ret = false;
goto done;
}
if (!NT_STATUS_IS_OK(status)) {
torture_warning(tctx, "smbcli_mkdir failed: %s\n",
nt_errstr(status));
- ret = False;
+ ret = false;
goto done;
}
if (!(fpath = talloc_asprintf(tctx, "%s\\%s", dirname, fname))) {
torture_warning(tctx, "talloc failed\n");
- ret = False;
+ ret = false;
goto done;
}
fnum = smbcli_open(cli->tree, fpath, O_RDWR | O_CREAT, DENY_NONE);
if (fnum == -1) {
torture_warning(tctx, "Could not create file %s: %s\n", fpath,
smbcli_errstr(cli->tree));
- ret = False;
+ ret = false;
goto done;
}
if (!(localdir = torture_setting_string(tctx, "localdir", NULL))) {
torture_warning(tctx, "Need 'localdir' setting\n");
- ret = False;
+ ret = false;
goto done;
}
if (!(localname = talloc_asprintf(tctx, "%s/%s/%s", localdir, dirname,
fname))) {
torture_warning(tctx, "talloc failed\n");
- ret = False;
+ ret = false;
goto done;
}
if (fcntl(fd, F_SETLK, &posix_lock) == -1) {
torture_warning(tctx, "fcntl failed: %s\n", strerror(errno));
- ret = False;
+ ret = false;
goto done;
}
status = smb_raw_lock(cli->tree, &io);
- ret = True;
+ ret = true;
CHECK_STATUS(status, NT_STATUS_FILE_LOCK_CONFLICT);
if (!ret) {
req = smb_raw_lock_send(cli->tree, &io);
if (req == NULL) {
torture_warning(tctx, "smb_raw_lock_send failed\n");
- ret = False;
+ ret = false;
goto done;
}
- /*
- * Ship the async timed request to the server
- */
- event_loop_once(req->transport->socket->event.ctx);
- msleep(500);
+ lock_result.done = false;
+ req->async.fn = receive_lock_result;
+ req->async.private_data = &lock_result;
- close(fd);
+ te = tevent_add_timer(req->transport->socket->event.ctx,
+ tctx, timeval_current_ofs(1, 0),
+ close_locked_file, &fd);
+ if (te == NULL) {
+ torture_warning(tctx, "tevent_add_timer failed\n");
+ ret = false;
+ goto done;
+ }
- status = smbcli_request_simple_recv(req);
+ while ((fd != -1) || (!lock_result.done)) {
+ if (tevent_loop_once(req->transport->socket->event.ctx)
+ == -1) {
+ torture_warning(tctx, "tevent_loop_once failed: %s\n",
+ strerror(errno));
+ ret = false;
+ goto done;
+ }
+ }
- CHECK_STATUS(status, NT_STATUS_OK);
+ CHECK_STATUS(lock_result.status, NT_STATUS_OK);
done:
if (fnum != -1) {
const char *fname = "testfile";
bool ret = false;
- if (!torture_open_connection(&cli, 0)) {
+ if (!torture_open_connection(&cli, tctx, 0)) {
ret = false;
goto done;
}
smbcli_unlink(cli->tree, fname);
+ ZERO_STRUCT(io);
io.generic.level = RAW_OPEN_NTCREATEX;
io.ntcreatex.in.flags = NTCREATEX_FLAGS_EXTENDED;
io.ntcreatex.in.root_fid = 0;
| NTCREATEX_SHARE_ACCESS_READ;
io.ntcreatex.in.open_disposition = NTCREATEX_DISP_OPEN;
io.ntcreatex.in.create_options = 0;
+ io.ntcreatex.in.impersonation = NTCREATEX_IMPERSONATION_ANONYMOUS;
io.ntcreatex.in.fname = "\\";
status = smb_raw_open(cli->tree, tctx, &io);
if (!NT_STATUS_IS_OK(status)) {
io.ntcreatex.in.file_attr = FILE_ATTRIBUTE_NORMAL;
io.ntcreatex.in.share_access = NTCREATEX_SHARE_ACCESS_NONE;
io.ntcreatex.in.create_options = 0;
+ io.ntcreatex.in.impersonation = NTCREATEX_IMPERSONATION_ANONYMOUS;
io.ntcreatex.in.fname = fname;
status = smb_raw_open(cli->tree, tctx, &io);
return ret;
}
+bool torture_samba3_oplock_logoff(struct torture_context *tctx)
+{
+ struct smbcli_state *cli;
+ NTSTATUS status;
+ uint16_t fnum1;
+ union smb_open io;
+ const char *fname = "testfile";
+ bool ret = false;
+ struct smbcli_request *req;
+ struct smb_echo echo_req;
+
+ if (!torture_open_connection(&cli, tctx, 0)) {
+ ret = false;
+ goto done;
+ }
+
+ smbcli_unlink(cli->tree, fname);
+
+ ZERO_STRUCT(io);
+ io.generic.level = RAW_OPEN_NTCREATEX;
+ io.ntcreatex.in.flags = NTCREATEX_FLAGS_EXTENDED;
+ io.ntcreatex.in.root_fid = 0;
+ io.ntcreatex.in.security_flags = 0;
+ io.ntcreatex.in.access_mask =
+ SEC_STD_SYNCHRONIZE | SEC_FILE_EXECUTE;
+ 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.fname = "testfile";
+ status = smb_raw_open(cli->tree, tctx, &io);
+ if (!NT_STATUS_IS_OK(status)) {
+ d_printf("first smb_open failed: %s\n", nt_errstr(status));
+ ret = false;
+ goto done;
+ }
+ fnum1 = io.ntcreatex.out.file.fnum;
+
+ /*
+ * Create a conflicting open, causing the one-second delay
+ */
+
+ req = smb_raw_open_send(cli->tree, &io);
+ if (req == NULL) {
+ d_printf("smb_raw_open_send failed\n");
+ ret = false;
+ goto done;
+ }
+
+ /*
+ * Pull the VUID from under that request. As of Nov 3, 2008 all Samba3
+ * versions (3.0, 3.2 and master) would spin sending ERRinvuid errors
+ * as long as the client is still connected.
+ */
+
+ status = smb_raw_ulogoff(cli->session);
+
+ if (!NT_STATUS_IS_OK(status)) {
+ d_printf("ulogoff failed: %s\n", nt_errstr(status));
+ ret = false;
+ goto done;
+ }
+
+ echo_req.in.repeat_count = 1;
+ echo_req.in.size = 1;
+ echo_req.in.data = (uint8_t *)"";
+
+ status = smb_raw_echo(cli->session->transport, &echo_req);
+ if (!NT_STATUS_IS_OK(status)) {
+ d_printf("smb_raw_echo returned %s\n",
+ nt_errstr(status));
+ ret = false;
+ goto done;
+ }
+
+ ret = true;
+ done:
+ return ret;
+}