2 Unix SMB/Netbios implementation.
4 NBT netbios routines and daemon - version 2
5 Copyright (C) Andrew Tridgell 1994-1995
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23 14 jan 96: lkcl@pires.co.uk
24 added multiple workgroup domain master support
32 extern int ClientDGRAM;
34 extern int DEBUGLEVEL;
37 extern BOOL CanRecurse;
38 extern pstring myname;
39 extern struct in_addr ipzero;
40 extern struct in_addr ipgrp;
42 /* netbios names database */
43 struct name_record *namelist;
45 #define GET_TTL(ttl) ((ttl)?MIN(ttl,lp_max_ttl()):lp_max_ttl())
48 /****************************************************************************
49 true if two netbios names are equal
50 ****************************************************************************/
51 static BOOL name_equal(struct nmb_name *n1,struct nmb_name *n2)
53 if (n1->name_type != n2->name_type) return(False);
55 return(strequal(n1->name,n2->name) && strequal(n1->scope,n2->scope));
58 /****************************************************************************
59 add a netbios name into the namelist
60 **************************************************************************/
61 static void add_name(struct name_record *n)
63 struct name_record *n2;
73 for (n2 = namelist; n2->next; n2 = n2->next) ;
80 /****************************************************************************
81 remove a name from the namelist. The pointer must be an element just
83 **************************************************************************/
84 void remove_name(struct name_record *n)
86 struct name_record *nlist = namelist;
88 while (nlist && nlist != n) nlist = nlist->next;
92 if (nlist->next) nlist->next->prev = nlist->prev;
93 if (nlist->prev) nlist->prev->next = nlist->next;
99 /****************************************************************************
100 find a name in the domain database namelist
102 FIND_SELF - look for names the samba server has added for itself
103 FIND_GLOBAL - the name can be anyone. first look on the client's
104 subnet, then the server's subnet, then all subnets.
105 **************************************************************************/
106 static struct name_record *find_name_search(struct nmb_name *name,
107 enum name_search search,
110 struct name_record *ret;
112 for (ret = namelist; ret; ret = ret->next)
114 if (!name_equal(&ret->name,name)) continue;
116 if (search == FIND_SELF && ret->source != SELF) continue;
125 /****************************************************************************
126 dump a copy of the name table
127 **************************************************************************/
128 void dump_names(void)
130 struct name_record *n;
131 time_t t = time(NULL);
133 DEBUG(3,("Dump of local name table:\n"));
135 for (n = namelist; n; n = n->next)
137 DEBUG(3,("%s %s TTL=%d NBFLAGS=%2x\n",
140 n->death_time?n->death_time-t:0,
146 /****************************************************************************
147 remove an entry from the name list
148 ****************************************************************************/
149 void remove_netbios_name(char *name,int type, enum name_source source,
153 struct name_record *n;
155 make_nmb_name(&nn, name, type, scope);
156 n = find_name_search(&nn, FIND_GLOBAL, ip);
158 if (n && n->source == source) remove_name(n);
162 /****************************************************************************
163 add an entry to the name list
164 ****************************************************************************/
165 struct name_record *add_netbios_entry(char *name, int type, int nb_flags,
167 enum name_source source,
171 struct name_record *n;
172 struct name_record *n2=NULL;
174 n = (struct name_record *)malloc(sizeof(*n));
175 if (!n) return(NULL);
177 bzero((char *)n,sizeof(*n));
179 make_nmb_name(&n->name,name,type,scope);
181 if ((n2 = find_name_search(&n->name, FIND_GLOBAL, new_only?ipzero:ip)))
184 if (new_only || (n2->source==SELF && source!=SELF)) return n2;
188 if (ttl) n->death_time = time(NULL)+ttl*3;
190 n->nb_flags = nb_flags;
193 if (!n2) add_name(n);
195 DEBUG(3,("Added netbios name %s at %s ttl=%d nb_flags=%2x\n",
196 namestr(&n->name),inet_ntoa(ip),ttl,nb_flags));
202 /****************************************************************************
203 remove an entry from the name list
204 ****************************************************************************/
205 void remove_name_entry(char *name,int type)
207 if (lp_wins_support())
209 /* we are a WINS server. */
210 remove_netbios_name(name,type,SELF,ipzero);
217 queue_netbios_pkt_wins(ClientNMB,NMB_REL,NAME_RELEASE,
224 /****************************************************************************
225 add an entry to the name list
226 ****************************************************************************/
227 void add_name_entry(char *name,int type,int nb_flags)
229 /* always add our own entries */
230 add_netbios_entry(name,type,nb_flags,0,SELF,ipzero,False);
232 if (!lp_wins_support())
237 queue_netbios_pkt_wins(ClientNMB,NMB_REG,NAME_REGISTER,
238 name, type, nb_flags,
244 /****************************************************************************
245 add the magic samba names, useful for finding samba servers
246 **************************************************************************/
247 void add_my_names(void)
253 add_name_entry(myname,0x20,NB_ACTIVE);
254 add_name_entry(myname,0x03,NB_ACTIVE);
255 add_name_entry(myname,0x00,NB_ACTIVE);
256 add_name_entry(myname,0x1f,NB_ACTIVE);
258 add_netbios_entry("*",0x0,NB_ACTIVE,0,SELF,ip,False);
259 add_netbios_entry("__SAMBA__",0x20,NB_ACTIVE,0,SELF,ip,False);
260 add_netbios_entry("__SAMBA__",0x00,NB_ACTIVE,0,SELF,ip,False);
262 if (lp_wins_support()) {
263 /* the 0x1c name gets added by any WINS server it seems */
264 add_name_entry(my_workgroup(),0x1c,NB_ACTIVE|NB_GROUP);
268 /****************************************************************************
269 remove all the samba names... from a WINS server if necessary.
270 **************************************************************************/
271 void remove_my_names()
273 struct name_record *n;
275 for (n = namelist; n; n = n->next)
277 if (n->source == SELF)
279 /* get all SELF names removed from the WINS server's database */
280 remove_name_entry(n->name.name, n->name.name_type);
286 /*******************************************************************
288 ******************************************************************/
289 void refresh_my_names(time_t t)
291 static time_t lasttime = 0;
293 if (t - lasttime < REFRESH_TIME)
300 /*******************************************************************
301 expires old names in the namelist
302 ******************************************************************/
303 void expire_names(time_t t)
305 struct name_record *n;
306 struct name_record *next;
308 /* expire old names */
309 for (n = namelist; n; n = next)
311 if (n->death_time && n->death_time < t)
313 DEBUG(3,("Removing dead name %s\n", namestr(&n->name)));
317 if (n->prev) n->prev->next = n->next;
318 if (n->next) n->next->prev = n->prev;
320 if (namelist == n) namelist = n->next;
332 /****************************************************************************
333 response for a reg release received
334 **************************************************************************/
335 void response_name_release(struct packet_struct *p)
337 struct nmb_packet *nmb = &p->packet.nmb;
338 char *name = nmb->question.question_name.name;
339 int type = nmb->question.question_name.name_type;
341 DEBUG(4,("response name release received\n"));
343 if (nmb->header.rcode == 0 && nmb->answers->rdata)
345 struct in_addr found_ip;
346 putip((char*)&found_ip,&nmb->answers->rdata[2]);
348 if (ismyip(found_ip))
350 remove_netbios_name(name,type,SELF,found_ip);
355 DEBUG(1,("name registration for %s rejected!\n",
356 namestr(&nmb->question.question_name)));
361 /****************************************************************************
362 reply to a name release
363 ****************************************************************************/
364 void reply_name_release(struct packet_struct *p)
366 struct nmb_packet *nmb = &p->packet.nmb;
369 int opcode = nmb->header.opcode;
370 int nb_flags = nmb->additional->rdata[0];
371 BOOL bcast = nmb->header.nm_flags.bcast;
372 struct name_record *n;
375 putip((char *)&ip,&nmb->additional->rdata[2]);
377 DEBUG(3,("Name release on name %s rcode=%d\n",
378 namestr(&nmb->question.question_name),rcode));
380 n = find_name_search(&nmb->question.question_name, FIND_GLOBAL, ip);
382 /* XXXX under what conditions should we reject the removal?? */
383 if (n && n->nb_flags == nb_flags)
396 putip(&rdata[2],(char *)&ip);
398 /* Send a NAME RELEASE RESPONSE */
399 reply_netbios_packet(p,nmb->header.name_trn_id,
401 &nmb->question.question_name,
402 nmb->question.question_type,
403 nmb->question.question_class,
409 /****************************************************************************
410 response for a reg request received
411 **************************************************************************/
412 void response_name_reg(struct packet_struct *p)
414 struct nmb_packet *nmb = &p->packet.nmb;
415 char *name = nmb->question.question_name.name;
416 int type = nmb->question.question_name.name_type;
418 DEBUG(4,("response name registration received!\n"));
420 if (nmb->header.rcode == 0 && nmb->answers->rdata)
422 int nb_flags = nmb->answers->rdata[0];
423 struct in_addr found_ip;
424 int ttl = nmb->answers->ttl;
425 enum name_source source = REGISTER;
427 putip((char*)&found_ip,&nmb->answers->rdata[2]);
429 if (ismyip(found_ip)) source = SELF;
431 add_netbios_entry(name,type,nb_flags,ttl,source,found_ip,True);
435 DEBUG(1,("name registration for %s rejected!\n",
436 namestr(&nmb->question.question_name)));
441 /****************************************************************************
442 reply to a reg request
443 **************************************************************************/
444 void reply_name_reg(struct packet_struct *p)
446 struct nmb_packet *nmb = &p->packet.nmb;
447 struct nmb_name *question = &nmb->question.question_name;
449 struct nmb_name *reply_name = question;
450 char *qname = question->name;
451 int name_type = question->name_type;
452 int name_class = nmb->question.question_class;
454 BOOL bcast = nmb->header.nm_flags.bcast;
456 int ttl = GET_TTL(nmb->additional->ttl);
457 int nb_flags = nmb->additional->rdata[0];
458 BOOL group = NAME_GROUP(nb_flags);
460 int opcode = nmb->header.opcode;
462 struct name_record *n = NULL;
464 BOOL recurse = True; /* true if samba replies yes/no: false if caller */
465 /* must challenge the current owner */
468 struct in_addr ip, from_ip;
470 DEBUG(3,("Name registration for name %s at %s rcode=%d\n",
471 namestr(question),inet_ntoa(ip),rcode));
473 putip((char *)&from_ip,&nmb->additional->rdata[2]);
478 /* apparently we should return 255.255.255.255 for group queries
483 /* see if the name already exists */
484 n = find_name_search(question, FIND_GLOBAL, from_ip);
488 if (!group) /* unique names */
490 if (n->source == SELF || NAME_GROUP(n->nb_flags))
492 /* no-one can register one of samba's names, nor can they
493 register a name that's a group name as a unique name */
498 else if(!ip_equal(ip, n->ip))
500 /* hm. this unique name doesn't belong to them. */
502 /* XXXX rfc1001.txt says:
503 * if we are doing secured WINS, we must send a Wait-Acknowledge
504 * packet (WACK) to the person who wants the name, then do a
505 * name query on the person who currently owns the unique name.
506 * if the current owner is alive, the person who wants the name
507 * can't have it. if they are not alive, they can.
509 * if we are doing non-secure WINS (which is much simpler) then
510 * we send a message to the person wanting the name saying 'he
511 * owns this name: i don't want to hear from you ever again
512 * until you've checked with him if you can have it!'. we then
513 * abandon the registration. once the person wanting the name
514 * has checked with the current owner, they will repeat the
515 * registration packet if the current owner is dead or doesn't
519 /* non-secured WINS implementation: caller is responsible
520 for checking with current owner of name, then getting back
521 to us... IF current owner no longer owns the unique name */
527 /* we inform on the current owner to the caller (which is
528 why it's non-secure */
530 reply_name = &n->name;
534 XXXX sorry, guys: i really can't see what name_type
535 and name_class should be set to according to rfc1001 */
539 /* XXXX removed code that checked with the owner of a name */
542 n->death_time = ttl?p->timestamp+ttl*3:0;
543 DEBUG(3,("%s owner: %s\n",namestr(&n->name),inet_ntoa(n->ip)));
548 /* refresh the name */
549 if (n->source != SELF)
551 n->death_time = ttl?p->timestamp + ttl*3:0;
557 /* add the name to our subnet/name database */
558 n = add_netbios_entry(qname,name_type,nb_flags,ttl,REGISTER,ip,True);
565 update_from_reg(nmb->question.question_name.name,
566 nmb->question.question_name.name_type, from_ip);
571 putip(&rdata[2],(char *)&ip);
573 /* Send a NAME REGISTRATION RESPONSE (pos/neg)
574 or and END-NODE CHALLENGE REGISTRATION RESPONSE */
575 reply_netbios_packet(p,nmb->header.name_trn_id,
576 rcode,opcode,recurse,
577 reply_name, name_type, name_class,
583 /****************************************************************************
584 reply to a name status query
585 ****************************************************************************/
586 void reply_name_status(struct packet_struct *p)
588 struct nmb_packet *nmb = &p->packet.nmb;
589 char *qname = nmb->question.question_name.name;
590 int ques_type = nmb->question.question_name.name_type;
591 char rdata[MAX_DGRAM_SIZE];
592 char *countptr, *buf, *bufend;
594 struct name_record *n;
596 DEBUG(3,("Name status for name %s %s\n",
597 namestr(&nmb->question.question_name), inet_ntoa(p->ip)));
599 n = find_name_search(&nmb->question.question_name,FIND_GLOBAL, p->ip);
603 /* XXXX hack, we should calculate exactly how many will fit */
604 bufend = &rdata[MAX_DGRAM_SIZE] - 18;
605 countptr = buf = rdata;
610 for (n = namelist ; n && buf < bufend; n = n->next)
612 int name_type = n->name.name_type;
614 if (n->source != SELF) continue;
616 /* start with first bit of putting info in buffer: the name */
619 sprintf(buf,"%-15.15s",n->name.name);
622 /* now check if we want to exclude other workgroup names
623 from the response. if we don't exclude them, windows clients
624 get confused and will respond with an error for NET VIEW */
626 if (name_type >= 0x1b && name_type <= 0x20 &&
627 ques_type >= 0x1b && ques_type <= 0x20)
629 if (!strequal(qname, n->name.name)) continue;
632 /* carry on putting name info in buffer */
635 buf[16] = n->nb_flags;
642 SCVAL(countptr,0,names_added);
644 /* XXXXXXX we should fill in more fields of the statistics structure */
647 extern int num_good_sends,num_good_receives;
648 SIVAL(buf,20,num_good_sends);
649 SIVAL(buf,24,num_good_receives);
652 SIVAL(buf,46,0xFFB8E5); /* undocumented - used by NT */
656 /* Send a POSITIVE NAME STATUS RESPONSE */
657 reply_netbios_packet(p,nmb->header.name_trn_id,
659 &nmb->question.question_name,
660 nmb->question.question_type,
661 nmb->question.question_class,
663 rdata,PTR_DIFF(buf,rdata));
667 /***************************************************************************
668 reply to a name query
669 ****************************************************************************/
670 static struct name_record *search_for_name(struct nmb_name *question,
671 struct in_addr ip, int Time,
672 enum name_search search)
674 int name_type = question->name_type;
675 char *qname = question->name;
676 BOOL dns_type = name_type == 0x20 || name_type == 0;
678 struct name_record *n;
680 DEBUG(3,("Search for %s from %s - ", namestr(question), inet_ntoa(ip)));
682 /* first look up name in cache. use ip as well as name to locate it */
683 n = find_name_search(question,search,ip);
685 /* now try DNS lookup. */
688 struct in_addr dns_ip;
691 /* only do DNS lookups if the query is for type 0x20 or type 0x0 */
694 DEBUG(3,("types 0x20 0x1b 0x0 only: name not found\n"));
698 /* look it up with DNS */
699 a = interpret_addr(qname);
701 putip((char *)&dns_ip,(char *)&a);
705 /* no luck with DNS. We could possibly recurse here XXXX */
706 /* if this isn't a bcast then we should send a negative reply XXXX */
707 DEBUG(3,("no recursion\n"));
708 add_netbios_entry(qname,name_type,NB_ACTIVE,60*60,DNSFAIL,dns_ip,True);
712 /* add it to our cache of names. give it 2 hours in the cache */
713 n = add_netbios_entry(qname,name_type,NB_ACTIVE,2*60*60,DNS,dns_ip,True);
715 /* failed to add it? yikes! */
719 /* is our entry already dead? */
722 if (n->death_time < Time) return False;
725 /* it may have been an earlier failure */
726 if (n->source == DNSFAIL)
728 DEBUG(3,("DNSFAIL\n"));
732 DEBUG(3,("OK %s\n",inet_ntoa(n->ip)));
739 /***************************************************************************
740 reply to a name query
741 ****************************************************************************/
742 void reply_name_query(struct packet_struct *p)
744 struct nmb_packet *nmb = &p->packet.nmb;
745 struct nmb_name *question = &nmb->question.question_name;
746 int name_type = question->name_type;
747 BOOL dns_type = name_type == 0x20 || name_type == 0;
748 BOOL bcast = nmb->header.nm_flags.bcast;
752 struct in_addr retip;
755 struct name_record *n;
756 enum name_search search = (dns_type || name_type == 0x1b) ?
757 FIND_GLOBAL : FIND_SELF;
759 DEBUG(3,("Name query "));
761 if ((n = search_for_name(question,p->ip,p->timestamp, search)))
763 /* don't respond to broadcast queries unless the query is for
764 a name we own or it is for a Primary Domain Controller name */
765 if (bcast && n->source != SELF && name_type != 0x1b)
767 if (!lp_wins_proxy() || same_net(p->ip,n->ip,*iface_nmask(p->ip))) {
768 /* never reply with a negative response to broadcast queries */
773 /* name is directed query, or it's self, or it's a PDC type name */
774 ttl = n->death_time - p->timestamp;
776 nb_flags = n->nb_flags;
780 if (bcast) return; /* never reply negative response to bcasts */
784 /* if the IP is 0 then substitute my IP */
785 if (zero_ip(retip)) retip = *iface_ip(p->ip);
790 DEBUG(3,("OK %s\n",inet_ntoa(retip)));
795 DEBUG(3,("UNKNOWN\n"));
802 putip(&rdata[2],(char *)&retip);
805 reply_netbios_packet(p,nmb->header.name_trn_id,
807 &nmb->question.question_name,
808 nmb->question.question_type,
809 nmb->question.question_class,
811 rdata, success ? 6 : 0);
816 /****************************************************************************
817 response from a name query
818 ****************************************************************************/
819 static void response_netbios_packet(struct packet_struct *p)
821 struct nmb_packet *nmb = &p->packet.nmb;
822 struct nmb_name *question = &nmb->question.question_name;
823 char *qname = question->name;
824 BOOL bcast = nmb->header.nm_flags.bcast;
825 struct name_response_record *n;
827 if (nmb->answers == NULL)
829 DEBUG(3,("NMB packet response from %s (bcast=%s) - UNKNOWN\n",
835 if (nmb->answers->rr_type == NMB_STATUS) {
836 DEBUG(3,("Name status "));
839 if (nmb->answers->rr_type == NMB_QUERY) {
840 DEBUG(3,("Name query "));
843 if (nmb->answers->rr_type == NMB_REG) {
844 DEBUG(3,("Name registration "));
847 if (nmb->answers->rr_type == NMB_REL) {
848 DEBUG(3,("Name release "));
851 DEBUG(3,("response for %s from %s (bcast=%s)\n",
852 namestr(&nmb->answers->rr_name),
856 if (!(n = find_name_query(nmb->header.name_trn_id))) {
857 DEBUG(3,("unknown response (received too late or from nmblookup?)\n"));
861 n->num_msgs++; /* count number of responses received */
865 case MASTER_SERVER_CHECK : DEBUG(4,("MASTER_SVR_CHECK\n")); break;
866 case SERVER_CHECK : DEBUG(4,("SERVER_CHECK\n")); break;
867 case FIND_MASTER : DEBUG(4,("FIND_MASTER\n")); break;
868 case NAME_STATUS_MASTER_CHECK: DEBUG(4,("NAME_STAT_MST_CHK\n")); break;
869 case NAME_STATUS_CHECK : DEBUG(4,("NAME_STATUS_CHECK\n")); break;
870 case CHECK_MASTER : DEBUG(4,("CHECK_MASTER\n")); break;
871 case NAME_CONFIRM_QUERY : DEBUG(4,("NAME_CONFIRM_QUERY\n")); break;
876 case MASTER_SERVER_CHECK:
880 if (nmb->answers->rr_type == NMB_QUERY)
882 enum cmd_type cmd = (n->cmd_type == MASTER_SERVER_CHECK) ?
883 NAME_STATUS_MASTER_CHECK :
885 if (n->num_msgs > 1 && !strequal(qname,n->name.name))
887 /* one subnet, one master browser per workgroup */
888 /* XXXX force an election? */
889 DEBUG(1,("more than one master browser replied!\n"));
892 /* initiate a name status check on the server that replied */
893 queue_netbios_packet(ClientNMB,NMB_STATUS, cmd,
894 nmb->answers->rr_name.name,
895 nmb->answers->rr_name.name_type,0,
896 False,False,n->to_ip);
900 DEBUG(1,("Name query reply has wrong answer rr_type\n"));
905 case NAME_STATUS_MASTER_CHECK:
906 case NAME_STATUS_CHECK:
908 if (nmb->answers->rr_type == NMB_STATUS)
910 /* NMB_STATUS arrives: contains the workgroup name
911 and server name we require */
912 struct nmb_name name;
915 if (interpret_node_status(nmb->answers->rdata,
916 &name,0x1d,serv_name,p->ip))
920 sync_server(n->cmd_type,serv_name,
921 name.name,name.name_type,
927 DEBUG(1,("No 0x1d name type in interpret_node_status()\n"));
932 DEBUG(1,("Name status reply has wrong answer rr_type\n"));
939 /* no action required here. it's when NO responses are received
940 that we need to do something (see expire_name_query_entries) */
942 DEBUG(4, ("Master browser exists for %s at %s\n",
944 inet_ntoa(n->to_ip)));
947 DEBUG(1,("more than one master browser!\n"));
949 if (nmb->answers->rr_type != NMB_QUERY)
951 DEBUG(1,("Name query reply has wrong answer rr_type\n"));
955 case NAME_CONFIRM_QUERY:
957 DEBUG(4, ("Name query at WINS server: %s at %s - ",
959 inet_ntoa(n->to_ip)));
960 if (nmb->header.rcode == 0 && nmb->answers->rdata)
962 int nb_flags = nmb->answers->rdata[0];
963 struct in_addr found_ip;
964 putip((char*)&found_ip,&nmb->answers->rdata[2]);
966 DEBUG(4, (" OK: %s\n", inet_ntoa(found_ip)));
967 add_netbios_entry(nmb->answers->rr_name.name,
968 nmb->answers->rr_name.name_type,
969 nb_flags,GET_TTL(0),STATUS_QUERY,found_ip,False);
973 DEBUG(4, (" NEGATIVE RESPONSE\n"));
980 DEBUG(0,("unknown command received in response_netbios_packet\n"));
987 /****************************************************************************
989 ****************************************************************************/
990 void process_nmb(struct packet_struct *p)
992 struct nmb_packet *nmb = &p->packet.nmb;
996 switch (nmb->header.opcode)
1002 if (nmb->header.qdcount==0 || nmb->header.arcount==0) break;
1003 if (nmb->header.response)
1004 response_name_reg(p);
1012 if (nmb->header.response)
1014 switch (nmb->question.question_type)
1018 response_netbios_packet(p);
1024 else if (nmb->header.qdcount>0)
1026 switch (nmb->question.question_type)
1030 reply_name_query(p);
1035 reply_name_status(p);
1046 if (nmb->header.qdcount==0 || nmb->header.arcount==0)
1048 DEBUG(2,("netbios release packet rejected\n"));
1052 if (nmb->header.response)
1053 response_name_release(p);
1055 reply_name_release(p);