summaryrefslogtreecommitdiff
path: root/source3/nmbd/nmbd_subnetdb.c
diff options
context:
space:
mode:
authorJeremy Allison <jra@samba.org>2003-08-27 01:25:01 +0000
committerJeremy Allison <jra@samba.org>2003-08-27 01:25:01 +0000
commit9fdc1363bec6ae9a0a0f9a37130b98a92ebe8ce2 (patch)
treea3f5b31cb23487dab3c01bb3eeb1a65c5a675afe /source3/nmbd/nmbd_subnetdb.c
parent7e27147422e78125c2bb5b8115bd9084a657e084 (diff)
downloadsamba-9fdc1363bec6ae9a0a0f9a37130b98a92ebe8ce2.tar.gz
samba-9fdc1363bec6ae9a0a0f9a37130b98a92ebe8ce2.tar.bz2
samba-9fdc1363bec6ae9a0a0f9a37130b98a92ebe8ce2.zip
Fix the character set handling properly in nmbd. Also fix bug where
iconv wasn't re-initialised on reading of "charset" parameters. This caused workgroup name to be set incorrectly if it contained an extended character. Jeremy. (This used to be commit 84ae44678a6c59c999bc1023fdd9b7ad87f4ec18)
Diffstat (limited to 'source3/nmbd/nmbd_subnetdb.c')
-rw-r--r--source3/nmbd/nmbd_subnetdb.c395
1 files changed, 189 insertions, 206 deletions
diff --git a/source3/nmbd/nmbd_subnetdb.c b/source3/nmbd/nmbd_subnetdb.c
index 6296826425..02a91f2760 100644
--- a/source3/nmbd/nmbd_subnetdb.c
+++ b/source3/nmbd/nmbd_subnetdb.c
@@ -63,28 +63,27 @@ static void add_subnet(struct subnet_record *subrec)
* ************************************************************************** **
*/
static int namelist_entry_compare( ubi_trItemPtr Item, ubi_trNodePtr Node )
- {
- struct name_record *NR = (struct name_record *)Node;
-
- if( DEBUGLVL( 10 ) )
- {
- struct nmb_name *Iname = (struct nmb_name *)Item;
+{
+ struct name_record *NR = (struct name_record *)Node;
- Debug1( "nmbd_subnetdb:namelist_entry_compare()\n" );
- Debug1( "%d == memcmp( \"%s\", \"%s\", %d )\n",
- memcmp( Item, &(NR->name), sizeof(struct nmb_name) ),
- nmb_namestr(Iname), nmb_namestr(&NR->name), (int)sizeof(struct nmb_name) );
- }
+ if( DEBUGLVL( 10 ) ) {
+ struct nmb_name *Iname = (struct nmb_name *)Item;
- return( memcmp( Item, &(NR->name), sizeof(struct nmb_name) ) );
- } /* namelist_entry_compare */
+ Debug1( "nmbd_subnetdb:namelist_entry_compare()\n" );
+ Debug1( "%d == memcmp( \"%s\", \"%s\", %d )\n",
+ memcmp( Item, &(NR->name), sizeof(struct nmb_name) ),
+ nmb_namestr(Iname), nmb_namestr(&NR->name), (int)sizeof(struct nmb_name) );
+ }
+ return( memcmp( Item, &(NR->name), sizeof(struct nmb_name) ) );
+}
/****************************************************************************
stop listening on a subnet
we don't free the record as we don't have proper reference counting for it
yet and it may be in use by a response record
****************************************************************************/
+
void close_subnet(struct subnet_record *subrec)
{
DLIST_REMOVE(subnetlist, subrec);
@@ -99,8 +98,6 @@ void close_subnet(struct subnet_record *subrec)
}
}
-
-
/****************************************************************************
Create a subnet entry.
****************************************************************************/
@@ -109,102 +106,90 @@ static struct subnet_record *make_subnet(const char *name, enum subnet_type type
struct in_addr myip, struct in_addr bcast_ip,
struct in_addr mask_ip)
{
- struct subnet_record *subrec = NULL;
- int nmb_sock, dgram_sock;
-
- /* Check if we are creating a non broadcast subnet - if so don't create
- sockets.
- */
-
- if(type != NORMAL_SUBNET)
- {
- nmb_sock = -1;
- dgram_sock = -1;
- }
- else
- {
- /*
- * Attempt to open the sockets on port 137/138 for this interface
- * and bind them.
- * Fail the subnet creation if this fails.
- */
-
- if((nmb_sock = open_socket_in(SOCK_DGRAM, global_nmb_port,0, myip.s_addr,True)) == -1)
- {
- if( DEBUGLVL( 0 ) )
- {
- Debug1( "nmbd_subnetdb:make_subnet()\n" );
- Debug1( " Failed to open nmb socket on interface %s ", inet_ntoa(myip) );
- Debug1( "for port %d. ", global_nmb_port );
- Debug1( "Error was %s\n", strerror(errno) );
- }
- return NULL;
- }
-
- if((dgram_sock = open_socket_in(SOCK_DGRAM,DGRAM_PORT,3, myip.s_addr,True)) == -1)
- {
- if( DEBUGLVL( 0 ) )
- {
- Debug1( "nmbd_subnetdb:make_subnet()\n" );
- Debug1( " Failed to open dgram socket on interface %s ", inet_ntoa(myip) );
- Debug1( "for port %d. ", DGRAM_PORT );
- Debug1( "Error was %s\n", strerror(errno) );
- }
- return NULL;
- }
-
- /* Make sure we can broadcast from these sockets. */
- set_socket_options(nmb_sock,"SO_BROADCAST");
- set_socket_options(dgram_sock,"SO_BROADCAST");
-
- }
-
- subrec = (struct subnet_record *)malloc(sizeof(*subrec));
-
- if (!subrec)
- {
- DEBUG(0,("make_subnet: malloc fail !\n"));
- close(nmb_sock);
- close(dgram_sock);
- return(NULL);
- }
+ struct subnet_record *subrec = NULL;
+ int nmb_sock, dgram_sock;
+
+ /* Check if we are creating a non broadcast subnet - if so don't create
+ sockets. */
+
+ if(type != NORMAL_SUBNET) {
+ nmb_sock = -1;
+ dgram_sock = -1;
+ } else {
+ /*
+ * Attempt to open the sockets on port 137/138 for this interface
+ * and bind them.
+ * Fail the subnet creation if this fails.
+ */
+
+ if((nmb_sock = open_socket_in(SOCK_DGRAM, global_nmb_port,0, myip.s_addr,True)) == -1) {
+ if( DEBUGLVL( 0 ) ) {
+ Debug1( "nmbd_subnetdb:make_subnet()\n" );
+ Debug1( " Failed to open nmb socket on interface %s ", inet_ntoa(myip) );
+ Debug1( "for port %d. ", global_nmb_port );
+ Debug1( "Error was %s\n", strerror(errno) );
+ }
+ return NULL;
+ }
+
+ if((dgram_sock = open_socket_in(SOCK_DGRAM,DGRAM_PORT,3, myip.s_addr,True)) == -1) {
+ if( DEBUGLVL( 0 ) ) {
+ Debug1( "nmbd_subnetdb:make_subnet()\n" );
+ Debug1( " Failed to open dgram socket on interface %s ", inet_ntoa(myip) );
+ Debug1( "for port %d. ", DGRAM_PORT );
+ Debug1( "Error was %s\n", strerror(errno) );
+ }
+ return NULL;
+ }
+
+ /* Make sure we can broadcast from these sockets. */
+ set_socket_options(nmb_sock,"SO_BROADCAST");
+ set_socket_options(dgram_sock,"SO_BROADCAST");
+ }
+
+ subrec = (struct subnet_record *)malloc(sizeof(*subrec));
+ if (!subrec) {
+ DEBUG(0,("make_subnet: malloc fail !\n"));
+ close(nmb_sock);
+ close(dgram_sock);
+ return(NULL);
+ }
- memset( (char *)subrec, '\0', sizeof(*subrec) );
- (void)ubi_trInitTree( subrec->namelist,
- namelist_entry_compare,
- ubi_trOVERWRITE );
-
- if((subrec->subnet_name = strdup(name)) == NULL)
- {
- DEBUG(0,("make_subnet: malloc fail for subnet name !\n"));
- close(nmb_sock);
- close(dgram_sock);
- ZERO_STRUCTP(subrec);
- SAFE_FREE(subrec);
- return(NULL);
- }
-
- DEBUG(2, ("making subnet name:%s ", name ));
- DEBUG(2, ("Broadcast address:%s ", inet_ntoa(bcast_ip)));
- DEBUG(2, ("Subnet mask:%s\n", inet_ntoa(mask_ip)));
+ memset( (char *)subrec, '\0', sizeof(*subrec) );
+ (void)ubi_trInitTree( subrec->namelist,
+ namelist_entry_compare,
+ ubi_trOVERWRITE );
+
+ if((subrec->subnet_name = strdup(name)) == NULL) {
+ DEBUG(0,("make_subnet: malloc fail for subnet name !\n"));
+ close(nmb_sock);
+ close(dgram_sock);
+ ZERO_STRUCTP(subrec);
+ SAFE_FREE(subrec);
+ return(NULL);
+ }
+
+ DEBUG(2, ("making subnet name:%s ", name ));
+ DEBUG(2, ("Broadcast address:%s ", inet_ntoa(bcast_ip)));
+ DEBUG(2, ("Subnet mask:%s\n", inet_ntoa(mask_ip)));
- subrec->namelist_changed = False;
- subrec->work_changed = False;
+ subrec->namelist_changed = False;
+ subrec->work_changed = False;
- subrec->bcast_ip = bcast_ip;
- subrec->mask_ip = mask_ip;
- subrec->myip = myip;
- subrec->type = type;
- subrec->nmb_sock = nmb_sock;
- subrec->dgram_sock = dgram_sock;
+ subrec->bcast_ip = bcast_ip;
+ subrec->mask_ip = mask_ip;
+ subrec->myip = myip;
+ subrec->type = type;
+ subrec->nmb_sock = nmb_sock;
+ subrec->dgram_sock = dgram_sock;
- return subrec;
+ return subrec;
}
-
/****************************************************************************
Create a normal subnet
**************************************************************************/
+
struct subnet_record *make_normal_subnet(struct interface *iface)
{
struct subnet_record *subrec;
@@ -217,100 +202,99 @@ struct subnet_record *make_normal_subnet(struct interface *iface)
return subrec;
}
-
/****************************************************************************
Create subnet entries.
**************************************************************************/
BOOL create_subnets(void)
{
- int num_interfaces = iface_count();
- int i;
- struct in_addr unicast_ip, ipzero;
- extern struct in_addr loopback_ip;
-
- if(num_interfaces == 0) {
- DEBUG(0,("create_subnets: No local interfaces !\n"));
- DEBUG(0,("create_subnets: Waiting for an interface to appear ...\n"));
- while (iface_count() == 0) {
- sleep(5);
- load_interfaces();
- }
- }
-
- num_interfaces = iface_count();
-
- /*
- * Create subnets from all the local interfaces and thread them onto
- * the linked list.
- */
-
- for (i = 0 ; i < num_interfaces; i++)
- {
- struct interface *iface = get_interface(i);
-
- /*
- * We don't want to add a loopback interface, in case
- * someone has added 127.0.0.1 for smbd, nmbd needs to
- * ignore it here. JRA.
- */
-
- if (ip_equal(iface->ip, loopback_ip)) {
- DEBUG(2,("create_subnets: Ignoring loopback interface.\n" ));
- continue;
- }
-
- if (!make_normal_subnet(iface)) return False;
- }
-
- if (lp_we_are_a_wins_server()) {
- /* Pick the first interface ip address as the WINS server ip. */
- unicast_ip = *iface_n_ip(0);
- } else {
- /* note that we do not set the wins server IP here. We just
- set it at zero and let the wins registration code cope
- with getting the IPs right for each packet */
- zero_ip(&unicast_ip);
- }
-
- /*
- * Create the unicast and remote broadcast subnets.
- * Don't put these onto the linked list.
- * The ip address of the unicast subnet is set to be
- * the WINS server address, if it exists, or ipzero if not.
- */
-
- unicast_subnet = make_subnet( "UNICAST_SUBNET", UNICAST_SUBNET,
- unicast_ip, unicast_ip, unicast_ip);
-
- zero_ip(&ipzero);
-
- remote_broadcast_subnet = make_subnet( "REMOTE_BROADCAST_SUBNET",
- REMOTE_BROADCAST_SUBNET,
- ipzero, ipzero, ipzero);
-
- if((unicast_subnet == NULL) || (remote_broadcast_subnet == NULL))
- return False;
-
- /*
- * If we are WINS server, create the WINS_SERVER_SUBNET - don't put on
- * the linked list.
- */
-
- if (lp_we_are_a_wins_server())
- {
- if( (wins_server_subnet = make_subnet( "WINS_SERVER_SUBNET",
- WINS_SERVER_SUBNET,
- ipzero, ipzero, ipzero )) == NULL )
- return False;
- }
-
- return True;
+ int num_interfaces = iface_count();
+ int i;
+ struct in_addr unicast_ip, ipzero;
+ extern struct in_addr loopback_ip;
+
+ if(num_interfaces == 0) {
+ DEBUG(0,("create_subnets: No local interfaces !\n"));
+ DEBUG(0,("create_subnets: Waiting for an interface to appear ...\n"));
+ while (iface_count() == 0) {
+ sleep(5);
+ load_interfaces();
+ }
+ }
+
+ num_interfaces = iface_count();
+
+ /*
+ * Create subnets from all the local interfaces and thread them onto
+ * the linked list.
+ */
+
+ for (i = 0 ; i < num_interfaces; i++) {
+ struct interface *iface = get_interface(i);
+
+ /*
+ * We don't want to add a loopback interface, in case
+ * someone has added 127.0.0.1 for smbd, nmbd needs to
+ * ignore it here. JRA.
+ */
+
+ if (ip_equal(iface->ip, loopback_ip)) {
+ DEBUG(2,("create_subnets: Ignoring loopback interface.\n" ));
+ continue;
+ }
+
+ if (!make_normal_subnet(iface))
+ return False;
+ }
+
+ if (lp_we_are_a_wins_server()) {
+ /* Pick the first interface ip address as the WINS server ip. */
+ unicast_ip = *iface_n_ip(0);
+ } else {
+ /* note that we do not set the wins server IP here. We just
+ set it at zero and let the wins registration code cope
+ with getting the IPs right for each packet */
+ zero_ip(&unicast_ip);
+ }
+
+ /*
+ * Create the unicast and remote broadcast subnets.
+ * Don't put these onto the linked list.
+ * The ip address of the unicast subnet is set to be
+ * the WINS server address, if it exists, or ipzero if not.
+ */
+
+ unicast_subnet = make_subnet( "UNICAST_SUBNET", UNICAST_SUBNET,
+ unicast_ip, unicast_ip, unicast_ip);
+
+ zero_ip(&ipzero);
+
+ remote_broadcast_subnet = make_subnet( "REMOTE_BROADCAST_SUBNET",
+ REMOTE_BROADCAST_SUBNET,
+ ipzero, ipzero, ipzero);
+
+ if((unicast_subnet == NULL) || (remote_broadcast_subnet == NULL))
+ return False;
+
+ /*
+ * If we are WINS server, create the WINS_SERVER_SUBNET - don't put on
+ * the linked list.
+ */
+
+ if (lp_we_are_a_wins_server()) {
+ if( (wins_server_subnet = make_subnet( "WINS_SERVER_SUBNET",
+ WINS_SERVER_SUBNET,
+ ipzero, ipzero, ipzero )) == NULL )
+ return False;
+ }
+
+ return True;
}
/*******************************************************************
Function to tell us if we can use the unicast subnet.
******************************************************************/
+
BOOL we_are_a_wins_client(void)
{
if (wins_srv_count() > 0) {
@@ -326,12 +310,12 @@ Access function used by NEXT_SUBNET_INCLUDING_UNICAST
struct subnet_record *get_next_subnet_maybe_unicast(struct subnet_record *subrec)
{
- if(subrec == unicast_subnet)
- return NULL;
- else if((subrec->next == NULL) && we_are_a_wins_client())
- return unicast_subnet;
- else
- return subrec->next;
+ if(subrec == unicast_subnet)
+ return NULL;
+ else if((subrec->next == NULL) && we_are_a_wins_client())
+ return unicast_subnet;
+ else
+ return subrec->next;
}
/*******************************************************************
@@ -343,19 +327,18 @@ struct subnet_record *get_next_subnet_maybe_unicast(struct subnet_record *subrec
struct subnet_record *get_next_subnet_maybe_unicast_or_wins_server(struct subnet_record *subrec)
{
- if(subrec == unicast_subnet)
- {
- if(wins_server_subnet)
- return wins_server_subnet;
- else
- return NULL;
- }
-
- if(wins_server_subnet && subrec == wins_server_subnet)
- return NULL;
-
- if((subrec->next == NULL) && we_are_a_wins_client())
- return unicast_subnet;
- else
- return subrec->next;
+ if(subrec == unicast_subnet) {
+ if(wins_server_subnet)
+ return wins_server_subnet;
+ else
+ return NULL;
+ }
+
+ if(wins_server_subnet && subrec == wins_server_subnet)
+ return NULL;
+
+ if((subrec->next == NULL) && we_are_a_wins_client())
+ return unicast_subnet;
+ else
+ return subrec->next;
}