2 Unix SMB/Netbios implementation.
4 NBT netbios routines and daemon - version 2
6 Copyright (C) Jeremy Allison 1994-1998
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
26 #define WINS_LIST "wins.dat"
28 extern int DEBUGLEVEL;
29 extern struct in_addr ipzero;
31 /****************************************************************************
32 Determine if this packet should be allocated to the WINS server.
33 *****************************************************************************/
35 BOOL packet_is_for_wins_server(struct packet_struct *packet)
37 struct nmb_packet *nmb = &packet->packet.nmb;
39 /* Only unicast packets go to a WINS server. */
40 if((wins_server_subnet == NULL) || (nmb->header.nm_flags.bcast == True))
42 DEBUG(10, ("packet_is_for_wins_server: failing WINS test #1.\n"));
46 /* Check for node status requests. */
47 if (nmb->question.question_type != QUESTION_TYPE_NB_QUERY)
50 switch(nmb->header.opcode)
53 * A WINS server issues WACKS, not receives them.
56 DEBUG(10, ("packet_is_for_wins_server: failing WINS test #2 (WACK).\n"));
59 * A WINS server only processes registration and
60 * release requests, not responses.
62 case NMB_NAME_REG_OPCODE:
63 case NMB_NAME_MULTIHOMED_REG_OPCODE:
64 case NMB_NAME_REFRESH_OPCODE_8: /* ambiguity in rfc1002 about which is correct. */
65 case NMB_NAME_REFRESH_OPCODE_9: /* WinNT uses 8 by default. */
66 if(nmb->header.response)
68 DEBUG(10, ("packet_is_for_wins_server: failing WINS test #3 (response = 1).\n"));
73 case NMB_NAME_RELEASE_OPCODE:
74 if(nmb->header.response)
76 DEBUG(10, ("packet_is_for_wins_server: failing WINS test #4 (response = 1).\n"));
82 * Only process unicast name queries with rd = 1.
84 case NMB_NAME_QUERY_OPCODE:
85 if(!nmb->header.response && !nmb->header.nm_flags.recursion_desired)
87 DEBUG(10, ("packet_is_for_wins_server: failing WINS test #5 (response = 1).\n"));
96 /****************************************************************************
97 Utility function to decide what ttl to give a register/refresh request.
98 *****************************************************************************/
100 static int get_ttl_from_packet(struct nmb_packet *nmb)
102 int ttl = nmb->additional->ttl;
104 if(ttl < lp_min_wins_ttl() )
105 ttl = lp_min_wins_ttl();
107 if(ttl > lp_max_wins_ttl() )
108 ttl = lp_max_wins_ttl();
113 /****************************************************************************
114 Load or create the WINS database.
115 *****************************************************************************/
117 BOOL initialise_wins(void)
120 time_t time_now = time(NULL);
124 if(!lp_we_are_a_wins_server())
127 add_samba_names_to_subnet(wins_server_subnet);
130 /* Setup the async dns. */
134 pstrcpy(fname,lp_lockdir());
135 trim_string(fname,NULL,"/");
137 pstrcat(fname,WINS_LIST);
139 if((fp = fopen(fname,"r")) == NULL)
141 DEBUG(2,("initialise_wins: Can't open wins database file %s. Error was %s\n",
142 fname, strerror(errno) ));
148 pstring name_str, ip_str, ttl_str, nb_flags_str;
149 unsigned int num_ips;
151 struct in_addr *ip_list;
155 enum name_source source;
162 /* Read a line from the wins.dat file. Strips whitespace
163 from the beginning and end of the line.
165 if (!fgets_slash(line,sizeof(pstring),fp))
174 * Now we handle multiple IP addresses per name we need
175 * to iterate over the line twice. The first time to
176 * determine how many IP addresses there are, the second
177 * time to actually parse them into the ip_list array.
180 if (!next_token(&ptr,name_str,NULL))
182 DEBUG(0,("initialise_wins: Failed to parse name when parsing line %s\n", line ));
186 if (!next_token(&ptr,ttl_str,NULL))
188 DEBUG(0,("initialise_wins: Failed to parse time to live when parsing line %s\n", line ));
193 * Determine the number of IP addresses per line.
198 got_token = next_token(&ptr,ip_str,NULL);
201 if(got_token && strchr(ip_str, '.'))
206 } while( got_token && was_ip);
210 DEBUG(0,("initialise_wins: Missing IP address when parsing line %s\n", line ));
216 DEBUG(0,("initialise_wins: Missing nb_flags when parsing line %s\n", line ));
220 /* Allocate the space for the ip_list. */
221 if((ip_list = (struct in_addr *)malloc( num_ips * sizeof(struct in_addr))) == NULL)
223 DEBUG(0,("initialise_wins: Malloc fail !\n"));
227 /* Reset and re-parse the line. */
229 next_token(&ptr,name_str,NULL);
230 next_token(&ptr,ttl_str,NULL);
231 for(i = 0; i < num_ips; i++)
233 next_token(&ptr, ip_str, NULL);
234 ip_list[i] = *interpret_addr2(ip_str);
235 if (ip_equal(ip_list[i], ipzero))
238 next_token(&ptr,nb_flags_str,NULL);
241 * Deal with SELF or REGISTER name encoding. Default is REGISTER
242 * for compatibility with old nmbds.
245 if(nb_flags_str[strlen(nb_flags_str)-1] == 'S')
247 DEBUG(5,("initialise_wins: Ignoring SELF name %s\n", line));
248 free((char *)ip_list);
252 if(nb_flags_str[strlen(nb_flags_str)-1] == 'R')
253 nb_flags_str[strlen(nb_flags_str)-1] = '\0';
255 /* Netbios name. # divides the name from the type (hex): netbios#xx */
256 pstrcpy(name,name_str);
258 if((p = strchr(name,'#')) != NULL)
261 sscanf(p+1,"%x",&type);
264 /* Decode the netbios flags (hex) and the time-to-live (in seconds). */
265 sscanf(nb_flags_str,"%x",&nb_flags);
266 sscanf(ttl_str,"%d",&ttl);
268 /* add all entries that have 60 seconds or more to live */
269 if ((ttl - 60) > time_now || ttl == PERMANENT_TTL)
271 struct name_record *namerec;
273 if(ttl != PERMANENT_TTL)
276 DEBUG(4, ("initialise_wins: add name: %s#%02x ttl = %d first IP %s flags = %2x\n",
277 name, type, ttl, inet_ntoa(ip_list[0]), nb_flags));
279 namerec = add_name_to_subnet(wins_server_subnet, name, type, nb_flags,
280 ttl, REGISTER_NAME, num_ips, ip_list);
285 DEBUG(4, ("initialise_wins: not adding name (ttl problem) %s#%02x ttl = %d first IP %s flags = %2x\n",
286 name, type, ttl, inet_ntoa(ip_list[0]), nb_flags));
289 free((char *)ip_list);
296 /****************************************************************************
297 Send a WINS WACK (Wait ACKnowledgement) response.
298 **************************************************************************/
300 static void send_wins_wack_response(int ttl, struct packet_struct *p)
302 struct nmb_packet *nmb = &p->packet.nmb;
303 unsigned char rdata[2];
305 rdata[0] = rdata[1] = 0;
307 /* Taken from nmblib.c - we need to send back almost
308 identical bytes from the requesting packet header. */
310 rdata[0] = (nmb->header.opcode & 0xF) << 3;
311 if (nmb->header.nm_flags.authoritative &&
312 nmb->header.response) rdata[0] |= 0x4;
313 if (nmb->header.nm_flags.trunc) rdata[0] |= 0x2;
314 if (nmb->header.nm_flags.recursion_desired) rdata[0] |= 0x1;
315 if (nmb->header.nm_flags.recursion_available &&
316 nmb->header.response) rdata[1] |= 0x80;
317 if (nmb->header.nm_flags.bcast) rdata[1] |= 0x10;
319 reply_netbios_packet(p, /* Packet to reply to. */
320 0, /* Result code. */
321 NMB_WAIT_ACK, /* nmbd type code. */
322 NMB_WACK_OPCODE, /* opcode. */
324 (char *)rdata, /* data to send. */
325 2); /* data length. */
328 /****************************************************************************
329 Send a WINS name registration response.
330 **************************************************************************/
332 static void send_wins_name_registration_response(int rcode, int ttl, struct packet_struct *p)
334 struct nmb_packet *nmb = &p->packet.nmb;
337 memcpy(&rdata[0], &nmb->additional->rdata[0], 6);
339 reply_netbios_packet(p, /* Packet to reply to. */
340 rcode, /* Result code. */
341 WINS_REG, /* nmbd type code. */
342 NMB_NAME_REG_OPCODE, /* opcode. */
344 rdata, /* data to send. */
345 6); /* data length. */
348 /***********************************************************************
349 Deal with a name refresh request to a WINS server.
350 ************************************************************************/
352 void wins_process_name_refresh_request(struct subnet_record *subrec,
353 struct packet_struct *p)
355 struct nmb_packet *nmb = &p->packet.nmb;
356 struct nmb_name *question = &nmb->question.question_name;
357 BOOL bcast = nmb->header.nm_flags.bcast;
358 uint16 nb_flags = get_nb_flags(nmb->additional->rdata);
359 BOOL group = (nb_flags & NB_GROUP) ? True : False;
360 struct name_record *namerec = NULL;
361 int ttl = get_ttl_from_packet(nmb);
362 struct in_addr from_ip;
364 putip((char *)&from_ip,&nmb->additional->rdata[2]);
369 * We should only get unicast name refresh packets here.
370 * Anyone trying to refresh broadcast should not be going to a WINS
371 * server. Log an error here.
374 DEBUG(0,("wins_process_name_refresh_request: broadcast name refresh request \
375 received for name %s from IP %s on subnet %s. Error - should not be sent to WINS server\n",
376 namestr(question), inet_ntoa(from_ip), subrec->subnet_name));
380 DEBUG(3,("wins_process_name_refresh_request: Name refresh for name %s \
381 IP %s\n", namestr(question), inet_ntoa(from_ip) ));
384 * See if the name already exists.
387 namerec = find_name_on_subnet(subrec, question, FIND_ANY_NAME);
390 * If this is a refresh request and the name doesn't exist then
396 DEBUG(3,("wins_process_name_refresh_request: Name refresh for name %s and \
397 the name does not exist.\n", namestr(question) ));
398 send_wins_name_registration_response(NAM_ERR, 0, p);
403 * Check that the group bits for the refreshing name and the
404 * name in our database match.
407 if((namerec != NULL) && ((group && !NAME_GROUP(namerec)) || (!group && NAME_GROUP(namerec))) )
409 DEBUG(3,("wins_process_name_refresh_request: Name %s group bit = %s \
410 does not match group bit in WINS for this name.\n", namestr(question), group ? "True" : "False" ));
411 send_wins_name_registration_response(RFS_ERR, 0, p);
416 * For a unique name check that the person refreshing the name is one of the registered IP
417 * addresses. If not - fail the refresh. Do the same for group names with a type of 0x1c.
418 * Just return success for unique 0x1d refreshes. For normal group names update the ttl
419 * and return success.
422 if((!group || (group && (question->name_type == 0x1c))) && find_ip_in_name_record(namerec, from_ip ))
427 update_name_ttl(namerec, ttl);
428 send_wins_name_registration_response(0, ttl, p);
434 * Normal groups are all registered with an IP address of 255.255.255.255
435 * so we can't search for the IP address.
437 update_name_ttl(namerec, ttl);
438 send_wins_name_registration_response(0, ttl, p);
441 else if(!group && (question->name_type == 0x1d))
444 * Special name type - just pretend the refresh succeeded.
446 send_wins_name_registration_response(0, ttl, p);
455 DEBUG(3,("wins_process_name_refresh_request: Name refresh for name %s with IP %s and \
456 is IP is not known to the name.\n", namestr(question), inet_ntoa(from_ip) ));
457 send_wins_name_registration_response(RFS_ERR, 0, p);
462 /***********************************************************************
463 Deal with a name registration request query success to a client that
466 We have a locked pointer to the original packet stashed away in the
467 userdata pointer. The success here is actually a failure as it means
468 the client we queried wants to keep the name, so we must return
469 a registration failure to the original requestor.
470 ************************************************************************/
472 static void wins_register_query_success(struct subnet_record *subrec,
473 struct userdata_struct *userdata,
474 struct nmb_name *question_name,
476 struct res_rec *answers)
478 struct packet_struct *orig_reg_packet;
480 memcpy((char *)&orig_reg_packet, userdata->data, sizeof(struct packet_struct *));
482 DEBUG(3,("wins_register_query_success: Original client at IP %s still wants the \
483 name %s. Rejecting registration request.\n", inet_ntoa(ip), namestr(question_name) ));
485 send_wins_name_registration_response(RFS_ERR, 0, orig_reg_packet);
487 orig_reg_packet->locked = False;
488 free_packet(orig_reg_packet);
491 /***********************************************************************
492 Deal with a name registration request query failure to a client that
495 We have a locked pointer to the original packet stashed away in the
496 userdata pointer. The failure here is actually a success as it means
497 the client we queried didn't want to keep the name, so we can remove
498 the old name record and then successfully add the new name.
499 ************************************************************************/
501 static void wins_register_query_fail(struct subnet_record *subrec,
502 struct response_record *rrec,
503 struct nmb_name *question_name,
506 struct userdata_struct *userdata = rrec->userdata;
507 struct packet_struct *orig_reg_packet;
508 struct nmb_packet *nmb;
509 struct name_record *namerec = NULL;
513 memcpy((char *)&orig_reg_packet, userdata->data, sizeof(struct packet_struct *));
515 nmb = &orig_reg_packet->packet.nmb;
517 nb_flags = get_nb_flags(nmb->additional->rdata);
518 group = (nb_flags & NB_GROUP) ? True : False;
521 * We want to just add the name, as we now know the original owner
522 * didn't want it. But we can't just do that as an arbitary
523 * amount of time may have taken place between the name query
524 * request and this timeout/error response. So we check that
525 * the name still exists and is in the same state - if so
526 * we remove it and call wins_process_name_registration_request()
527 * as we know it will do the right thing now.
530 namerec = find_name_on_subnet(subrec, question_name, FIND_ANY_NAME);
532 if( (namerec != NULL)
533 && (namerec->data.source == REGISTER_NAME)
534 && ip_equal(rrec->packet->ip, *namerec->data.ip) )
536 remove_name_from_namelist( subrec, namerec);
541 wins_process_name_registration_request(subrec, orig_reg_packet);
543 DEBUG(2,("wins_register_query_fail: The state of the WINS database changed between \
544 querying for name %s in order to replace it and this reply.\n", namestr(question_name) ));
546 orig_reg_packet->locked = False;
547 free_packet(orig_reg_packet);
550 /***********************************************************************
551 Deal with a name registration request to a WINS server.
553 Use the following pseudocode :
561 | +--- existing name is group
564 | | +--- add name (return).
567 | +--- exiting name is unique
570 | +--- query existing owner (return).
573 +--------name doesn't exist
576 +--- add name (return).
584 | +--- existing name is group
587 | | +--- fail add (return).
590 | +--- exiting name is unique
593 | +--- query existing owner (return).
596 +--------name doesn't exist
599 +--- add name (return).
601 As can be seen from the above, the two cases may be collapsed onto each
602 other with the exception of the case where the name already exists and
603 is a group name. This case we handle with an if statement.
605 ************************************************************************/
607 void wins_process_name_registration_request(struct subnet_record *subrec,
608 struct packet_struct *p)
610 struct nmb_packet *nmb = &p->packet.nmb;
611 struct nmb_name *question = &nmb->question.question_name;
612 BOOL bcast = nmb->header.nm_flags.bcast;
613 uint16 nb_flags = get_nb_flags(nmb->additional->rdata);
614 int ttl = get_ttl_from_packet(nmb);
615 struct name_record *namerec = NULL;
616 struct in_addr from_ip;
617 BOOL registering_group_name = (nb_flags & NB_GROUP) ? True : False;;
619 putip((char *)&from_ip,&nmb->additional->rdata[2]);
624 * We should only get unicast name registration packets here.
625 * Anyone trying to register broadcast should not be going to a WINS
626 * server. Log an error here.
629 DEBUG(0,("wins_process_name_registration_request: broadcast name registration request \
630 received for name %s from IP %s on subnet %s. Error - should not be sent to WINS server\n",
631 namestr(question), inet_ntoa(from_ip), subrec->subnet_name));
635 DEBUG(3,("wins_process_name_registration_request: %s name registration for name %s \
636 IP %s\n", registering_group_name ? "Group" : "Unique", namestr(question), inet_ntoa(from_ip) ));
639 * See if the name already exists.
642 namerec = find_name_on_subnet(subrec, question, FIND_ANY_NAME);
645 * Deal with the case where the name found was a dns entry.
646 * Remove it as we now have a NetBIOS client registering the
650 if( (namerec != NULL)
651 && ( (namerec->data.source == DNS_NAME)
652 || (namerec->data.source == DNSFAIL_NAME) ) )
654 DEBUG(5,("wins_process_name_registration_request: Name (%s) in WINS was \
655 a dns lookup - removing it.\n", namestr(question) ));
656 remove_name_from_namelist( subrec, namerec );
661 * Reject if the name exists and is not a REGISTER_NAME.
662 * (ie. Don't allow any static names to be overwritten.
665 if((namerec != NULL) && (namerec->data.source != REGISTER_NAME))
667 DEBUG( 3, ( "wins_process_name_registration_request: Attempt \
668 to register name %s. Name already exists in WINS with source type %d.\n",
669 namestr(question), namerec->data.source ));
670 send_wins_name_registration_response(RFS_ERR, 0, p);
675 * Special policy decisions based on MS documentation.
676 * 1). All group names (except names ending in 0x1c) are added as 255.255.255.255.
677 * 2). All unique names ending in 0x1d are ignored, although a positive response is sent.
681 * A group name is always added as the local broadcast address, except
682 * for group names ending in 0x1c.
683 * Group names with type 0x1c are registered with individual IP addresses.
686 if(registering_group_name && (question->name_type != 0x1c))
687 from_ip = *interpret_addr2("255.255.255.255");
690 * Ignore all attempts to register a unique 0x1d name, although return success.
693 if(!registering_group_name && (question->name_type == 0x1d))
695 DEBUG(3,("wins_process_name_registration_request: Ignoring request \
696 to register name %s from IP %s.", namestr(question), inet_ntoa(p->ip) ));
697 send_wins_name_registration_response(0, ttl, p);
702 * Next two cases are the 'if statement' mentioned above.
705 if((namerec != NULL) && NAME_GROUP(namerec))
707 if(registering_group_name)
710 * If we are adding a group name, the name exists and is also a group entry just add this
711 * IP address to it and update the ttl.
714 DEBUG(3,("wins_process_name_registration_request: Adding IP %s to group name %s.\n",
715 inet_ntoa(from_ip), namestr(question) ));
717 * Check the ip address is not already in the group.
719 if(!find_ip_in_name_record(namerec, from_ip))
720 add_ip_to_name_record(namerec, from_ip);
721 update_name_ttl(namerec, ttl);
722 send_wins_name_registration_response(0, ttl, p);
728 * If we are adding a unique name, the name exists in the WINS db
729 * and is a group name then reject the registration.
732 DEBUG(3,("wins_process_name_registration_request: Attempt to register name %s. Name \
733 already exists in WINS as a GROUP name.\n", namestr(question) ));
734 send_wins_name_registration_response(RFS_ERR, 0, p);
740 * From here on down we know that if the name exists in the WINS db it is
741 * a unique name, not a group name.
745 * If the name exists and is one of our names then check the
746 * registering IP address. If it's not one of ours then automatically
747 * reject without doing the query - we know we will reject it.
750 if((namerec != NULL) && (is_myname(namerec->name.name)) )
754 DEBUG(3,("wins_process_name_registration_request: Attempt to register name %s. Name \
755 is one of our (WINS server) names. Denying registration.\n", namestr(question) ));
756 send_wins_name_registration_response(RFS_ERR, 0, p);
762 * It's one of our names and one of our IP's - update the ttl.
764 update_name_ttl(namerec, ttl);
765 send_wins_name_registration_response(0, ttl, p);
771 * If the name exists and it is a unique registration and the registering IP
772 * is the same as the the (single) already registered IP then just update the ttl.
775 if( !registering_group_name
777 && (namerec->data.num_ips == 1)
778 && ip_equal( namerec->data.ip[0], from_ip ) )
780 update_name_ttl( namerec, ttl );
781 send_wins_name_registration_response( 0, ttl, p );
786 * Finally if the name exists do a query to the registering machine
787 * to see if they still claim to have the name.
790 if( namerec != NULL )
792 char ud[sizeof(struct userdata_struct) + sizeof(struct packet_struct *)];
793 struct userdata_struct *userdata = (struct userdata_struct *)ud;
796 * First send a WACK to the registering machine.
799 send_wins_wack_response(60, p);
802 * When the reply comes back we need the original packet.
803 * Lock this so it won't be freed and then put it into
804 * the userdata structure.
809 userdata = (struct userdata_struct *)ud;
811 userdata->copy_fn = NULL;
812 userdata->free_fn = NULL;
813 userdata->userdata_len = sizeof(struct packet_struct *);
814 memcpy(userdata->data, (char *)&p, sizeof(struct packet_struct *) );
817 * Use the new call to send a query directly to an IP address.
818 * This sends the query directly to the IP address, and ensures
819 * the recursion desired flag is not set (you were right Luke :-).
820 * This function should *only* be called from the WINS server
824 query_name_from_wins_server( *namerec->data.ip,
827 wins_register_query_success,
828 wins_register_query_fail,
834 * Name did not exist - add it.
837 add_name_to_subnet(subrec, question->name, question->name_type,
838 nb_flags, ttl, REGISTER_NAME, 1, &from_ip);
840 send_wins_name_registration_response(0, ttl, p);
843 /***********************************************************************
844 Deal with a mutihomed name query success to the machine that
845 requested the multihomed name registration.
847 We have a locked pointer to the original packet stashed away in the
849 ************************************************************************/
851 static void wins_multihomed_register_query_success(struct subnet_record *subrec,
852 struct userdata_struct *userdata,
853 struct nmb_name *question_name,
855 struct res_rec *answers)
857 struct packet_struct *orig_reg_packet;
858 struct nmb_packet *nmb;
859 struct name_record *namerec = NULL;
860 struct in_addr from_ip;
863 memcpy((char *)&orig_reg_packet, userdata->data, sizeof(struct packet_struct *));
865 nmb = &orig_reg_packet->packet.nmb;
867 putip((char *)&from_ip,&nmb->additional->rdata[2]);
868 ttl = get_ttl_from_packet(nmb);
871 * We want to just add the new IP, as we now know the requesting
872 * machine claims to own it. But we can't just do that as an arbitary
873 * amount of time may have taken place between the name query
874 * request and this response. So we check that
875 * the name still exists and is in the same state - if so
876 * we just add the extra IP and update the ttl.
879 namerec = find_name_on_subnet(subrec, question_name, FIND_ANY_NAME);
881 if( (namerec == NULL) || (namerec->data.source != REGISTER_NAME) )
883 DEBUG(3,("wins_multihomed_register_query_success: name %s is not in the correct state to add \
884 a subsequent IP addess.\n", namestr(question_name) ));
885 send_wins_name_registration_response(RFS_ERR, 0, orig_reg_packet);
889 if(!find_ip_in_name_record(namerec, from_ip))
890 add_ip_to_name_record(namerec, from_ip);
891 update_name_ttl(namerec, ttl);
892 send_wins_name_registration_response(0, ttl, orig_reg_packet);
896 /***********************************************************************
897 Deal with a name registration request query failure to a client that
900 We have a locked pointer to the original packet stashed away in the
902 ************************************************************************/
904 static void wins_multihomed_register_query_fail(struct subnet_record *subrec,
905 struct response_record *rrec,
906 struct nmb_name *question_name,
909 struct userdata_struct *userdata = rrec->userdata;
910 struct packet_struct *orig_reg_packet;
912 memcpy((char *)&orig_reg_packet, userdata->data, sizeof(struct packet_struct *));
914 DEBUG(3,("wins_multihomed_register_query_fail: Registering machine at IP %s failed to answer \
915 query successfully for name %s.\n", inet_ntoa(orig_reg_packet->ip), namestr(question_name) ));
916 send_wins_name_registration_response(RFS_ERR, 0, orig_reg_packet);
920 /***********************************************************************
921 Deal with a multihomed name registration request to a WINS server.
922 These cannot be group name registrations.
923 ***********************************************************************/
925 void wins_process_multihomed_name_registration_request( struct subnet_record *subrec,
926 struct packet_struct *p)
928 struct nmb_packet *nmb = &p->packet.nmb;
929 struct nmb_name *question = &nmb->question.question_name;
930 BOOL bcast = nmb->header.nm_flags.bcast;
931 uint16 nb_flags = get_nb_flags(nmb->additional->rdata);
932 int ttl = get_ttl_from_packet(nmb);
933 struct name_record *namerec = NULL;
934 struct in_addr from_ip;
935 BOOL group = (nb_flags & NB_GROUP) ? True : False;;
937 putip((char *)&from_ip,&nmb->additional->rdata[2]);
942 * We should only get unicast name registration packets here.
943 * Anyone trying to register broadcast should not be going to a WINS
944 * server. Log an error here.
947 DEBUG(0,("wins_process_multihomed_name_registration_request: broadcast name registration request \
948 received for name %s from IP %s on subnet %s. Error - should not be sent to WINS server\n",
949 namestr(question), inet_ntoa(from_ip), subrec->subnet_name));
954 * Only unique names should be registered multihomed.
959 DEBUG(0,("wins_process_multihomed_name_registration_request: group name registration request \
960 received for name %s from IP %s on subnet %s. Errror - group names should not be multihomed.\n",
961 namestr(question), inet_ntoa(from_ip), subrec->subnet_name));
965 DEBUG(3,("wins_process_multihomed_name_registration_request: name registration for name %s \
966 IP %s\n", namestr(question), inet_ntoa(from_ip) ));
969 * Deal with policy regarding 0x1d names.
972 if(question->name_type == 0x1d)
974 DEBUG(3,("wins_process_multihomed_name_registration_request: Ignoring request \
975 to register name %s from IP %s.", namestr(question), inet_ntoa(p->ip) ));
976 send_wins_name_registration_response(0, ttl, p);
981 * See if the name already exists.
984 namerec = find_name_on_subnet(subrec, question, FIND_ANY_NAME);
987 * Deal with the case where the name found was a dns entry.
988 * Remove it as we now have a NetBIOS client registering the
992 if( (namerec != NULL)
993 && ( (namerec->data.source == DNS_NAME)
994 || (namerec->data.source == DNSFAIL_NAME) ) )
996 DEBUG(5,("wins_process_multihomed_name_registration_request: Name (%s) in WINS was a dns lookup \
997 - removing it.\n", namestr(question) ));
998 remove_name_from_namelist( subrec, namerec);
1003 * Reject if the name exists and is not a REGISTER_NAME.
1004 * (ie. Don't allow any static names to be overwritten.
1007 if( (namerec != NULL) && (namerec->data.source != REGISTER_NAME) )
1009 DEBUG( 3, ( "wins_process_multihomed_name_registration_request: Attempt \
1010 to register name %s. Name already exists in WINS with source type %d.\n",
1011 namestr(question), namerec->data.source ));
1012 send_wins_name_registration_response(RFS_ERR, 0, p);
1017 * Reject if the name exists and is a GROUP name.
1020 if((namerec != NULL) && NAME_GROUP(namerec))
1022 DEBUG(3,("wins_process_multihomed_name_registration_request: Attempt to register name %s. Name \
1023 already exists in WINS as a GROUP name.\n", namestr(question) ));
1024 send_wins_name_registration_response(RFS_ERR, 0, p);
1029 * From here on down we know that if the name exists in the WINS db it is
1030 * a unique name, not a group name.
1034 * If the name exists and is one of our names then check the
1035 * registering IP address. If it's not one of ours then automatically
1036 * reject without doing the query - we know we will reject it.
1039 if((namerec != NULL) && (is_myname(namerec->name.name)) )
1041 if(!ismyip(from_ip))
1043 DEBUG(3,("wins_process_multihomed_name_registration_request: Attempt to register name %s. Name \
1044 is one of our (WINS server) names. Denying registration.\n", namestr(question) ));
1045 send_wins_name_registration_response(RFS_ERR, 0, p);
1051 * It's one of our names and one of our IP's. Ensure the IP is in the record and
1054 if(!find_ip_in_name_record(namerec, from_ip))
1055 add_ip_to_name_record(namerec, from_ip);
1056 update_name_ttl(namerec, ttl);
1057 send_wins_name_registration_response(0, ttl, p);
1063 * If the name exists check if the IP address is already registered
1064 * to that name. If so then update the ttl and reply success.
1067 if((namerec != NULL) && find_ip_in_name_record(namerec, from_ip))
1069 update_name_ttl(namerec, ttl);
1070 send_wins_name_registration_response(0, ttl, p);
1075 * If the name exists do a query to the owner
1076 * to see if they still want the name.
1081 char ud[sizeof(struct userdata_struct) + sizeof(struct packet_struct *)];
1082 struct userdata_struct *userdata = (struct userdata_struct *)ud;
1085 * First send a WACK to the registering machine.
1088 send_wins_wack_response(60, p);
1091 * When the reply comes back we need the original packet.
1092 * Lock this so it won't be freed and then put it into
1093 * the userdata structure.
1098 userdata = (struct userdata_struct *)ud;
1100 userdata->copy_fn = NULL;
1101 userdata->free_fn = NULL;
1102 userdata->userdata_len = sizeof(struct packet_struct *);
1103 memcpy(userdata->data, (char *)&p, sizeof(struct packet_struct *) );
1106 * As query_name uses the subnet broadcast address as the destination
1107 * of the packet we temporarily change the subnet broadcast address to
1108 * be the IP address of the requesting machine and send the packet. This
1109 * is a *horrible* hack but the alternative is to add the destination
1110 * address parameter to all query_name() calls. I hate this code :-).
1113 subrec->bcast_ip = p->ip;
1114 query_name( subrec, question->name, question->name_type,
1115 wins_multihomed_register_query_success,
1116 wins_multihomed_register_query_fail,
1118 subrec->bcast_ip = ipzero;
1123 * Name did not exist - add it.
1126 add_name_to_subnet(subrec, question->name, question->name_type,
1127 nb_flags, ttl, REGISTER_NAME, 1, &from_ip);
1129 send_wins_name_registration_response(0, ttl, p);
1132 /***********************************************************************
1133 Deal with the special name query for *<1b>.
1134 ***********************************************************************/
1136 static void process_wins_dmb_query_request(struct subnet_record *subrec,
1137 struct packet_struct *p)
1139 struct name_record *namerec = NULL;
1144 * Go through all the names in the WINS db looking for those
1145 * ending in <1b>. Use this to calculate the number of IP
1146 * addresses we need to return.
1150 for(namerec = subrec->namelist; namerec; namerec = namerec->next)
1152 if(namerec->name.name_type == 0x1b)
1153 num_ips += namerec->data.num_ips;
1159 * There are no 0x1b names registered. Return name query fail.
1161 send_wins_name_query_response(NAM_ERR, p, NULL);
1165 if((prdata = (char *)malloc( num_ips * 6 )) == NULL)
1167 DEBUG(0,("process_wins_dmb_query_request: Malloc fail !.\n"));
1172 * Go through all the names again in the WINS db looking for those
1173 * ending in <1b>. Add their IP addresses into the list we will
1178 for(namerec = subrec->namelist; namerec; namerec = namerec->next)
1180 if(namerec->name.name_type == 0x1b)
1183 for(i = 0; i < namerec->data.num_ips; i++)
1185 set_nb_flags(&prdata[num_ips * 6],namerec->data.nb_flags);
1186 putip((char *)&prdata[(num_ips * 6) + 2], &namerec->data.ip[i]);
1193 * Send back the reply containing the IP list.
1196 reply_netbios_packet(p, /* Packet to reply to. */
1197 0, /* Result code. */
1198 WINS_QUERY, /* nmbd type code. */
1199 NMB_NAME_QUERY_OPCODE, /* opcode. */
1200 lp_min_wins_ttl(), /* ttl. */
1201 prdata, /* data to send. */
1202 num_ips*6); /* data length. */
1207 /****************************************************************************
1208 Send a WINS name query response.
1209 **************************************************************************/
1211 void send_wins_name_query_response(int rcode, struct packet_struct *p,
1212 struct name_record *namerec)
1215 char *prdata = rdata;
1216 int reply_data_len = 0;
1225 int same_net_index = -1;
1227 ttl = (namerec->data.death_time != PERMANENT_TTL) ?
1228 namerec->data.death_time - p->timestamp : lp_max_wins_ttl();
1230 /* Copy all known ip addresses into the return data. */
1231 /* Optimise for the common case of one IP address so
1232 we don't need a malloc. */
1234 if( namerec->data.num_ips == 1 )
1238 if((prdata = (char *)malloc( namerec->data.num_ips * 6 )) == NULL)
1240 DEBUG(0,("send_wins_name_query_response: malloc fail !\n"));
1245 * Look over the known IP addresses and see if one of them
1246 * is on the same (local) net as the requesting IP address. If so then
1247 * put that IP address into the packet as the first IP.
1248 * We can only do this for local nets as they're the only
1249 * ones we know the netmask for.
1254 if(is_local_net(p->ip))
1256 struct in_addr *n_mask = iface_nmask(p->ip);
1258 for( j = 0; j < namerec->data.num_ips; j++)
1260 if(same_net( namerec->data.ip[j], p->ip, *n_mask))
1262 set_nb_flags(&prdata[0],namerec->data.nb_flags);
1263 putip((char *)&prdata[2], &namerec->data.ip[j]);
1271 for(j = 0; j < namerec->data.num_ips; j++)
1273 if(j == same_net_index)
1275 set_nb_flags(&prdata[i*6],namerec->data.nb_flags);
1276 putip((char *)&prdata[2+(i*6)], &namerec->data.ip[j]);
1279 reply_data_len = namerec->data.num_ips * 6;
1283 reply_netbios_packet(p, /* Packet to reply to. */
1284 rcode, /* Result code. */
1285 WINS_QUERY, /* nmbd type code. */
1286 NMB_NAME_QUERY_OPCODE, /* opcode. */
1288 prdata, /* data to send. */
1289 reply_data_len); /* data length. */
1291 if((prdata != rdata) && (prdata != NULL))
1295 /***********************************************************************
1296 Deal with a name query.
1297 ***********************************************************************/
1299 void wins_process_name_query_request(struct subnet_record *subrec,
1300 struct packet_struct *p)
1302 struct nmb_packet *nmb = &p->packet.nmb;
1303 struct nmb_name *question = &nmb->question.question_name;
1304 struct name_record *namerec = NULL;
1306 DEBUG(3,("wins_process_name_query: name query for name %s from IP %s\n",
1307 namestr(question), inet_ntoa(p->ip) ));
1310 * Special name code. If the queried name is *<1b> then search
1311 * the entire WINS database and return a list of all the IP addresses
1312 * registered to any <1b> name. This is to allow domain master browsers
1313 * to discover other domains that may not have a presence on their subnet.
1316 if(strequal( question->name, "*") && (question->name_type == 0x1b))
1318 process_wins_dmb_query_request( subrec, p);
1322 namerec = find_name_on_subnet(subrec, question, FIND_ANY_NAME);
1327 * If it's a DNSFAIL_NAME then reply name not found.
1330 if( namerec->data.source == DNSFAIL_NAME )
1332 DEBUG(3,("wins_process_name_query: name query for name %s returning DNS fail.\n",
1333 namestr(question) ));
1334 send_wins_name_query_response(NAM_ERR, p, namerec);
1339 * If the name has expired then reply name not found.
1342 if( (namerec->data.death_time != PERMANENT_TTL)
1343 && (namerec->data.death_time < p->timestamp) )
1345 DEBUG(3,("wins_process_name_query: name query for name %s - name expired. Returning fail.\n",
1346 namestr(question) ));
1347 send_wins_name_query_response(NAM_ERR, p, namerec);
1351 DEBUG(3,("wins_process_name_query: name query for name %s returning first IP %s.\n",
1352 namestr(question), inet_ntoa(namerec->data.ip[0]) ));
1354 send_wins_name_query_response(0, p, namerec);
1359 * Name not found in WINS - try a dns query if it's a 0x20 name.
1362 if(lp_dns_proxy() &&
1363 ((question->name_type == 0x20) || question->name_type == 0))
1366 DEBUG(3,("wins_process_name_query: name query for name %s not found - doing dns lookup.\n",
1367 namestr(question) ));
1369 queue_dns_query(p, question, &namerec);
1374 * Name not found - return error.
1377 send_wins_name_query_response(NAM_ERR, p, NULL);
1380 /****************************************************************************
1381 Send a WINS name release response.
1382 **************************************************************************/
1384 static void send_wins_name_release_response(int rcode, struct packet_struct *p)
1386 struct nmb_packet *nmb = &p->packet.nmb;
1389 memcpy(&rdata[0], &nmb->additional->rdata[0], 6);
1391 reply_netbios_packet(p, /* Packet to reply to. */
1392 rcode, /* Result code. */
1393 NMB_REL, /* nmbd type code. */
1394 NMB_NAME_RELEASE_OPCODE, /* opcode. */
1396 rdata, /* data to send. */
1397 6); /* data length. */
1400 /***********************************************************************
1401 Deal with a name release.
1402 ***********************************************************************/
1404 void wins_process_name_release_request(struct subnet_record *subrec,
1405 struct packet_struct *p)
1407 struct nmb_packet *nmb = &p->packet.nmb;
1408 struct nmb_name *question = &nmb->question.question_name;
1409 BOOL bcast = nmb->header.nm_flags.bcast;
1410 uint16 nb_flags = get_nb_flags(nmb->additional->rdata);
1411 struct name_record *namerec = NULL;
1412 struct in_addr from_ip;
1413 BOOL releasing_group_name = (nb_flags & NB_GROUP) ? True : False;;
1415 putip((char *)&from_ip,&nmb->additional->rdata[2]);
1420 * We should only get unicast name registration packets here.
1421 * Anyone trying to register broadcast should not be going to a WINS
1422 * server. Log an error here.
1425 DEBUG(0,("wins_process_name_release_request: broadcast name registration request \
1426 received for name %s from IP %s on subnet %s. Error - should not be sent to WINS server\n",
1427 namestr(question), inet_ntoa(from_ip), subrec->subnet_name));
1431 DEBUG(3,("wins_process_name_release_request: %s name release for name %s \
1432 IP %s\n", releasing_group_name ? "Group" : "Unique", namestr(question), inet_ntoa(from_ip) ));
1435 * Deal with policy regarding 0x1d names.
1438 if(!releasing_group_name && (question->name_type == 0x1d))
1440 DEBUG(3,("wins_process_name_release_request: Ignoring request \
1441 to release name %s from IP %s.", namestr(question), inet_ntoa(p->ip) ));
1442 send_wins_name_release_response(0, p);
1447 * See if the name already exists.
1450 namerec = find_name_on_subnet(subrec, question, FIND_ANY_NAME);
1452 if( (namerec == NULL)
1453 || ((namerec != NULL) && (namerec->data.source != REGISTER_NAME)) )
1455 send_wins_name_release_response(NAM_ERR, p);
1460 * Check that the sending machine has permission to release this name.
1461 * If it's a group name not ending in 0x1c then just say yes and let
1462 * the group time out.
1465 if(releasing_group_name && (question->name_type != 0x1c))
1467 send_wins_name_release_response(0, p);
1472 * Check that the releasing node is on the list of IP addresses
1473 * for this name. Disallow the release if not.
1476 if(!find_ip_in_name_record(namerec, from_ip))
1478 DEBUG(3,("wins_process_name_release_request: Refusing request to \
1479 release name %s as IP %s is not one of the known IP's for this name.\n",
1480 namestr(question), inet_ntoa(from_ip) ));
1481 send_wins_name_release_response(NAM_ERR, p);
1486 * Release the name and then remove the IP from the known list.
1489 send_wins_name_release_response(0, p);
1490 remove_ip_from_name_record(namerec, from_ip);
1493 * Remove the name entirely if no IP addresses left.
1495 if (namerec->data.num_ips == 0)
1496 remove_name_from_namelist(subrec, namerec);
1500 /*******************************************************************
1501 WINS time dependent processing.
1502 ******************************************************************/
1504 void initiate_wins_processing(time_t t)
1506 static time_t lasttime = 0;
1510 if (t - lasttime < 5)
1513 if(!lp_we_are_a_wins_server())
1516 expire_names_on_subnet(wins_server_subnet, t);
1518 if(wins_server_subnet->namelist_changed)
1519 wins_write_database();
1521 wins_server_subnet->namelist_changed = False;
1524 /*******************************************************************
1525 Write out the current WINS database.
1526 ******************************************************************/
1528 void wins_write_database(void)
1530 struct name_record *namerec;
1531 pstring fname, fnamenew;
1535 if(!lp_we_are_a_wins_server())
1538 pstrcpy(fname,lp_lockdir());
1539 trim_string(fname,NULL,"/");
1541 pstrcat(fname,WINS_LIST);
1542 pstrcpy(fnamenew,fname);
1543 pstrcat(fnamenew,".");
1545 if((fp = fopen(fnamenew,"w")) == NULL)
1547 DEBUG(0,("wins_write_database: Can't open %s. Error was %s\n", fnamenew, strerror(errno)));
1551 DEBUG(4,("wins_write_database: Dump of WINS name list.\n"));
1553 for (namerec = wins_server_subnet->namelist; namerec; namerec = namerec->next)
1558 DEBUG(4,("%-19s ", namestr(&namerec->name) ));
1560 if( namerec->data.death_time != PERMANENT_TTL )
1562 tm = LocalTime(&namerec->data.death_time);
1563 DEBUG(4,("TTL = %s", asctime(tm) ));
1566 DEBUG(4,("TTL = PERMANENT\t"));
1568 for (i = 0; i < namerec->data.num_ips; i++)
1569 DEBUG(4,("%15s ", inet_ntoa(namerec->data.ip[i]) ));
1570 DEBUG(4,("%2x\n", namerec->data.nb_flags ));
1572 if( namerec->data.source == REGISTER_NAME )
1574 fprintf(fp, "\"%s#%02x\" %d ",
1575 namerec->name.name,namerec->name.name_type, /* Ignore scope. */
1576 (int)namerec->data.death_time);
1578 for (i = 0; i < namerec->data.num_ips; i++)
1579 fprintf( fp, "%s ", inet_ntoa( namerec->data.ip[i] ) );
1580 fprintf( fp, "%2xR\n", namerec->data.nb_flags );
1586 chmod(fnamenew,0644);
1587 rename(fnamenew,fname);