⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 locktest.c

📁 samba最新软件
💻 C
📖 第 1 页 / 共 2 页
字号:
/*    Unix SMB/CIFS implementation.   randomised byte range lock tester   Copyright (C) Andrew Tridgell 1999      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 3 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, see <http://www.gnu.org/licenses/>.*/#include "includes.h"#include "lib/cmdline/popt_common.h"#include "lib/events/events.h"#include "system/filesys.h"#include "system/time.h"#include "pstring.h"#include "auth/credentials/credentials.h"#include "auth/gensec/gensec.h"#include "libcli/libcli.h"#include "param/param.h"#include "dynconfig/dynconfig.h"#include "libcli/resolve/resolve.h"static int numops = 1000;static int showall;static int analyze;static int hide_unlock_fails;static int use_oplocks;static uint_t lock_range = 100;static uint_t lock_base = 0;static uint_t min_length = 0;static int exact_error_codes;static int zero_zero;#define FILENAME "\\locktest.dat"#define READ_PCT 50#define LOCK_PCT 45#define UNLOCK_PCT 70#define RANGE_MULTIPLE 1#define NSERVERS 2#define NCONNECTIONS 2#define NFILES 2#define LOCK_TIMEOUT 0static struct cli_credentials *servers[NSERVERS];enum lock_op {OP_LOCK, OP_UNLOCK, OP_REOPEN};struct record {	enum lock_op lock_op;	enum brl_type lock_type;	char conn, f;	uint64_t start, len;	char needed;	uint16_t pid;};#define PRESETS 0#if PRESETSstatic struct record preset[] = {{OP_LOCK, WRITE_LOCK, 0, 0, 2, 0, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 0, 0, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 3, 0, 1},{OP_UNLOCK, 0       , 0, 0, 2, 0, 1},{OP_REOPEN, 0, 0, 0, 0, 0, 1},{OP_LOCK, READ_LOCK, 0, 0, 2, 0, 1},{OP_LOCK, READ_LOCK, 0, 0, 1, 1, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 0, 0, 1},{OP_REOPEN, 0, 0, 0, 0, 0, 1},{OP_LOCK, READ_LOCK, 0, 0, 2, 0, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 3, 1, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 0, 0, 1},{OP_REOPEN, 0, 0, 0, 0, 0, 1},{OP_LOCK, READ_LOCK, 0, 0, 2, 0, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 1, 1, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 0, 0, 1},{OP_REOPEN, 0, 0, 0, 0, 0, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 2, 0, 1},{OP_LOCK, READ_LOCK, 0, 0, 1, 1, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 0, 0, 1},{OP_REOPEN, 0, 0, 0, 0, 0, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 2, 0, 1},{OP_LOCK, READ_LOCK, 0, 0, 3, 1, 1},{OP_LOCK, WRITE_LOCK, 0, 0, 0, 0, 1},{OP_REOPEN, 0, 0, 0, 0, 0, 1},};#endifstatic struct record *recorded;/***************************************************** return a connection to a server*******************************************************/static struct smbcli_state *connect_one(struct event_context *ev,					struct loadparm_context *lp_ctx,					char *share, int snum, int conn){	struct smbcli_state *c;	fstring server, myname;	NTSTATUS status;	int retries = 10;	struct smbcli_options options;	lp_smbcli_options(lp_ctx, &options);	printf("connect_one(%s, %d, %d)\n", share, snum, conn);	fstrcpy(server,share+2);	share = strchr_m(server,'\\');	if (!share) return NULL;	*share = 0;	share++;	if (snum == 0) {		char **unc_list = NULL;		int num_unc_names;		const char *p;		p = lp_parm_string(lp_ctx, NULL, "torture", "unclist");		if (p) {			char *h, *s;			unc_list = file_lines_load(p, &num_unc_names, NULL);			if (!unc_list || num_unc_names <= 0) {				printf("Failed to load unc names list from '%s'\n", p);				exit(1);			}			if (!smbcli_parse_unc(unc_list[conn % num_unc_names],					      NULL, &h, &s)) {				printf("Failed to parse UNC name %s\n",				       unc_list[conn % num_unc_names]);				exit(1);			}			fstrcpy(server, h);			fstrcpy(share, s);		}	}	slprintf(myname,sizeof(myname), "lock-%u-%u", getpid(), snum);	cli_credentials_set_workstation(servers[snum], myname, CRED_SPECIFIED);	do {		printf("\\\\%s\\%s\n", server, share);		status = smbcli_full_connection(NULL, &c, 						server, 						lp_smb_ports(lp_ctx),						share, NULL,						servers[snum], 						lp_resolve_context(lp_ctx),						ev, &options);		if (!NT_STATUS_IS_OK(status)) {			sleep(2);		}	} while (!NT_STATUS_IS_OK(status) && retries--);	if (!NT_STATUS_IS_OK(status)) {		return NULL;	}	return c;}static void reconnect(struct event_context *ev,		      struct loadparm_context *lp_ctx,		      struct smbcli_state *cli[NSERVERS][NCONNECTIONS], int fnum[NSERVERS][NCONNECTIONS][NFILES],		      char *share[NSERVERS]){	int server, conn, f;	for (server=0;server<NSERVERS;server++)	for (conn=0;conn<NCONNECTIONS;conn++) {		if (cli[server][conn]) {			for (f=0;f<NFILES;f++) {				if (fnum[server][conn][f] != -1) {					smbcli_close(cli[server][conn]->tree, fnum[server][conn][f]);					fnum[server][conn][f] = -1;				}			}			talloc_free(cli[server][conn]);		}		cli[server][conn] = connect_one(ev, lp_ctx, share[server], 						server, conn);		if (!cli[server][conn]) {			DEBUG(0,("Failed to connect to %s\n", share[server]));			exit(1);		}	}}static bool test_one(struct smbcli_state *cli[NSERVERS][NCONNECTIONS], 		     int fnum[NSERVERS][NCONNECTIONS][NFILES],		     struct record *rec){	uint_t conn = rec->conn;	uint_t f = rec->f;	uint64_t start = rec->start;	uint64_t len = rec->len;	enum brl_type op = rec->lock_type;	int server;	bool ret[NSERVERS];	NTSTATUS status[NSERVERS];	switch (rec->lock_op) {	case OP_LOCK:		/* set a lock */		for (server=0;server<NSERVERS;server++) {			NTSTATUS res;			struct smbcli_tree *tree=cli[server][conn]->tree;			int fn=fnum[server][conn][f];			if (!(tree->session->transport->negotiate.capabilities & CAP_LARGE_FILES)) {				res=smbcli_lock(tree, fn, start, len, LOCK_TIMEOUT, rec->lock_op);			} else {				union smb_lock parms;				int ltype;				struct smb_lock_entry lock[1];				parms.lockx.level = RAW_LOCK_LOCKX;				parms.lockx.in.file.fnum = fn;					ltype = (rec->lock_op == READ_LOCK? 1 : 0);				ltype |= LOCKING_ANDX_LARGE_FILES;				parms.lockx.in.mode = ltype;				parms.lockx.in.timeout = LOCK_TIMEOUT;				parms.lockx.in.ulock_cnt = 0;				parms.lockx.in.lock_cnt = 1;				lock[0].pid = rec->pid;				lock[0].offset = start;				lock[0].count = len;				parms.lockx.in.locks = &lock[0];				res = smb_raw_lock(tree, &parms);			}			ret[server] = NT_STATUS_IS_OK(res); 			status[server] = smbcli_nt_error(cli[server][conn]->tree);			if (!exact_error_codes && 			    NT_STATUS_EQUAL(status[server], 					    NT_STATUS_FILE_LOCK_CONFLICT)) {				status[server] = NT_STATUS_LOCK_NOT_GRANTED;			}		}		if (showall || !NT_STATUS_EQUAL(status[0],status[1])) {			printf("lock   conn=%u f=%u range=%.0f(%.0f) op=%s -> %s:%s\n",			       conn, f, 			       (double)start, (double)len,			       op==READ_LOCK?"READ_LOCK":"WRITE_LOCK",			       nt_errstr(status[0]), nt_errstr(status[1]));		}		if (!NT_STATUS_EQUAL(status[0],status[1])) return false;		break;			case OP_UNLOCK:		/* unset a lock */		for (server=0;server<NSERVERS;server++) {			NTSTATUS res;			struct smbcli_tree *tree=cli[server][conn]->tree;			int fn=fnum[server][conn][f];			if (!(tree->session->transport->negotiate.capabilities & CAP_LARGE_FILES)) {				res=smbcli_unlock(tree, fn, start, len);			} else {				union smb_lock parms;				struct smb_lock_entry lock[1];				parms.lockx.level = RAW_LOCK_LOCKX;				parms.lockx.in.file.fnum = fn;				parms.lockx.in.mode = LOCKING_ANDX_LARGE_FILES;				parms.lockx.in.timeout = 0;				parms.lockx.in.ulock_cnt = 1;				parms.lockx.in.lock_cnt = 0;				lock[0].pid = rec->pid;				lock[0].count = len;				lock[0].offset = start;				parms.lockx.in.locks = &lock[0];				res = smb_raw_lock(tree, &parms);			}			ret[server] = NT_STATUS_IS_OK(res);			status[server] = smbcli_nt_error(cli[server][conn]->tree);		}		if (showall || 		    (!hide_unlock_fails && !NT_STATUS_EQUAL(status[0],status[1]))) {			printf("unlock conn=%u f=%u range=%.0f(%.0f)       -> %s:%s\n",			       conn, f, 			       (double)start, (double)len,			       nt_errstr(status[0]), nt_errstr(status[1]));		}		if (!hide_unlock_fails && !NT_STATUS_EQUAL(status[0],status[1])) 			return false;		break;	case OP_REOPEN:		/* reopen the file */		for (server=0;server<NSERVERS;server++) {			smbcli_close(cli[server][conn]->tree, fnum[server][conn][f]);			fnum[server][conn][f] = -1;		}		for (server=0;server<NSERVERS;server++) {			fnum[server][conn][f] = smbcli_open(cli[server][conn]->tree, FILENAME,							 O_RDWR|O_CREAT,							 DENY_NONE);			if (fnum[server][conn][f] == -1) {				printf("failed to reopen on share%d\n", server);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -