2 Linux DNS client library implementation
3 Copyright (C) 2006 Krishna Ganugapati <krishnag@centeris.com>
4 Copyright (C) 2006 Gerald Carter <jerry@samba.org>
6 ** NOTE! The following LGPL license applies to the libaddns
7 ** library. This does NOT imply that all of Samba is released
10 This library is free software; you can redistribute it and/or
11 modify it under the terms of the GNU Lesser General Public
12 License as published by the Free Software Foundation; either
13 version 2.1 of the License, or (at your option) any later version.
15 This library is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
18 Lesser General Public License for more details.
20 You should have received a copy of the GNU Lesser General Public
21 License along with this library; if not, write to the Free Software
22 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
28 /*********************************************************************
29 *********************************************************************/
31 static int32
DNSStdMarshallQuestionSection( HANDLE hSendBuffer
,
32 DNS_QUESTION_RECORD
** ppDNSQuestionRecords
,
38 DNS_QUESTION_RECORD
*pDNSQuestionRecord
= NULL
;
39 int16 wnQueryType
= 0;
40 int16 wnQueryClass
= 0;
42 for ( i
= 0; i
< wQuestions
; i
++ ) {
44 pDNSQuestionRecord
= *( ppDNSQuestionRecords
+ i
);
46 DNSMarshallDomainName( hSendBuffer
,
49 BAIL_ON_ERROR( dwError
);
51 wnQueryType
= htons( pDNSQuestionRecord
->wQueryType
);
53 DNSMarshallBuffer( hSendBuffer
,
54 ( uint8
* ) & wnQueryType
,
55 ( int32
) sizeof( int16
),
57 BAIL_ON_ERROR( dwError
);
59 wnQueryClass
= htons( pDNSQuestionRecord
->wQueryClass
);
61 DNSMarshallBuffer( hSendBuffer
,
62 ( uint8
* ) & wnQueryClass
,
63 ( int32
) sizeof( int16
),
65 BAIL_ON_ERROR( dwError
);
75 /*********************************************************************
76 *********************************************************************/
78 static int32
DNSStdMarshallAnswerSection( HANDLE hSendBuffer
,
79 DNS_RR_RECORD
** ppDNSAnswerRRRecords
,
84 DNS_RR_RECORD
*pDNSAnswerRRRecord
= NULL
;
87 for ( i
= 0; i
< wAnswers
; i
++ ) {
89 pDNSAnswerRRRecord
= *( ppDNSAnswerRRRecords
+ i
);
92 DNSMarshallRRHeader( hSendBuffer
,
94 BAIL_ON_ERROR( dwError
);
96 dwError
= DNSMarshallRData( hSendBuffer
, pDNSAnswerRRRecord
);
97 BAIL_ON_ERROR( dwError
);
107 /*********************************************************************
108 *********************************************************************/
110 static int32
DNSStdMarshallAuthoritySection( HANDLE hSendBuffer
,
111 DNS_RR_RECORD
** ppDNSAuthorityRRRecords
,
117 DNS_RR_RECORD
*pDNSAuthorityRRRecord
= NULL
;
119 for ( i
= 0; i
< wAuthoritys
; i
++ ) {
121 pDNSAuthorityRRRecord
= *( ppDNSAuthorityRRRecords
+ i
);
124 DNSMarshallRRHeader( hSendBuffer
,
125 pDNSAuthorityRRRecord
);
127 dwError
= DNSMarshallRData( hSendBuffer
,
128 pDNSAuthorityRRRecord
);
129 BAIL_ON_ERROR( dwError
);
137 /*********************************************************************
138 *********************************************************************/
140 static int32
DNSStdMarshallAdditionalSection( HANDLE hSendBuffer
,
141 DNS_RR_RECORD
** ppDNSAdditionalsRRRecords
,
146 DNS_RR_RECORD
*pDNSAdditionalRRRecord
= NULL
;
148 for ( i
= 0; i
< wAdditionals
; i
++ ) {
150 pDNSAdditionalRRRecord
= *( ppDNSAdditionalsRRRecords
+ i
);
153 DNSMarshallRRHeader( hSendBuffer
,
154 pDNSAdditionalRRRecord
);
155 BAIL_ON_ERROR( dwError
);
157 dwError
= DNSMarshallRData( hSendBuffer
,
158 pDNSAdditionalRRRecord
);
159 BAIL_ON_ERROR( dwError
);
168 /*********************************************************************
169 *********************************************************************/
171 static int32
DNSBuildRequestMessage( DNS_REQUEST
* pDNSRequest
, HANDLE
* phSendBuffer
)
174 char DNSMessageHeader
[12];
175 int16 wnIdentification
= 0;
176 int16 wnParameter
= 0;
177 int16 wnQuestions
= 0;
179 int16 wnAuthoritys
= 0;
180 int16 wnAdditionals
= 0;
182 HANDLE hSendBuffer
= ( HANDLE
) NULL
;
184 dwError
= DNSCreateSendBuffer( &hSendBuffer
);
185 BAIL_ON_ERROR( dwError
);
187 wnIdentification
= htons( pDNSRequest
->wIdentification
);
188 memcpy( DNSMessageHeader
, ( char * ) &wnIdentification
, 2 );
190 wnParameter
= htons( pDNSRequest
->wParameter
);
191 memcpy( DNSMessageHeader
+ 2, ( char * ) &wnParameter
, 2 );
193 wnQuestions
= htons( pDNSRequest
->wQuestions
);
194 memcpy( DNSMessageHeader
+ 4, ( char * ) &wnQuestions
, 2 );
196 wnAnswers
= htons( pDNSRequest
->wAnswers
);
197 memcpy( DNSMessageHeader
+ 6, ( char * ) &wnAnswers
, 2 );
199 wnAuthoritys
= htons( pDNSRequest
->wAuthoritys
);
200 memcpy( DNSMessageHeader
+ 8, ( char * ) &wnAuthoritys
, 2 );
202 wnAdditionals
= htons( pDNSRequest
->wAdditionals
);
203 memcpy( DNSMessageHeader
+ 10, ( char * ) &wnAdditionals
, 2 );
206 DNSMarshallBuffer( hSendBuffer
, ( uint8
* ) DNSMessageHeader
,
208 BAIL_ON_ERROR( dwError
);
210 if ( pDNSRequest
->wQuestions
) {
212 DNSStdMarshallQuestionSection( hSendBuffer
,
217 BAIL_ON_ERROR( dwError
);
220 if ( pDNSRequest
->wAnswers
) {
222 DNSStdMarshallAnswerSection( hSendBuffer
,
225 pDNSRequest
->wAnswers
);
226 BAIL_ON_ERROR( dwError
);
229 if ( pDNSRequest
->wAuthoritys
) {
231 DNSStdMarshallAuthoritySection( hSendBuffer
,
236 BAIL_ON_ERROR( dwError
);
239 if ( pDNSRequest
->wAdditionals
) {
241 DNSStdMarshallAdditionalSection( hSendBuffer
,
246 BAIL_ON_ERROR( dwError
);
249 DNSDumpSendBufferContext( hSendBuffer
);
251 *phSendBuffer
= hSendBuffer
;
258 DNSFreeSendBufferContext( hSendBuffer
);
261 *phSendBuffer
= ( HANDLE
) NULL
;
265 /*********************************************************************
266 *********************************************************************/
268 int32
DNSStdSendStdRequest2( HANDLE hDNSServer
, DNS_REQUEST
* pDNSRequest
)
271 int32 dwBytesSent
= 0;
272 HANDLE hSendBuffer
= ( HANDLE
) NULL
;
274 dwError
= DNSBuildRequestMessage( pDNSRequest
, &hSendBuffer
);
275 BAIL_ON_ERROR( dwError
);
278 DNSSendBufferContext( hDNSServer
, hSendBuffer
, &dwBytesSent
);
279 BAIL_ON_ERROR( dwError
);
284 DNSFreeSendBufferContext( hSendBuffer
);
290 /*********************************************************************
291 *********************************************************************/
293 int32
DNSMarshallDomainName( HANDLE hSendBuffer
, DNS_DOMAIN_NAME
* pDomainName
)
296 DNS_DOMAIN_LABEL
*pTemp
= NULL
;
301 pTemp
= pDomainName
->pLabelList
;
303 dwLen
= ( int32
) strlen( pTemp
->pszLabel
);
305 DNSMarshallBuffer( hSendBuffer
, ( uint8
* ) & dwLen
,
306 sizeof( char ), &dwSent
);
307 BAIL_ON_ERROR( dwError
);
310 DNSMarshallBuffer( hSendBuffer
,
311 ( uint8
* ) pTemp
->pszLabel
, dwLen
,
313 BAIL_ON_ERROR( dwError
);
314 pTemp
= pTemp
->pNext
;
316 DNSMarshallBuffer( hSendBuffer
, ( uint8
* ) & uEndChar
,
317 sizeof( char ), &dwSent
);
324 /*********************************************************************
325 *********************************************************************/
327 int32
DNSMarshallRRHeader( HANDLE hSendBuffer
, DNS_RR_RECORD
* pDNSRecord
)
333 int16 wnRDataSize
= 0;
337 DNSMarshallDomainName( hSendBuffer
,
338 pDNSRecord
->RRHeader
.pDomainName
);
339 BAIL_ON_ERROR( dwError
);
341 wnType
= htons( pDNSRecord
->RRHeader
.wType
);
343 DNSMarshallBuffer( hSendBuffer
, ( uint8
* ) & wnType
,
344 sizeof( int16
), &dwRead
);
345 BAIL_ON_ERROR( dwError
);
347 wnClass
= htons( pDNSRecord
->RRHeader
.wClass
);
349 DNSMarshallBuffer( hSendBuffer
, ( uint8
* ) & wnClass
,
350 sizeof( int16
), &dwRead
);
351 BAIL_ON_ERROR( dwError
);
353 dwnTTL
= htonl( pDNSRecord
->RRHeader
.dwTTL
);
355 DNSMarshallBuffer( hSendBuffer
, ( uint8
* ) & dwnTTL
,
356 sizeof( int32
), &dwRead
);
357 BAIL_ON_ERROR( dwError
);
359 wnRDataSize
= htons( pDNSRecord
->RRHeader
.wRDataSize
);
361 DNSMarshallBuffer( hSendBuffer
, ( uint8
* ) & wnRDataSize
,
362 sizeof( int16
), &dwRead
);
363 BAIL_ON_ERROR( dwError
);
370 /*********************************************************************
371 *********************************************************************/
373 int32
DNSMarshallRData( HANDLE hSendBuffer
, DNS_RR_RECORD
* pDNSRecord
)
379 DNSMarshallBuffer( hSendBuffer
, pDNSRecord
->pRData
,
380 pDNSRecord
->RRHeader
.wRDataSize
,
382 BAIL_ON_ERROR( dwError
);
389 /*********************************************************************
390 *********************************************************************/
392 int32
DNSStdAddQuestionSection( DNS_REQUEST
* pDNSRequest
,
393 DNS_QUESTION_RECORD
* pDNSQuestion
)
395 int32 dwNumQuestions
= 0;
398 dwNumQuestions
= pDNSRequest
->wQuestions
;
400 dwError
= DNSReallocMemory( ( uint8
* ) pDNSRequest
->ppQuestionRRSet
,
401 ( void * ) &pDNSRequest
->ppQuestionRRSet
,
403 1 ) * sizeof( DNS_QUESTION_RECORD
* )
405 BAIL_ON_ERROR( dwError
);
407 *( pDNSRequest
->ppQuestionRRSet
+ dwNumQuestions
) = pDNSQuestion
;
409 pDNSRequest
->wQuestions
+= 1;
416 /*********************************************************************
417 *********************************************************************/
419 int32
DNSStdAddAdditionalSection( DNS_REQUEST
* pDNSRequest
,
420 DNS_RR_RECORD
* pDNSRecord
)
422 int32 dwNumAdditionals
= 0;
425 dwNumAdditionals
= pDNSRequest
->wAdditionals
;
426 dwError
= DNSReallocMemory( pDNSRequest
->ppAdditionalRRSet
,
427 ( void * ) &pDNSRequest
->
430 1 ) * sizeof( DNS_RR_RECORD
* ) );
431 BAIL_ON_ERROR( dwError
);
433 *( pDNSRequest
->ppAdditionalRRSet
+ dwNumAdditionals
) = pDNSRecord
;
435 pDNSRequest
->wAdditionals
+= 1;
441 /*********************************************************************
442 *********************************************************************/
444 int32
DNSStdCreateStdRequest( DNS_REQUEST
** ppDNSRequest
)
447 DNS_REQUEST
*pDNSRequest
= NULL
;
450 int16 wRecursionDesired
= RECURSION_DESIRED
;
451 int16 wParameter
= QR_QUERY
;
452 int16 wOpcode
= OPCODE_QUERY
;
455 DNSAllocateMemory( sizeof( DNS_REQUEST
),
456 ( void * ) &pDNSRequest
);
457 BAIL_ON_ERROR( dwError
);
459 dwError
= DNSGenerateIdentifier( &pDNSRequest
->wIdentification
);
460 BAIL_ON_ERROR( dwError
);
464 wRecursionDesired <<= 7;
465 wParameter |= wOpcode;
466 wParameter |= wRecursionDesired;
468 pDNSRequest
->wParameter
= 0x00;
470 *ppDNSRequest
= pDNSRequest
;
476 *ppDNSRequest
= NULL
;