1 /* -*- Mode: C; tab-width: 4 -*-
3 * Copyright (c) 2006 Apple Computer, Inc. All rights reserved.
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
17 Change History (most recent first):
19 $Log: dnsextd_parser.y,v $
20 Revision 1.9 2009/01/11 03:20:06 mkrochma
21 <rdar://problem/5797526> Fixes from Igor Seleznev to get mdnsd working on Solaris
23 Revision 1.8 2007/03/21 19:47:50 cheshire
24 <rdar://problem/4789463> Leak: On error path in ParseConfig
26 Revision 1.7 2007/01/17 17:38:13 cheshire
27 Need to include stdlib.h for malloc/free
29 Revision 1.6 2006/12/22 20:59:51 cheshire
30 <rdar://problem/4742742> Read *all* DNS keys from keychain,
31 not just key for the system-wide default registration domain
33 Revision 1.5 2006/10/20 05:47:09 herscher
34 Set the DNSZone pointer to NULL in ParseConfig() before parsing the configuration file.
36 Revision 1.4 2006/08/16 00:35:39 mkrochma
37 <rdar://problem/4386944> Get rid of NotAnInteger references
39 Revision 1.3 2006/08/14 23:24:56 cheshire
40 Re-licensed mDNSResponder daemon source code under Apache License, Version 2.0
42 Revision 1.2 2006/07/14 02:03:37 cheshire
43 <rdar://problem/4472013> Add Private DNS server functionality to dnsextd
44 private_port and llq_port should use htons, not htonl
46 Revision 1.1 2006/07/06 00:09:05 cheshire
47 <rdar://problem/4472013> Add Private DNS server functionality to dnsextd
55 #include "mDNSEmbeddedAPI.h"
56 #include "DebugServices.h"
59 void yyerror( const char* error );
63 typedef struct StringListElem
66 struct StringListElem * next;
70 typedef struct OptionsInfo
72 char server_address[ 256 ];
74 char source_address[ 256 ];
81 typedef struct ZoneInfo
84 char certificate_name[ 256 ];
85 char allow_clients_file[ 256 ];
86 char allow_clients[ 256 ];
91 typedef struct KeySpec
94 char algorithm[ 256 ];
96 struct KeySpec * next;
100 typedef struct ZoneSpec
103 DNSZoneSpecType type;
104 StringListElem * allowUpdate;
105 StringListElem * allowQuery;
107 struct ZoneSpec * next;
111 static StringListElem * g_stringList = NULL;
112 static KeySpec * g_keys;
113 static ZoneSpec * g_zones;
114 static ZoneSpec g_zoneSpec;
115 static const char * g_filename;
117 #define YYPARSE_PARAM context
156 %token <string> DOTTED_DECIMAL_ADDRESS
157 %token <string> WILDCARD
158 %token <string> DOMAINNAME
159 %token <string> HOSTNAME
160 %token <string> QUOTEDSTRING
161 %token <number> NUMBER
163 %type <string> addressstatement
164 %type <string> networkaddress
170 commands command SEMICOLON
184 OPTIONS optionscontent
186 // SetupOptions( &g_optionsInfo, context );
191 OBRACE optionsstatements EBRACE
196 optionsstatements optionsstatement SEMICOLON
203 LISTEN_ON addresscontent
207 LISTEN_ON PORT NUMBER addresscontent
211 NAMESERVER ADDRESS networkaddress
215 NAMESERVER ADDRESS networkaddress PORT NUMBER
221 ( ( DaemonInfo* ) context )->private_port = mDNSOpaque16fromIntVal( NUMBER );
226 ( ( DaemonInfo* ) context )->llq_port = mDNSOpaque16fromIntVal( NUMBER );
231 KEY QUOTEDSTRING OBRACE SECRET QUOTEDSTRING SEMICOLON EBRACE
235 keySpec = ( KeySpec* ) malloc( sizeof( KeySpec ) );
239 LogMsg("ERROR: memory allocation failure");
243 strncpy( keySpec->name, $2, sizeof( keySpec->name ) );
244 strncpy( keySpec->secret, $5, sizeof( keySpec->secret ) );
246 keySpec->next = g_keys;
252 ZONE QUOTEDSTRING zonecontent
256 zoneSpec = ( ZoneSpec* ) malloc( sizeof( ZoneSpec ) );
260 LogMsg("ERROR: memory allocation failure");
264 strncpy( zoneSpec->name, $2, sizeof( zoneSpec->name ) );
265 zoneSpec->type = g_zoneSpec.type;
266 strcpy( zoneSpec->key, g_zoneSpec.key );
267 zoneSpec->allowUpdate = g_zoneSpec.allowUpdate;
268 zoneSpec->allowQuery = g_zoneSpec.allowQuery;
270 zoneSpec->next = g_zones;
274 ZONE QUOTEDSTRING IN zonecontent
278 zoneSpec = ( ZoneSpec* ) malloc( sizeof( ZoneSpec ) );
282 LogMsg("ERROR: memory allocation failure");
286 strncpy( zoneSpec->name, $2, sizeof( zoneSpec->name ) );
287 zoneSpec->type = g_zoneSpec.type;
288 strcpy( zoneSpec->key, g_zoneSpec.key );
289 zoneSpec->allowUpdate = g_zoneSpec.allowUpdate;
290 zoneSpec->allowQuery = g_zoneSpec.allowQuery;
292 zoneSpec->next = g_zones;
298 OBRACE zonestatements EBRACE
302 zonestatements zonestatement SEMICOLON
308 g_zoneSpec.type = kDNSZonePublic;
313 g_zoneSpec.type = kDNSZonePrivate;
316 ALLOWUPDATE keycontent
318 g_zoneSpec.allowUpdate = g_stringList;
322 ALLOWQUERY keycontent
324 g_zoneSpec.allowQuery = g_stringList;
330 OBRACE addressstatements EBRACE
336 addressstatements addressstatement SEMICOLON
342 DOTTED_DECIMAL_ADDRESS
349 OBRACE keystatements EBRACE
355 keystatements keystatement SEMICOLON
363 StringListElem * elem;
365 elem = ( StringListElem* ) malloc( sizeof( StringListElem ) );
369 LogMsg("ERROR: memory allocation failure");
375 elem->next = g_stringList;
382 DOTTED_DECIMAL_ADDRESS
390 OBRACE zonestatements EBRACE SEMICOLON
414 void yyerror( const char *str )
416 fprintf( stderr,"%s:%d: error: %s\n", g_filename, yylineno, str );
434 DomainAuthInfo * key;
441 // Tear down the current zone specifiers
447 DNSZone * next = zone->next;
449 key = zone->updateKeys;
453 DomainAuthInfo * nextKey = key->next;
460 key = zone->queryKeys;
464 DomainAuthInfo * nextKey = key->next;
478 yyin = fopen( file, "r" );
479 require_action( yyin, exit, err = 0 );
481 err = yyparse( ( void* ) d );
482 require_action( !err, exit, err = 1 );
484 for ( zoneSpec = g_zones; zoneSpec; zoneSpec = zoneSpec->next )
486 StringListElem * elem;
489 zone = ( DNSZone* ) malloc( sizeof( DNSZone ) );
490 require_action( zone, exit, err = 1 );
491 memset( zone, 0, sizeof( DNSZone ) );
493 zone->next = d->zones;
496 // Fill in the domainname
498 ok = MakeDomainNameFromDNSNameString( &zone->name, zoneSpec->name );
499 require_action( ok, exit, err = 1 );
503 zone->type = zoneSpec->type;
505 // Fill in the allow-update keys
507 for ( elem = zoneSpec->allowUpdate; elem; elem = elem->next )
509 mDNSBool found = mDNSfalse;
511 for ( keySpec = g_keys; keySpec; keySpec = keySpec->next )
513 if ( strcmp( elem->string, keySpec->name ) == 0 )
515 DomainAuthInfo * authInfo = malloc( sizeof( DomainAuthInfo ) );
517 require_action( authInfo, exit, err = 1 );
518 memset( authInfo, 0, sizeof( DomainAuthInfo ) );
520 ok = MakeDomainNameFromDNSNameString( &authInfo->keyname, keySpec->name );
521 if (!ok) { free(authInfo); err = 1; goto exit; }
523 keylen = DNSDigest_ConstructHMACKeyfromBase64( authInfo, keySpec->secret );
524 if (keylen < 0) { free(authInfo); err = 1; goto exit; }
526 authInfo->next = zone->updateKeys;
527 zone->updateKeys = authInfo;
536 require_action( found, exit, err = 1 );
539 // Fill in the allow-query keys
541 for ( elem = zoneSpec->allowQuery; elem; elem = elem->next )
543 mDNSBool found = mDNSfalse;
545 for ( keySpec = g_keys; keySpec; keySpec = keySpec->next )
547 if ( strcmp( elem->string, keySpec->name ) == 0 )
549 DomainAuthInfo * authInfo = malloc( sizeof( DomainAuthInfo ) );
551 require_action( authInfo, exit, err = 1 );
552 memset( authInfo, 0, sizeof( DomainAuthInfo ) );
554 ok = MakeDomainNameFromDNSNameString( &authInfo->keyname, keySpec->name );
555 if (!ok) { free(authInfo); err = 1; goto exit; }
557 keylen = DNSDigest_ConstructHMACKeyfromBase64( authInfo, keySpec->secret );
558 if (keylen < 0) { free(authInfo); err = 1; goto exit; }
560 authInfo->next = zone->queryKeys;
561 zone->queryKeys = authInfo;
570 require_action( found, exit, err = 1 );
587 DaemonInfo * d = ( DaemonInfo* ) context;
589 if ( strlen( info->source_address ) )
591 inet_pton( AF_INET, info->source_address, &d->addr.sin_addr );
594 if ( info->source_port )
596 d->addr.sin_port = htons( ( mDNSu16 ) info->source_port );
599 if ( strlen( info->server_address ) )
601 inet_pton( AF_INET, info->server_address, &d->ns_addr.sin_addr );
604 if ( info->server_port )
606 d->ns_addr.sin_port = htons( ( mDNSu16 ) info->server_port );
609 if ( info->private_port )
611 d->private_port = mDNSOpaque16fromIntVal( info->private_port );
614 if ( info->llq_port )
616 d->llq_port = mDNSOpaque16fromIntVal( info->llq_port );