summaryrefslogtreecommitdiff
path: root/source3/libsmb/libsmbclient.c
diff options
context:
space:
mode:
Diffstat (limited to 'source3/libsmb/libsmbclient.c')
-rw-r--r--source3/libsmb/libsmbclient.c207
1 files changed, 44 insertions, 163 deletions
diff --git a/source3/libsmb/libsmbclient.c b/source3/libsmb/libsmbclient.c
index f74a0be7f3..440527cd9d 100644
--- a/source3/libsmb/libsmbclient.c
+++ b/source3/libsmb/libsmbclient.c
@@ -52,82 +52,6 @@ extern BOOL in_client;
*/
static int smbc_initialized = 0;
-static int
-hex2int( unsigned int _char )
-{
- if ( _char >= 'A' && _char <='F')
- return _char - 'A' + 10;
- if ( _char >= 'a' && _char <='f')
- return _char - 'a' + 10;
- if ( _char >= '0' && _char <='9')
- return _char - '0';
- return -1;
-}
-
-static void
-decode_urlpart(char *segment)
-{
- int old_length = strlen(segment);
- int new_length = 0;
- int new_length2 = 0;
- int i = 0;
- pstring new_segment;
- char *new_usegment = 0;
-
- if ( !old_length ) {
- return;
- }
-
- /* make a copy of the old one */
- new_usegment = (char*)malloc( old_length * 3 + 1 );
-
- while( i < old_length ) {
- int bReencode = False;
- unsigned char character = segment[ i++ ];
- if ((character <= ' ') || (character > 127))
- bReencode = True;
-
- new_usegment [ new_length2++ ] = character;
- if (character == '%' ) {
- int a = i+1 < old_length ? hex2int( segment[i] ) : -1;
- int b = i+1 < old_length ? hex2int( segment[i+1] ) : -1;
- if ((a == -1) || (b == -1)) { /* Only replace if sequence is valid */
- /* Contains stray %, make sure to re-encode! */
- bReencode = True;
- } else {
- /* Valid %xx sequence */
- character = a * 16 + b; /* Replace with value of %dd */
- if (!character)
- break; /* Stop at %00 */
-
- new_usegment [ new_length2++ ] = (unsigned char) segment[i++];
- new_usegment [ new_length2++ ] = (unsigned char) segment[i++];
- }
- }
- if (bReencode) {
- unsigned int c = character / 16;
- new_length2--;
- new_usegment [ new_length2++ ] = '%';
-
- c += (c > 9) ? ('A' - 10) : '0';
- new_usegment[ new_length2++ ] = c;
-
- c = character % 16;
- c += (c > 9) ? ('A' - 10) : '0';
- new_usegment[ new_length2++ ] = c;
- }
-
- new_segment [ new_length++ ] = character;
- }
- new_segment [ new_length ] = 0;
-
- /* this assumes (very safely) that removing %aa sequences
- only shortens the string */
- strncpy(segment, new_segment, old_length);
-
- free(new_usegment);
-}
-
/*
* Function to parse a path and turn it into components
*
@@ -173,7 +97,7 @@ smbc_parse_path(SMBCCTX *context, const char *fname, char *server, char *share,
p += 2; /* Skip the // or \\ */
if (*p == (char)0)
- goto decoding;
+ return 0;
if (*p == '/') {
@@ -234,7 +158,7 @@ smbc_parse_path(SMBCCTX *context, const char *fname, char *server, char *share,
}
- if (*p == (char)0) goto decoding; /* That's it ... */
+ if (*p == (char)0) return 0; /* That's it ... */
if (!next_token(&p, share, "/", sizeof(fstring))) {
@@ -246,13 +170,6 @@ smbc_parse_path(SMBCCTX *context, const char *fname, char *server, char *share,
all_string_sub(path, "/", "\\", 0);
- decoding:
- decode_urlpart(path);
- decode_urlpart(server);
- decode_urlpart(share);
- decode_urlpart(user);
- decode_urlpart(password);
-
return 0;
}
@@ -1475,47 +1392,9 @@ dir_list_fn(file_info *finfo, const char *mask, void *state)
}
-
-/* Return the IP address and workgroup of a master browser on the
- network. */
-
-static BOOL find_master_ip_bcast(pstring workgroup, struct in_addr *server_ip)
-{
- struct in_addr *ip_list;
- int i, count;
-
- /* Go looking for workgroups by broadcasting on the local network */
-
- if (!name_resolve_bcast(MSBROWSE, 1, &ip_list, &count)) {
- return False;
- }
-
- for (i = count-1; i < count; i++) {
- static fstring name;
-
- DEBUG(0, ("name_status_find %d %s\n", i, inet_ntoa(ip_list[i])));
-
- if (!name_status_find("*", 0, 0x1d, ip_list[i], name))
- continue;
-
- if (!find_master_ip(name, server_ip))
- continue;
-
- pstrcpy(workgroup, name);
-
- DEBUG(4, ("found master browser %s, %s\n",
- name, inet_ntoa(ip_list[i])));
-
- return True;
- }
-
- return False;
-}
-
static SMBCFILE *smbc_opendir_ctx(SMBCCTX *context, const char *fname)
{
- fstring server, share, user, password;
- pstring workgroup;
+ fstring server, share, user, password, workgroup;
pstring path;
SMBCSRV *srv = NULL;
SMBCFILE *dir = NULL;
@@ -1524,31 +1403,28 @@ static SMBCFILE *smbc_opendir_ctx(SMBCCTX *context, const char *fname)
if (!context || !context->internal ||
!context->internal->_initialized) {
- fprintf(stderr, "no valid context\n");
errno = EINVAL;
return NULL;
}
if (!fname) {
- fprintf(stderr, "no valid fname\n");
+
errno = EINVAL;
return NULL;
}
if (smbc_parse_path(context, fname, server, share, path, user, password)) {
- fprintf(stderr, "no valid path\n");
+
errno = EINVAL;
return NULL;
}
- fprintf(stderr, "parsed path: fname='%s' server='%s' share='%s' path='%s'\n", fname, server, share, path);
-
if (user[0] == (char)0) fstrcpy(user, context->user);
- pstrcpy(workgroup, context->workgroup);
+ fstrcpy(workgroup, context->workgroup);
dir = malloc(sizeof(*dir));
@@ -1569,12 +1445,9 @@ static SMBCFILE *smbc_opendir_ctx(SMBCCTX *context, const char *fname)
dir->dir_list = dir->dir_next = dir->dir_end = NULL;
if (server[0] == (char)0) {
- struct in_addr server_ip;
-
- fprintf(stderr, "empty server\n");
if (share[0] != (char)0 || path[0] != (char)0) {
- fprintf(stderr, "share %d path %d\n", share[0], path[0]);
+
errno = EINVAL;
if (dir) {
SAFE_FREE(dir->fname);
@@ -1588,40 +1461,48 @@ static SMBCFILE *smbc_opendir_ctx(SMBCCTX *context, const char *fname)
/* first try to get the LMB for our workgroup, and if that fails, */
/* try the DMB */
- pstrcpy(workgroup, lp_workgroup());
+ if (!(resolve_name(context->workgroup, &rem_ip, 0x1d) ||
+ resolve_name(context->workgroup, &rem_ip, 0x1b))) {
+
+ errno = EINVAL; /* Something wrong with smb.conf? */
+ return NULL;
- if (!find_master_ip(lp_workgroup(), &server_ip)) {
- DEBUG(4, ("Unable to find master browser for workgroup %s\n",
- workgroup));
- if (!find_master_ip_bcast(workgroup, &server_ip)) {
- DEBUG(4, ("Unable to find master browser by "
- "broadcast\n"));
- errno = ENOENT;
+ }
+
+ dir->dir_type = SMBC_WORKGROUP;
+
+ /* find the name of the server ... */
+
+ if (!name_status_find("*", 0, 0, rem_ip, server)) {
+
+ DEBUG(0,("Could not get the name of local/domain master browser for server %s\n", server));
+ errno = EINVAL;
return NULL;
- }
- }
-
- /*
- * Get a connection to IPC$ on the server if we do not already have one
- */
-
- srv = smbc_server(context, inet_ntoa(server_ip), "IPC$", workgroup, user, password);
-
- if (!srv) {
-
- if (dir) {
- SAFE_FREE(dir->fname);
- SAFE_FREE(dir);
- }
- return NULL;
- }
-
+
+ }
+
+ /*
+ * Get a connection to IPC$ on the server if we do not already have one
+ */
+
+ srv = smbc_server(context, server, "IPC$", workgroup, user, password);
+
+ if (!srv) {
+
+ if (dir) {
+ SAFE_FREE(dir->fname);
+ SAFE_FREE(dir);
+ }
+
+ return NULL;
+
+ }
+
dir->srv = srv;
- dir->dir_type = SMBC_WORKGROUP;
/* Now, list the stuff ... */
- if (!cli_NetServerEnum(&srv->cli, workgroup, SV_TYPE_DOMAIN_ENUM, list_fn,
+ if (!cli_NetServerEnum(&srv->cli, workgroup, 0x80000000, list_fn,
(void *)dir)) {
if (dir) {
@@ -2691,7 +2572,7 @@ SMBCCTX * smbc_init_context(SMBCCTX * context)
/* Do we still need this ? */
DEBUGLEVEL = 10;
- setup_logging( "libsmbclient", True);
+ setup_logging( "libsmbclient", False);
/* Here we would open the smb.conf file if needed ... */