ftp.nice.ch/pub/next/unix/network/system/sharity-light.0.4.s.tar.gz#/rumba.0.4.s/rumba.c

This is rumba.c in view mode; [Download] [Up]

/*
 * Name: rumba.c
 * Description: Main function and argument parsing.
 * Author: original source for smbmount: Volker Lendecke,
 *     this version: Christian Starkjohann <cs@hal.kph.tuwien.ac.at>
 * Date: 1997-01-03
 * Copyright: GNU-GPL
 * Tabsize: 4
 */


#include "syshdr.h"
#include <pwd.h>
#include <grp.h>
#include <ctype.h>
#include <netdb.h>
#include "psinode.h"
#include "my_defines.h"
#include <syslog.h>

/* ------------------------------------------------------------------------- */

int		debug_mode = 0;
char	fake_dot_in_root = 1;
char	fake_dotdot_in_root = 1;
char	rw_is_safe = 0;
char	allow_readonly = 0;
char	use_extended = 0;
char	use_syslog = 0;
int		conf_uid, conf_gid, conf_dirmode = 0777, conf_filemode = 0777;

char 	*progname;

/* ------------------------------------------------------------------------- */

static void	vlogprintf(int level, const char *format, va_list vlist)
{
char	buffer[32768];	/* should we alloc a larger chunk of virtual mem? */

	if(use_syslog){
		vsprintf(buffer, format, vlist);
		syslog(level, "%s", buffer);
	}else{
		vfprintf(stderr, format, vlist);
	}
}

/* ------------------------------------------------------------------------- */

void	dprintf(const char *format, ...)
{
va_list		vlist;

	va_start(vlist, format);
	vlogprintf(LOG_INFO, format, vlist);
	va_end(vlist);
}

/* ------------------------------------------------------------------------- */

void	eprintf(const char *format, ...)
{
va_list		vlist;

	va_start(vlist, format);
	vlogprintf(LOG_ERR, format, vlist);
	va_end(vlist);
}

/* ------------------------------------------------------------------------- */

static inline void	str_upper(char *name)
{
	while(*name){
		*name = toupper(*name);
		name ++;
	}
}

/* ------------------------------------------------------------------------- */

static void	print_version(void)
{
	printf("%s: Version 0.4 (1997-02-10)\n", progname);
	exit(0);
}

/* ------------------------------------------------------------------------- */

static void
usage(void)
{
	printf("usage: %s //server/service mount-point [options]\n", progname);
	printf("Try `%s -h' for more information\n", progname);
}

/* ------------------------------------------------------------------------- */

static void
help(void)
{
	printf("\n");
	printf("usage: %s //server/service mount-point [options]\n", progname);
	printf("\n"
		"-s servername  Netbios name of server\n"
		"-c clientname  Netbios name of client\n"
		"-U username    Username sent to server\n"
		"-u uid         uid the mounted files get\n"
		"-g gid         gid the mounted files get\n"
		"-f mode        permission the files get (octal notation)\n"
		"-d mode        permission the dirs get (octal notation)\n"
		"-C             Don't convert password to uppercase\n"
		"-P password    Use this password\n"
		"-n             Do not use any password\n"
		"               If neither -P nor -n are given, you are\n"
		"               asked for a password.\n"
		"-S             Read/write access is safe. Without this\n"
		"               option, files are closed when switching from\n"
		"               read to write or vice versa\n"
		"-w             allow setting files to read only\n"
		"-e             use getattrE and setattrE smb commands\n"
		"-F .           don\'t fake . entry in root directory\n"
		"-F ..          don\'t fake .. entry in root directory\n"
		"-h             print this help text\n"
		"-v             print version number and exit\n"
		"\n"
		"-p port        Port to connect to (used only for testing)\n"
		"-m max_xmit    max_xmit offered (used only for testing)\n"
		"-D debug-mode  activate debugging (bitmask, hex/dec/octal notation)\n"
		"               this option also forces foreground operation\n"
		"\n");
}

/* ------------------------------------------------------------------------- */

static int
extract_service(const char *service, char **server, char **share, char **root,
                char **user)
{
char service_copy[strlen(service)+1];
char *complete_service;

char *share_start;
char *root_start;
char *user_start;

static char s_server[64];
static char s_share [64];
static char s_root  [64];
static char s_user  [64];

	strcpy(service_copy, service);
	complete_service = service_copy;

	if (strlen(complete_service) < 4 || complete_service[0] != '/') {
		return -1;
	}
	while (complete_service[0] == '/') complete_service += 1;
	share_start = strchr(complete_service, '/');
	if (share_start == NULL) {
		return -1;
	}
	*share_start++ = '\0';
	root_start = strchr(share_start, '/');
	if (root_start != NULL) {
		*root_start++ = '\0';
	}
	if ((strlen(complete_service) > 63) || (strlen(share_start) > 63)) {
		eprintf("server or share too long: %s\n", service);
		return -1;
	}
	if (root_start != NULL) {
		int i;
		if (strlen(root_start) > 62) {
			eprintf("root too long: %s\n", root_start);
			return -1;
		}
		s_root[0] = '/';
		strcpy(s_root + 1, root_start);
		for (i = 0; s_root[i] != '\0'; i++) {
			if (s_root[i] == '/') {
				s_root[i] = '\\';
			}
		}
		/* i == strlen(s_root) */
		if (s_root[i-1] == '\\') {
			s_root[i-1] = '\0';
		}
	} else {
		s_root[0] = '\0';
	}
	user_start = strchr(share_start, '%');
	if (user_start != NULL) {
		user_start[0] = '\0';
		user_start += 1;
		strcpy(s_user, user_start);
	} else {
		s_user[0] = '\0';
	}

	strcpy(s_server, complete_service);
	strcpy(s_share,  share_start);

	*server = s_server;
	*share  = s_share;
	*root   = s_root;
	*user   = s_user;
	return 0;
}

/* ------------------------------------------------------------------------- */

int	main(int argc, char **argv)
{
int				opt, um, i;
struct passwd	*pwd;
struct group	*grp;
char			mountpoint_abs[MAXPATHLEN + 1];
char			hostname[MAXHOSTNAMELEN + 1];
struct			hostent *h;
int				got_password, upcase_password;
int				port = -1, max_xmit = -1;
char			server_name[17], client_name[17];
char			username[64], password[64], run_as_daemon;
char			*mount_point, *server, *share, *root, *user_dummy;
static char		root_fh[32] = {0};

	progname = argv[0];
	openlog(progname, LOG_PID, LOG_DAEMON);
	*username = *password = *server_name = *client_name = 0;
	got_password = 0;
	upcase_password = 1;
	run_as_daemon = 1;
	memset(hostname, 0, sizeof(hostname));
	if(argc < 2 || (argc == 2 && strcmp(argv[1], "-h") == 0)){
		help();
		exit(0);
	}
	if(argc == 2 && strcmp(argv[1], "-v") == 0){
		print_version();
	}
	gethostname(hostname, MAXHOSTNAMELEN);
	if (geteuid() != 0) {
		eprintf("%s must be installed suid root\n", progname);
	}
	mount_point = argv[2];
	if(extract_service(argv[1], &server, &share, &root, &user_dummy) != 0) {
		usage();
		return 1;
	}
	argv += 2;
	argc -= 2;

	if ((h = gethostbyname(server)) == NULL) {
		eprintf("%s: unknown host\n", server);
		return 1;
	}
	if(getenv("USER")){
		strcpy(username, getenv("USER"));
		str_upper(username);
	}
	if(username[0] == 0 && getenv("LOGNAME")){
		strcpy(username,getenv("LOGNAME"));
		str_upper(username);
	}

	conf_uid = getuid();
	conf_gid = getgid();
	um = umask(0);
	umask(um);
	conf_filemode = 0777 & ~um;
	conf_dirmode  = 0;

	while((opt=getopt(argc, argv, "Chewp:s:c:U:u:g:f:d:m:P:nD:F:Sv")) != EOF){
		switch(opt){
		case 'C':
			upcase_password = 0;
			break;
		case 'p':
			port = atoi(optarg);
			break;
		case 's':
			if(strlen(optarg) > 16){
				eprintf("Server name too long: %s\n", optarg);
				return 1;
			}
			strcpy(server_name, optarg);
			break;
		case 'c':
			if(strlen(optarg) > 16){
				eprintf("Client name too long: %s\n", optarg);
				return 1;
			}
			strcpy(client_name, optarg);
			break;
		case 'U':
			if(strlen(optarg) > 63){
				eprintf("Username too long: %s\n", optarg);
				return 1;
			}
			strcpy(username, optarg);
			break;
		case 'u':
			if (isdigit(optarg[0])){
				conf_uid = atoi(optarg);
			}else{
				pwd = getpwnam(optarg);
				if(pwd == NULL){
					eprintf("Unknown user: %s\n", optarg);
					return 1;
				}
				conf_uid = pwd->pw_uid;
			}
			break;
		case 'g':
			if(isdigit(optarg[0])){
				conf_gid = atoi(optarg);
			}else{
				grp = getgrnam(optarg);
				if(grp == NULL){
					eprintf("Unknown group: %s\n", optarg);
					return 1;
				}
				conf_gid = grp->gr_gid;
			}
			break;
		case 'f':
			conf_filemode = strtol(optarg, NULL, 8);
			break;
		case 'd':
			conf_dirmode = strtol(optarg, NULL, 8);
			break;
		case 'm':
			max_xmit = atoi(optarg);
			break;
		case 'P':
			strcpy(password, optarg);
			for(i=0;optarg[i]!=0;i++)
				optarg[i] = '*';
			got_password = 1;
			break;
		case 'n':
			got_password = 1;
			break;
		case 'w':
			allow_readonly = 1;
			break;
		case 'e':
			use_extended = 1;
			break;
		case 'D':
			run_as_daemon = 0;
			debug_mode = strtol(optarg, NULL, 0);
			break;
		case 'F':
			if(strcmp(optarg, ".") == 0)
				fake_dot_in_root = 0;
			else if(strcmp(optarg, "..") == 0)
				fake_dotdot_in_root = 0;
			else
				eprintf("Parameter of -F must be \".\" or \"..\"\n");
			break;
		case 'S':
			rw_is_safe = 1;
			break;
		case 'v':
			print_version();
			exit(0);
		case 'h':
			help();
			exit(0);
		default:
			return 1;
		}
	}

	if(conf_dirmode == 0){
		conf_dirmode = conf_filemode;
		conf_dirmode |= (conf_dirmode & 0444) >> 2;
	}
	if(!got_password){
		strcpy(password, getpass("Password: "));
	}
	if(upcase_password){
		str_upper(password);
	}
	
	kernel_init();
	fo_init();
	psi_init(2048, 1000, 1400);
	psi_define_root(root, (long long *)root_fh);
	if(fo_mount(server, server_name, client_name, share, root, username,
										password, max_xmit, port) != 0){
		exit(1);
	}
	if(*mount_point == '/'){		/* absolute path given? */
		strcpy(mountpoint_abs, mount_point);
	}else{
		if(getwd(mountpoint_abs) == NULL){
			mountpoint_abs[0] = 0;
		}else{
			strcat(mountpoint_abs, "/");
		}
		strcat(mountpoint_abs, mount_point);
	}
	mount_and_dispatch(mountpoint_abs, nfs_dispatch, root_fh, run_as_daemon);
	return 0;
}

These are the contents of the former NiCE NeXT User Group NeXTSTEP/OpenStep software archive, currently hosted by Netfuture.ch.