Index: projects/arpv2_merge_1/etc/regdomain.xml
===================================================================
--- projects/arpv2_merge_1/etc/regdomain.xml (revision 186114)
+++ projects/arpv2_merge_1/etc/regdomain.xml (revision 186115)
@@ -1,1580 +1,1717 @@
DEBUG
- 0
+ 0x1ff
FCC
0x10
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
23
23
IEEE80211_CHAN_PASSIVE
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
17
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
23
IEEE80211_CHAN_HT40
FCC3
0x3a
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
17
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
JAPAN
0x40
23
IEEE80211_CHAN_B
23
IEEE80211_CHAN_B
23
IEEE80211_CHAN_G
23
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
23
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
23
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
ETSI
0x30
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
24
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
17
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT40
24
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
24
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
ETSI2
0x32
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
24
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT20
24
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
ETSI3
0x33
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
24
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
17
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT40
24
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
24
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
APAC
0x50
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
23
IEEE80211_CHAN_PASSIVE
23
23
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
17
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT20
23
IEEE80211_CHAN_HT40
APAC2
0x51
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
23
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
17
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
IEEE80211_CHAN_HT20
23
IEEE80211_CHAN_HT40
APAC3
0x5d
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
17
23
IEEE80211_CHAN_PASSIVE
IEEE80211_CHAN_DFS
23
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
17
IEEE80211_CHAN_HT20
17
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT20
23
IEEE80211_CHAN_HT40
KOREA
0x45
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_B
IEEE80211_CHAN_PASSIVE
30
IEEE80211_CHAN_G
30
IEEE80211_CHAN_G
IEEE80211_CHAN_PASSIVE
17
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_PASSIVE
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
17
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
ROW
0x8a
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_G
23
IEEE80211_CHAN_PASSIVE
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
NONE
0xf0
30
IEEE80211_CHAN_B
30
IEEE80211_CHAN_B
IEEE80211_CHAN_PASSIVE
30
IEEE80211_CHAN_G
30
IEEE80211_CHAN_G
IEEE80211_CHAN_PASSIVE
17
IEEE80211_CHAN_PASSIVE
24
IEEE80211_CHAN_PASSIVE
24
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_PASSIVE
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
30
IEEE80211_CHAN_G
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
17
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
17
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
24
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
24
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
24
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
24
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT20
IEEE80211_CHAN_PASSIVE
23
IEEE80211_CHAN_HT40
IEEE80211_CHAN_PASSIVE
+
+
+ SR9
+ 0x0298
+
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+
+
+ XR9
+ 0x299
+
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+
+
+ GZ901
+ 0x29a
+
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
+ 30
+ IEEE80211_CHAN_G
+
+
+
8 Albania
12 Algeria
32 Argentina
51 Armenia
36 Australia
40 Austria
31 Azerbaijan
48 Bahrain
50 Bangladesh
112 Belarus
56 Belgium
84 Belize
68 Bolivia
76 Brazil
96 Brunei
100 Bulgaria
124 Canada
152 Chile
156 China
170 Colombia
188 Costa Rica
191 Croatia
196 Cyprus
203 Czech Republic
208 Denmark
214 Dominican Republic
218 Ecuador
818 Egypt
222 El Salvador
233 Estonia
246 Finland
250 France
255 France2
268 Georgia
276 Germany
300 Greece
320 Guatemala
+
+ 5002 ZComax GZ-901
+
340 Honduras
344 Hong Kong
348 Hungary
352 Iceland
356 India
360 Indonesia
364 Iran
372 Ireland
376 Israel
380 Italy
388 Jamaica
392 Japan
393 Japan1
394 Japan2
395 Japan3
396 Japan4
397 Japan5
400 Jordan
398 Kazakhstan
408 North Korea
410 Korea Republic
411 Korea Republic2
414 Kuwait
428 Latvia
422 Lebanon
438 Liechtenstein
440 Lithuania
442 Luxemborg
446 Macau
807 Macedonia
458 Malaysia
470 Malta
484 Mexico
492 Monaco
504 Morocco
524 Nepal
528 Netherlands
554 New Zealand
578 Norway
512 Oman
586 Pakistan
591 Panama
604 Peru
608 Phillipines
616 Poland
620 Portugal
630 Puerto Rico
634 Quatar
642 Romania
643 Rusia
682 Saudi Arabia
702 Singapore
703 Slovak Republic
705 Slovenia
710 South Africa
724 Spain
144 Sri Lanka
752 Sweden
756 Switzerland
760 Syria
158 Taiwan
764 Thailand
780 Tobago
788 Tunisia
792 Turkey
+
+ 5000 Ubiquiti SR9
+
+
+ 5001 Ubiquiti XR9
+
804 Ukraine
784 United Arab Emirates
826 United Kingdom
840 United States
858 Uruguay
860 Uzbekistan
862 Venezuela
704 Viet Nam
887 Yemen
716 Zimbabwe
+
+
+ 0 Debug
+
5120 5240
20 20
IEEE80211_CHAN_A
5120 5240
40 20
IEEE80211_CHAN_A
5180 5240
20 20
IEEE80211_CHAN_A
5180 5240
40 20
IEEE80211_CHAN_A
5200 5240
20 20
IEEE80211_CHAN_A
5200 5240
40 20
IEEE80211_CHAN_A
5260 5320
20 20
IEEE80211_CHAN_A
5260 5320
40 20
IEEE80211_CHAN_A
5260 5700
20 20
IEEE80211_CHAN_A
5280 5320
20 20
IEEE80211_CHAN_A
5280 5320
40 20
IEEE80211_CHAN_A
5500 5620
20 20
IEEE80211_CHAN_A
5500 5620
40 20
IEEE80211_CHAN_A
5500 5680
40 20
IEEE80211_CHAN_A
5500 5700
20 20
IEEE80211_CHAN_A
5725 5825
40 20
IEEE80211_CHAN_A
5745 5805
20 20
IEEE80211_CHAN_A
5745 5805
40 20
IEEE80211_CHAN_A
5745 5825
40 20
IEEE80211_CHAN_A
5825 5825
20 20
IEEE80211_CHAN_A
5825 5825
40 20
IEEE80211_CHAN_A
2312 2372
20 5
2412 2462
20 5
2412 2462
40 5
2412 2472
20 5
2412 2472
40 5
2467 2472
20 5
2467 2472
40 5
2484 2484
20 5
2512 2732
20 5
+
+
+ 2422 2437
+ 5 5
+ IEEE80211_CHAN_GSM
+ IEEE80211_CHAN_QUARTER
+
+
+ 2422 2437
+ 10 5
+ IEEE80211_CHAN_GSM
+ IEEE80211_CHAN_HALF
+
+
+ 2427 2432
+ 20 5
+ IEEE80211_CHAN_GSM
+
+
+
+ 2427 2442
+ 5 5
+ IEEE80211_CHAN_GSM
+ IEEE80211_CHAN_QUARTER
+
+
+ 2427 2442
+ 10 5
+ IEEE80211_CHAN_GSM
+ IEEE80211_CHAN_HALF
+
+
+ 2432 2437
+ 20 5
+ IEEE80211_CHAN_GSM
+
+
+
+ 2447 2467
+ 5 5
+ IEEE80211_CHAN_GSM
+ IEEE80211_CHAN_QUARTER
+
+
+ 2457 2462
+ 10 5
+ IEEE80211_CHAN_GSM
+ IEEE80211_CHAN_HALF
+
+
+ 2457 2462
+ 20 5
+ IEEE80211_CHAN_GSM
+
+
Index: projects/arpv2_merge_1/include/arpa/nameser.h
===================================================================
--- projects/arpv2_merge_1/include/arpa/nameser.h (revision 186114)
+++ projects/arpv2_merge_1/include/arpa/nameser.h (revision 186115)
@@ -1,583 +1,584 @@
/*
* Copyright (c) 1983, 1989, 1993
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
* Copyright (c) 1996-1999 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/*
- * $Id: nameser.h,v 1.7.18.1 2005/04/27 05:00:50 sra Exp $
+ * $Id: nameser.h,v 1.7.18.2 2008/04/03 23:15:15 marka Exp $
* $FreeBSD$
*/
#ifndef _ARPA_NAMESER_H_
#define _ARPA_NAMESER_H_
/*! \file */
#define BIND_4_COMPAT
#include
#include
#include
/*%
* Revision information. This is the release date in YYYYMMDD format.
* It can change every day so the right thing to do with it is use it
* in preprocessor commands such as "#if (__NAMESER > 19931104)". Do not
* compare for equality; rather, use it to determine whether your libbind.a
* contains a new enough lib/nameser/ to support the feature you need.
*/
#define __NAMESER 19991006 /*%< New interface version stamp. */
/*
* Define constants based on RFC0883, RFC1034, RFC 1035
*/
#define NS_PACKETSZ 512 /*%< default UDP packet size */
#define NS_MAXDNAME 1025 /*%< maximum domain name */
#define NS_MAXMSG 65535 /*%< maximum message size */
#define NS_MAXCDNAME 255 /*%< maximum compressed domain name */
#define NS_MAXLABEL 63 /*%< maximum length of domain label */
#define NS_HFIXEDSZ 12 /*%< #/bytes of fixed data in header */
#define NS_QFIXEDSZ 4 /*%< #/bytes of fixed data in query */
#define NS_RRFIXEDSZ 10 /*%< #/bytes of fixed data in r record */
#define NS_INT32SZ 4 /*%< #/bytes of data in a u_int32_t */
#define NS_INT16SZ 2 /*%< #/bytes of data in a u_int16_t */
#define NS_INT8SZ 1 /*%< #/bytes of data in a u_int8_t */
#define NS_INADDRSZ 4 /*%< IPv4 T_A */
#define NS_IN6ADDRSZ 16 /*%< IPv6 T_AAAA */
#define NS_CMPRSFLGS 0xc0 /*%< Flag bits indicating name compression. */
#define NS_DEFAULTPORT 53 /*%< For both TCP and UDP. */
/*
* These can be expanded with synonyms, just keep ns_parse.c:ns_parserecord()
* in synch with it.
*/
typedef enum __ns_sect {
ns_s_qd = 0, /*%< Query: Question. */
ns_s_zn = 0, /*%< Update: Zone. */
ns_s_an = 1, /*%< Query: Answer. */
ns_s_pr = 1, /*%< Update: Prerequisites. */
ns_s_ns = 2, /*%< Query: Name servers. */
ns_s_ud = 2, /*%< Update: Update. */
ns_s_ar = 3, /*%< Query|Update: Additional records. */
ns_s_max = 4
} ns_sect;
/*%
* This is a message handle. It is caller allocated and has no dynamic data.
* This structure is intended to be opaque to all but ns_parse.c, thus the
* leading _'s on the member names. Use the accessor functions, not the _'s.
*/
typedef struct __ns_msg {
const u_char *_msg, *_eom;
u_int16_t _id, _flags, _counts[ns_s_max];
const u_char *_sections[ns_s_max];
ns_sect _sect;
int _rrnum;
const u_char *_msg_ptr;
} ns_msg;
/* Private data structure - do not use from outside library. */
struct _ns_flagdata { int mask, shift; };
extern struct _ns_flagdata _ns_flagdata[];
/* Accessor macros - this is part of the public interface. */
#define ns_msg_id(handle) ((handle)._id + 0)
#define ns_msg_base(handle) ((handle)._msg + 0)
#define ns_msg_end(handle) ((handle)._eom + 0)
#define ns_msg_size(handle) ((handle)._eom - (handle)._msg)
#define ns_msg_count(handle, section) ((handle)._counts[section] + 0)
/*%
* This is a parsed record. It is caller allocated and has no dynamic data.
*/
typedef struct __ns_rr {
char name[NS_MAXDNAME];
u_int16_t type;
u_int16_t rr_class;
u_int32_t ttl;
u_int16_t rdlength;
const u_char * rdata;
} ns_rr;
/* Accessor macros - this is part of the public interface. */
#define ns_rr_name(rr) (((rr).name[0] != '\0') ? (rr).name : ".")
#define ns_rr_type(rr) ((ns_type)((rr).type + 0))
#define ns_rr_class(rr) ((ns_class)((rr).rr_class + 0))
#define ns_rr_ttl(rr) ((rr).ttl + 0)
#define ns_rr_rdlen(rr) ((rr).rdlength + 0)
#define ns_rr_rdata(rr) ((rr).rdata + 0)
/*%
* These don't have to be in the same order as in the packet flags word,
* and they can even overlap in some cases, but they will need to be kept
* in synch with ns_parse.c:ns_flagdata[].
*/
typedef enum __ns_flag {
ns_f_qr, /*%< Question/Response. */
ns_f_opcode, /*%< Operation code. */
ns_f_aa, /*%< Authoritative Answer. */
ns_f_tc, /*%< Truncation occurred. */
ns_f_rd, /*%< Recursion Desired. */
ns_f_ra, /*%< Recursion Available. */
ns_f_z, /*%< MBZ. */
ns_f_ad, /*%< Authentic Data (DNSSEC). */
ns_f_cd, /*%< Checking Disabled (DNSSEC). */
ns_f_rcode, /*%< Response code. */
ns_f_max
} ns_flag;
/*%
* Currently defined opcodes.
*/
typedef enum __ns_opcode {
ns_o_query = 0, /*%< Standard query. */
ns_o_iquery = 1, /*%< Inverse query (deprecated/unsupported). */
ns_o_status = 2, /*%< Name server status query (unsupported). */
/* Opcode 3 is undefined/reserved. */
ns_o_notify = 4, /*%< Zone change notification. */
ns_o_update = 5, /*%< Zone update message. */
ns_o_max = 6
} ns_opcode;
/*%
* Currently defined response codes.
*/
typedef enum __ns_rcode {
ns_r_noerror = 0, /*%< No error occurred. */
ns_r_formerr = 1, /*%< Format error. */
ns_r_servfail = 2, /*%< Server failure. */
ns_r_nxdomain = 3, /*%< Name error. */
ns_r_notimpl = 4, /*%< Unimplemented. */
ns_r_refused = 5, /*%< Operation refused. */
/* these are for BIND_UPDATE */
ns_r_yxdomain = 6, /*%< Name exists */
ns_r_yxrrset = 7, /*%< RRset exists */
ns_r_nxrrset = 8, /*%< RRset does not exist */
ns_r_notauth = 9, /*%< Not authoritative for zone */
ns_r_notzone = 10, /*%< Zone of record different from zone section */
ns_r_max = 11,
/* The following are EDNS extended rcodes */
ns_r_badvers = 16,
/* The following are TSIG errors */
ns_r_badsig = 16,
ns_r_badkey = 17,
ns_r_badtime = 18
} ns_rcode;
/* BIND_UPDATE */
typedef enum __ns_update_operation {
ns_uop_delete = 0,
ns_uop_add = 1,
ns_uop_max = 2
} ns_update_operation;
/*%
* This structure is used for TSIG authenticated messages
*/
struct ns_tsig_key {
char name[NS_MAXDNAME], alg[NS_MAXDNAME];
unsigned char *data;
int len;
};
typedef struct ns_tsig_key ns_tsig_key;
/*%
* This structure is used for TSIG authenticated TCP messages
*/
struct ns_tcp_tsig_state {
int counter;
struct dst_key *key;
void *ctx;
unsigned char sig[NS_PACKETSZ];
int siglen;
};
typedef struct ns_tcp_tsig_state ns_tcp_tsig_state;
#define NS_TSIG_FUDGE 300
#define NS_TSIG_TCP_COUNT 100
#define NS_TSIG_ALG_HMAC_MD5 "HMAC-MD5.SIG-ALG.REG.INT"
#define NS_TSIG_ERROR_NO_TSIG -10
#define NS_TSIG_ERROR_NO_SPACE -11
#define NS_TSIG_ERROR_FORMERR -12
/*%
* Currently defined type values for resources and queries.
*/
typedef enum __ns_type {
ns_t_invalid = 0, /*%< Cookie. */
ns_t_a = 1, /*%< Host address. */
ns_t_ns = 2, /*%< Authoritative server. */
ns_t_md = 3, /*%< Mail destination. */
ns_t_mf = 4, /*%< Mail forwarder. */
ns_t_cname = 5, /*%< Canonical name. */
ns_t_soa = 6, /*%< Start of authority zone. */
ns_t_mb = 7, /*%< Mailbox domain name. */
ns_t_mg = 8, /*%< Mail group member. */
ns_t_mr = 9, /*%< Mail rename name. */
ns_t_null = 10, /*%< Null resource record. */
ns_t_wks = 11, /*%< Well known service. */
ns_t_ptr = 12, /*%< Domain name pointer. */
ns_t_hinfo = 13, /*%< Host information. */
ns_t_minfo = 14, /*%< Mailbox information. */
ns_t_mx = 15, /*%< Mail routing information. */
ns_t_txt = 16, /*%< Text strings. */
ns_t_rp = 17, /*%< Responsible person. */
ns_t_afsdb = 18, /*%< AFS cell database. */
ns_t_x25 = 19, /*%< X_25 calling address. */
ns_t_isdn = 20, /*%< ISDN calling address. */
ns_t_rt = 21, /*%< Router. */
ns_t_nsap = 22, /*%< NSAP address. */
ns_t_nsap_ptr = 23, /*%< Reverse NSAP lookup (deprecated). */
ns_t_sig = 24, /*%< Security signature. */
ns_t_key = 25, /*%< Security key. */
ns_t_px = 26, /*%< X.400 mail mapping. */
ns_t_gpos = 27, /*%< Geographical position (withdrawn). */
ns_t_aaaa = 28, /*%< Ip6 Address. */
ns_t_loc = 29, /*%< Location Information. */
ns_t_nxt = 30, /*%< Next domain (security). */
ns_t_eid = 31, /*%< Endpoint identifier. */
ns_t_nimloc = 32, /*%< Nimrod Locator. */
ns_t_srv = 33, /*%< Server Selection. */
ns_t_atma = 34, /*%< ATM Address */
ns_t_naptr = 35, /*%< Naming Authority PoinTeR */
ns_t_kx = 36, /*%< Key Exchange */
ns_t_cert = 37, /*%< Certification record */
ns_t_a6 = 38, /*%< IPv6 address (deprecates AAAA) */
ns_t_dname = 39, /*%< Non-terminal DNAME (for IPv6) */
ns_t_sink = 40, /*%< Kitchen sink (experimentatl) */
ns_t_opt = 41, /*%< EDNS0 option (meta-RR) */
ns_t_apl = 42, /*%< Address prefix list (RFC3123) */
ns_t_tkey = 249, /*%< Transaction key */
ns_t_tsig = 250, /*%< Transaction signature. */
ns_t_ixfr = 251, /*%< Incremental zone transfer. */
ns_t_axfr = 252, /*%< Transfer zone of authority. */
ns_t_mailb = 253, /*%< Transfer mailbox records. */
ns_t_maila = 254, /*%< Transfer mail agent records. */
ns_t_any = 255, /*%< Wildcard match. */
ns_t_zxfr = 256, /*%< BIND-specific, nonstandard. */
ns_t_max = 65536
} ns_type;
/* Exclusively a QTYPE? (not also an RTYPE) */
#define ns_t_qt_p(t) (ns_t_xfr_p(t) || (t) == ns_t_any || \
(t) == ns_t_mailb || (t) == ns_t_maila)
/* Some kind of meta-RR? (not a QTYPE, but also not an RTYPE) */
#define ns_t_mrr_p(t) ((t) == ns_t_tsig || (t) == ns_t_opt)
/* Exclusively an RTYPE? (not also a QTYPE or a meta-RR) */
#define ns_t_rr_p(t) (!ns_t_qt_p(t) && !ns_t_mrr_p(t))
#define ns_t_udp_p(t) ((t) != ns_t_axfr && (t) != ns_t_zxfr)
#define ns_t_xfr_p(t) ((t) == ns_t_axfr || (t) == ns_t_ixfr || \
(t) == ns_t_zxfr)
/*%
* Values for class field
*/
typedef enum __ns_class {
ns_c_invalid = 0, /*%< Cookie. */
ns_c_in = 1, /*%< Internet. */
ns_c_2 = 2, /*%< unallocated/unsupported. */
ns_c_chaos = 3, /*%< MIT Chaos-net. */
ns_c_hs = 4, /*%< MIT Hesiod. */
/* Query class values which do not appear in resource records */
ns_c_none = 254, /*%< for prereq. sections in update requests */
ns_c_any = 255, /*%< Wildcard match. */
ns_c_max = 65536
} ns_class;
/* DNSSEC constants. */
typedef enum __ns_key_types {
ns_kt_rsa = 1, /*%< key type RSA/MD5 */
ns_kt_dh = 2, /*%< Diffie Hellman */
ns_kt_dsa = 3, /*%< Digital Signature Standard (MANDATORY) */
ns_kt_private = 254 /*%< Private key type starts with OID */
} ns_key_types;
typedef enum __ns_cert_types {
cert_t_pkix = 1, /*%< PKIX (X.509v3) */
cert_t_spki = 2, /*%< SPKI */
cert_t_pgp = 3, /*%< PGP */
cert_t_url = 253, /*%< URL private type */
cert_t_oid = 254 /*%< OID private type */
} ns_cert_types;
/* Flags field of the KEY RR rdata. */
#define NS_KEY_TYPEMASK 0xC000 /*%< Mask for "type" bits */
#define NS_KEY_TYPE_AUTH_CONF 0x0000 /*%< Key usable for both */
#define NS_KEY_TYPE_CONF_ONLY 0x8000 /*%< Key usable for confidentiality */
#define NS_KEY_TYPE_AUTH_ONLY 0x4000 /*%< Key usable for authentication */
#define NS_KEY_TYPE_NO_KEY 0xC000 /*%< No key usable for either; no key */
/* The type bits can also be interpreted independently, as single bits: */
#define NS_KEY_NO_AUTH 0x8000 /*%< Key unusable for authentication */
#define NS_KEY_NO_CONF 0x4000 /*%< Key unusable for confidentiality */
#define NS_KEY_RESERVED2 0x2000 /* Security is *mandatory* if bit=0 */
#define NS_KEY_EXTENDED_FLAGS 0x1000 /*%< reserved - must be zero */
#define NS_KEY_RESERVED4 0x0800 /*%< reserved - must be zero */
#define NS_KEY_RESERVED5 0x0400 /*%< reserved - must be zero */
#define NS_KEY_NAME_TYPE 0x0300 /*%< these bits determine the type */
#define NS_KEY_NAME_USER 0x0000 /*%< key is assoc. with user */
#define NS_KEY_NAME_ENTITY 0x0200 /*%< key is assoc. with entity eg host */
#define NS_KEY_NAME_ZONE 0x0100 /*%< key is zone key */
#define NS_KEY_NAME_RESERVED 0x0300 /*%< reserved meaning */
#define NS_KEY_RESERVED8 0x0080 /*%< reserved - must be zero */
#define NS_KEY_RESERVED9 0x0040 /*%< reserved - must be zero */
#define NS_KEY_RESERVED10 0x0020 /*%< reserved - must be zero */
#define NS_KEY_RESERVED11 0x0010 /*%< reserved - must be zero */
#define NS_KEY_SIGNATORYMASK 0x000F /*%< key can sign RR's of same name */
#define NS_KEY_RESERVED_BITMASK ( NS_KEY_RESERVED2 | \
NS_KEY_RESERVED4 | \
NS_KEY_RESERVED5 | \
NS_KEY_RESERVED8 | \
NS_KEY_RESERVED9 | \
NS_KEY_RESERVED10 | \
NS_KEY_RESERVED11 )
#define NS_KEY_RESERVED_BITMASK2 0xFFFF /*%< no bits defined here */
/* The Algorithm field of the KEY and SIG RR's is an integer, {1..254} */
#define NS_ALG_MD5RSA 1 /*%< MD5 with RSA */
#define NS_ALG_DH 2 /*%< Diffie Hellman KEY */
#define NS_ALG_DSA 3 /*%< DSA KEY */
#define NS_ALG_DSS NS_ALG_DSA
#define NS_ALG_EXPIRE_ONLY 253 /*%< No alg, no security */
#define NS_ALG_PRIVATE_OID 254 /*%< Key begins with OID giving alg */
/* Protocol values */
/* value 0 is reserved */
#define NS_KEY_PROT_TLS 1
#define NS_KEY_PROT_EMAIL 2
#define NS_KEY_PROT_DNSSEC 3
#define NS_KEY_PROT_IPSEC 4
#define NS_KEY_PROT_ANY 255
/* Signatures */
#define NS_MD5RSA_MIN_BITS 512 /*%< Size of a mod or exp in bits */
#define NS_MD5RSA_MAX_BITS 4096
/* Total of binary mod and exp */
#define NS_MD5RSA_MAX_BYTES ((NS_MD5RSA_MAX_BITS+7/8)*2+3)
/* Max length of text sig block */
#define NS_MD5RSA_MAX_BASE64 (((NS_MD5RSA_MAX_BYTES+2)/3)*4)
#define NS_MD5RSA_MIN_SIZE ((NS_MD5RSA_MIN_BITS+7)/8)
#define NS_MD5RSA_MAX_SIZE ((NS_MD5RSA_MAX_BITS+7)/8)
#define NS_DSA_SIG_SIZE 41
#define NS_DSA_MIN_SIZE 213
#define NS_DSA_MAX_BYTES 405
/* Offsets into SIG record rdata to find various values */
#define NS_SIG_TYPE 0 /*%< Type flags */
#define NS_SIG_ALG 2 /*%< Algorithm */
#define NS_SIG_LABELS 3 /*%< How many labels in name */
#define NS_SIG_OTTL 4 /*%< Original TTL */
#define NS_SIG_EXPIR 8 /*%< Expiration time */
#define NS_SIG_SIGNED 12 /*%< Signature time */
#define NS_SIG_FOOT 16 /*%< Key footprint */
#define NS_SIG_SIGNER 18 /*%< Domain name of who signed it */
/* How RR types are represented as bit-flags in NXT records */
#define NS_NXT_BITS 8
#define NS_NXT_BIT_SET( n,p) (p[(n)/NS_NXT_BITS] |= (0x80>>((n)%NS_NXT_BITS)))
#define NS_NXT_BIT_CLEAR(n,p) (p[(n)/NS_NXT_BITS] &= ~(0x80>>((n)%NS_NXT_BITS)))
#define NS_NXT_BIT_ISSET(n,p) (p[(n)/NS_NXT_BITS] & (0x80>>((n)%NS_NXT_BITS)))
#define NS_NXT_MAX 127
/*%
- * EDNS0 extended flags, host order.
+ * EDNS0 extended flags and option codes, host order.
*/
#define NS_OPT_DNSSEC_OK 0x8000U
+#define NS_OPT_NSID 3
/*%
* Inline versions of get/put short/long. Pointer is advanced.
*/
#define NS_GET16(s, cp) do { \
register const u_char *t_cp = (const u_char *)(cp); \
(s) = ((u_int16_t)t_cp[0] << 8) \
| ((u_int16_t)t_cp[1]) \
; \
(cp) += NS_INT16SZ; \
} while (0)
#define NS_GET32(l, cp) do { \
register const u_char *t_cp = (const u_char *)(cp); \
(l) = ((u_int32_t)t_cp[0] << 24) \
| ((u_int32_t)t_cp[1] << 16) \
| ((u_int32_t)t_cp[2] << 8) \
| ((u_int32_t)t_cp[3]) \
; \
(cp) += NS_INT32SZ; \
} while (0)
#define NS_PUT16(s, cp) do { \
register u_int16_t t_s = (u_int16_t)(s); \
register u_char *t_cp = (u_char *)(cp); \
*t_cp++ = t_s >> 8; \
*t_cp = t_s; \
(cp) += NS_INT16SZ; \
} while (0)
#define NS_PUT32(l, cp) do { \
register u_int32_t t_l = (u_int32_t)(l); \
register u_char *t_cp = (u_char *)(cp); \
*t_cp++ = t_l >> 24; \
*t_cp++ = t_l >> 16; \
*t_cp++ = t_l >> 8; \
*t_cp = t_l; \
(cp) += NS_INT32SZ; \
} while (0)
/*%
* ANSI C identifier hiding for bind's lib/nameser.
*/
#define ns_msg_getflag __ns_msg_getflag
#define ns_get16 __ns_get16
#define ns_get32 __ns_get32
#define ns_put16 __ns_put16
#define ns_put32 __ns_put32
#define ns_initparse __ns_initparse
#define ns_skiprr __ns_skiprr
#define ns_parserr __ns_parserr
#define ns_sprintrr __ns_sprintrr
#define ns_sprintrrf __ns_sprintrrf
#define ns_format_ttl __ns_format_ttl
#define ns_parse_ttl __ns_parse_ttl
#if 0
#define ns_datetosecs __ns_datetosecs
#endif
#define ns_name_ntol __ns_name_ntol
#define ns_name_ntop __ns_name_ntop
#define ns_name_pton __ns_name_pton
#define ns_name_unpack __ns_name_unpack
#define ns_name_pack __ns_name_pack
#define ns_name_compress __ns_name_compress
#define ns_name_uncompress __ns_name_uncompress
#define ns_name_skip __ns_name_skip
#define ns_name_rollback __ns_name_rollback
#if 0
#define ns_sign __ns_sign
#define ns_sign2 __ns_sign2
#define ns_sign_tcp __ns_sign_tcp
#define ns_sign_tcp2 __ns_sign_tcp2
#define ns_sign_tcp_init __ns_sign_tcp_init
#define ns_find_tsig __ns_find_tsig
#define ns_verify __ns_verify
#define ns_verify_tcp __ns_verify_tcp
#define ns_verify_tcp_init __ns_verify_tcp_init
#endif
#define ns_samedomain __ns_samedomain
#if 0
#define ns_subdomain __ns_subdomain
#endif
#define ns_makecanon __ns_makecanon
#define ns_samename __ns_samename
__BEGIN_DECLS
int ns_msg_getflag(ns_msg, int);
u_int ns_get16(const u_char *);
u_long ns_get32(const u_char *);
void ns_put16(u_int, u_char *);
void ns_put32(u_long, u_char *);
int ns_initparse(const u_char *, int, ns_msg *);
int ns_skiprr(const u_char *, const u_char *, ns_sect, int);
int ns_parserr(ns_msg *, ns_sect, int, ns_rr *);
int ns_sprintrr(const ns_msg *, const ns_rr *,
const char *, const char *, char *, size_t);
int ns_sprintrrf(const u_char *, size_t, const char *,
ns_class, ns_type, u_long, const u_char *,
size_t, const char *, const char *,
char *, size_t);
int ns_format_ttl(u_long, char *, size_t);
int ns_parse_ttl(const char *, u_long *);
#if 0
u_int32_t ns_datetosecs(const char *cp, int *errp);
#endif
int ns_name_ntol(const u_char *, u_char *, size_t);
int ns_name_ntop(const u_char *, char *, size_t);
int ns_name_pton(const char *, u_char *, size_t);
int ns_name_unpack(const u_char *, const u_char *,
const u_char *, u_char *, size_t);
int ns_name_pack(const u_char *, u_char *, int,
const u_char **, const u_char **);
int ns_name_uncompress(const u_char *, const u_char *,
const u_char *, char *, size_t);
int ns_name_compress(const char *, u_char *, size_t,
const u_char **, const u_char **);
int ns_name_skip(const u_char **, const u_char *);
void ns_name_rollback(const u_char *, const u_char **,
const u_char **);
#if 0
int ns_sign(u_char *, int *, int, int, void *,
const u_char *, int, u_char *, int *, time_t);
int ns_sign2(u_char *, int *, int, int, void *,
const u_char *, int, u_char *, int *, time_t,
u_char **, u_char **);
int ns_sign_tcp(u_char *, int *, int, int,
ns_tcp_tsig_state *, int);
int ns_sign_tcp2(u_char *, int *, int, int,
ns_tcp_tsig_state *, int,
u_char **, u_char **);
int ns_sign_tcp_init(void *, const u_char *, int,
ns_tcp_tsig_state *);
u_char *ns_find_tsig(u_char *, u_char *);
int ns_verify(u_char *, int *, void *,
const u_char *, int, u_char *, int *,
time_t *, int);
int ns_verify_tcp(u_char *, int *, ns_tcp_tsig_state *, int);
int ns_verify_tcp_init(void *, const u_char *, int,
ns_tcp_tsig_state *);
#endif
int ns_samedomain(const char *, const char *);
#if 0
int ns_subdomain(const char *, const char *);
#endif
int ns_makecanon(const char *, char *, size_t);
int ns_samename(const char *, const char *);
__END_DECLS
#ifdef BIND_4_COMPAT
#include
#endif
#endif /* !_ARPA_NAMESER_H_ */
/*! \file */
Index: projects/arpv2_merge_1/include/resolv.h
===================================================================
--- projects/arpv2_merge_1/include/resolv.h (revision 186114)
+++ projects/arpv2_merge_1/include/resolv.h (revision 186115)
@@ -1,498 +1,502 @@
/*
* Copyright (c) 1983, 1987, 1989
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. All advertising materials mentioning features or use of this software
* must display the following acknowledgement:
* This product includes software developed by the University of
* California, Berkeley and its contributors.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
* Portions Copyright (c) 1996-1999 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/*%
* @(#)resolv.h 8.1 (Berkeley) 6/2/93
- * $Id: resolv.h,v 1.19.18.3 2005/08/25 04:43:51 marka Exp $
+ * $Id: resolv.h,v 1.19.18.4 2008/04/03 23:15:15 marka Exp $
* $FreeBSD$
*/
#ifndef _RESOLV_H_
#define _RESOLV_H_
#include
#include
#include
#include
#include
#include
/*%
* Revision information. This is the release date in YYYYMMDD format.
* It can change every day so the right thing to do with it is use it
* in preprocessor commands such as "#if (__RES > 19931104)". Do not
* compare for equality; rather, use it to determine whether your resolver
* is new enough to contain a certain feature.
*/
#define __RES 20030124
/*%
* This used to be defined in res_query.c, now it's in herror.c.
* [XXX no it's not. It's in irs/irs_data.c]
* It was
* never extern'd by any *.h file before it was placed here. For thread
* aware programs, the last h_errno value set is stored in res->h_errno.
*
* XXX: There doesn't seem to be a good reason for exposing RES_SET_H_ERRNO
* (and __h_errno_set) to the public via .
* XXX: __h_errno_set is really part of IRS, not part of the resolver.
* If somebody wants to build and use a resolver that doesn't use IRS,
* what do they do? Perhaps something like
* #ifdef WANT_IRS
* # define RES_SET_H_ERRNO(r,x) __h_errno_set(r,x)
* #else
* # define RES_SET_H_ERRNO(r,x) (h_errno = (r)->res_h_errno = (x))
* #endif
*/
#define RES_SET_H_ERRNO(r,x) __h_errno_set(r,x)
struct __res_state; /*%< forward */
__BEGIN_DECLS
void __h_errno_set(struct __res_state *, int);
__END_DECLS
/*%
* Resolver configuration file.
* Normally not present, but may contain the address of the
* initial name server(s) to query and the domain search list.
*/
#ifndef _PATH_RESCONF
#define _PATH_RESCONF "/etc/resolv.conf"
#endif
typedef enum { res_goahead, res_nextns, res_modified, res_done, res_error }
res_sendhookact;
typedef res_sendhookact (*res_send_qhook)(struct sockaddr * const *,
const u_char **, int *,
u_char *, int, int *);
typedef res_sendhookact (*res_send_rhook)(const struct sockaddr *,
const u_char *, int, u_char *,
int, int *);
struct res_sym {
int number; /*%< Identifying number, like T_MX */
const char * name; /*%< Its symbolic name, like "MX" */
const char * humanname; /*%< Its fun name, like "mail exchanger" */
};
/*%
* Global defines and variables for resolver stub.
*/
#define MAXNS 3 /*%< max # name servers we'll track */
#define MAXDFLSRCH 3 /*%< # default domain levels to try */
#define MAXDNSRCH 6 /*%< max # domains in search path */
#define LOCALDOMAINPARTS 2 /*%< min levels in name that is "local" */
#define RES_TIMEOUT 5 /*%< min. seconds between retries */
#define MAXRESOLVSORT 10 /*%< number of net to sort on */
#define RES_MAXNDOTS 15 /*%< should reflect bit field size */
#define RES_MAXRETRANS 30 /*%< only for resolv.conf/RES_OPTIONS */
#define RES_MAXRETRY 5 /*%< only for resolv.conf/RES_OPTIONS */
#define RES_DFLRETRY 2 /*%< Default #/tries. */
#define RES_MAXTIME 65535 /*%< Infinity, in milliseconds. */
struct __res_state_ext;
struct __res_state {
int retrans; /*%< retransmission time interval */
int retry; /*%< number of times to retransmit */
/*
* XXX: If `sun' is defined, `options' and `pfcode' are
* defined as u_int in original BIND9 distribution. However,
* it breaks binary backward compatibility against FreeBSD's
* resolver. So, we changed not to see `sun'.
*/
#if defined(sun) && 0
u_int options; /*%< option flags - see below. */
#else
u_long options; /*%< option flags - see below. */
#endif
int nscount; /*%< number of name servers */
struct sockaddr_in
nsaddr_list[MAXNS]; /*%< address of name server */
#define nsaddr nsaddr_list[0] /*%< for backward compatibility */
u_short id; /*%< current message id */
char *dnsrch[MAXDNSRCH+1]; /*%< components of domain to search */
char defdname[256]; /*%< default domain (deprecated) */
#if defined(sun) && 0
u_int pfcode; /*%< RES_PRF_ flags - see below. */
#else
u_long pfcode; /*%< RES_PRF_ flags - see below. */
#endif
unsigned ndots:4; /*%< threshold for initial abs. query */
unsigned nsort:4; /*%< number of elements in sort_list[] */
char unused[3];
struct {
struct in_addr addr;
u_int32_t mask;
} sort_list[MAXRESOLVSORT];
res_send_qhook qhook; /*%< query hook */
res_send_rhook rhook; /*%< response hook */
int res_h_errno; /*%< last one set for this context */
int _vcsock; /*%< PRIVATE: for res_send VC i/o */
u_int _flags; /*%< PRIVATE: see below */
u_int _pad; /*%< make _u 64 bit aligned */
union {
/* On an 32-bit arch this means 512b total. */
char pad[72 - 4*sizeof (int) - 2*sizeof (void *)];
struct {
u_int16_t nscount;
u_int16_t nstimes[MAXNS]; /*%< ms. */
int nssocks[MAXNS];
struct __res_state_ext *ext; /*%< extention for IPv6 */
} _ext;
} _u;
};
typedef struct __res_state *res_state;
union res_sockaddr_union {
struct sockaddr_in sin;
#ifdef IN6ADDR_ANY_INIT
struct sockaddr_in6 sin6;
#endif
#ifdef ISC_ALIGN64
int64_t __align64; /*%< 64bit alignment */
#else
int32_t __align32; /*%< 32bit alignment */
#endif
char __space[128]; /*%< max size */
};
/*%
* Resolver flags (used to be discrete per-module statics ints).
*/
#define RES_F_VC 0x00000001 /*%< socket is TCP */
#define RES_F_CONN 0x00000002 /*%< socket is connected */
#define RES_F_EDNS0ERR 0x00000004 /*%< EDNS0 caused errors */
#define RES_F__UNUSED 0x00000008 /*%< (unused) */
#define RES_F_LASTMASK 0x000000F0 /*%< ordinal server of last res_nsend */
#define RES_F_LASTSHIFT 4 /*%< bit position of LASTMASK "flag" */
#define RES_GETLAST(res) (((res)._flags & RES_F_LASTMASK) >> RES_F_LASTSHIFT)
/* res_findzonecut2() options */
#define RES_EXHAUSTIVE 0x00000001 /*%< always do all queries */
#define RES_IPV4ONLY 0x00000002 /*%< IPv4 only */
#define RES_IPV6ONLY 0x00000004 /*%< IPv6 only */
/*%
* Resolver options (keep these in synch with res_debug.c, please)
*/
#define RES_INIT 0x00000001 /*%< address initialized */
#define RES_DEBUG 0x00000002 /*%< print debug messages */
#define RES_AAONLY 0x00000004 /*%< authoritative answers only (!IMPL)*/
#define RES_USEVC 0x00000008 /*%< use virtual circuit */
#define RES_PRIMARY 0x00000010 /*%< query primary server only (!IMPL) */
#define RES_IGNTC 0x00000020 /*%< ignore truncation errors */
#define RES_RECURSE 0x00000040 /*%< recursion desired */
#define RES_DEFNAMES 0x00000080 /*%< use default domain name */
#define RES_STAYOPEN 0x00000100 /*%< Keep TCP socket open */
#define RES_DNSRCH 0x00000200 /*%< search up local domain tree */
#define RES_INSECURE1 0x00000400 /*%< type 1 security disabled */
#define RES_INSECURE2 0x00000800 /*%< type 2 security disabled */
#define RES_NOALIASES 0x00001000 /*%< shuts off HOSTALIASES feature */
#define RES_USE_INET6 0x00002000 /*%< use/map IPv6 in gethostbyname() */
#define RES_ROTATE 0x00004000 /*%< rotate ns list after each query */
#define RES_NOCHECKNAME 0x00008000 /*%< do not check names for sanity. */
#define RES_KEEPTSIG 0x00010000 /*%< do not strip TSIG records */
#define RES_BLAST 0x00020000 /*%< blast all recursive servers */
+#define RES_NSID 0x00040000 /*%< request name server ID */
#define RES_NOTLDQUERY 0x00100000 /*%< don't unqualified name as a tld */
#define RES_USE_DNSSEC 0x00200000 /*%< use DNSSEC using OK bit in OPT */
/* #define RES_DEBUG2 0x00400000 */ /* nslookup internal */
/* KAME extensions: use higher bit to avoid conflict with ISC use */
#define RES_USE_DNAME 0x10000000 /*%< use DNAME */
#define RES_USE_EDNS0 0x40000000 /*%< use EDNS0 if configured */
#define RES_NO_NIBBLE2 0x80000000 /*%< disable alternate nibble lookup */
#define RES_DEFAULT (RES_RECURSE | RES_DEFNAMES | \
RES_DNSRCH | RES_NO_NIBBLE2)
/*%
* Resolver "pfcode" values. Used by dig.
*/
#define RES_PRF_STATS 0x00000001
#define RES_PRF_UPDATE 0x00000002
#define RES_PRF_CLASS 0x00000004
#define RES_PRF_CMD 0x00000008
#define RES_PRF_QUES 0x00000010
#define RES_PRF_ANS 0x00000020
#define RES_PRF_AUTH 0x00000040
#define RES_PRF_ADD 0x00000080
#define RES_PRF_HEAD1 0x00000100
#define RES_PRF_HEAD2 0x00000200
#define RES_PRF_TTLID 0x00000400
#define RES_PRF_HEADX 0x00000800
#define RES_PRF_QUERY 0x00001000
#define RES_PRF_REPLY 0x00002000
#define RES_PRF_INIT 0x00004000
#define RES_PRF_TRUNC 0x00008000
/* 0x00010000 */
/* Things involving an internal (static) resolver context. */
__BEGIN_DECLS
extern struct __res_state *__res_state(void);
__END_DECLS
#define _res (*__res_state())
#ifndef __BIND_NOSTATIC
#define fp_nquery __fp_nquery
#define fp_query __fp_query
#define hostalias __hostalias
#define p_query __p_query
#define res_close __res_close
#define res_init __res_init
#define res_isourserver __res_isourserver
#define res_mkquery __res_mkquery
#define res_opt __res_opt
#define res_query __res_query
#define res_querydomain __res_querydomain
#define res_search __res_search
#define res_send __res_send
#define res_sendsigned __res_sendsigned
__BEGIN_DECLS
void fp_nquery(const u_char *, int, FILE *);
void fp_query(const u_char *, FILE *);
const char * hostalias(const char *);
void p_query(const u_char *);
void res_close(void);
int res_init(void);
int res_isourserver(const struct sockaddr_in *);
int res_mkquery(int, const char *, int, int, const u_char *,
int, const u_char *, u_char *, int);
int res_opt(int, u_char *, int, int);
int res_query(const char *, int, int, u_char *, int);
int res_querydomain(const char *, const char *, int, int,
u_char *, int);
int res_search(const char *, int, int, u_char *, int);
int res_send(const u_char *, int, u_char *, int);
int res_sendsigned(const u_char *, int, ns_tsig_key *,
u_char *, int);
__END_DECLS
#endif
#if !defined(SHARED_LIBBIND) || defined(LIB)
/*
* If libbind is a shared object (well, DLL anyway)
* these externs break the linker when resolv.h is
* included by a lib client (like named)
* Make them go away if a client is including this
*
*/
extern const struct res_sym __p_key_syms[];
extern const struct res_sym __p_cert_syms[];
extern const struct res_sym __p_class_syms[];
extern const struct res_sym __p_type_syms[];
extern const struct res_sym __p_rcode_syms[];
#endif /* SHARED_LIBBIND */
#define b64_ntop __b64_ntop
#define b64_pton __b64_pton
#define dn_comp __dn_comp
#define dn_count_labels __dn_count_labels
#define dn_expand __dn_expand
#define dn_skipname __dn_skipname
#define fp_resstat __fp_resstat
#define loc_aton __loc_aton
#define loc_ntoa __loc_ntoa
#define p_cdname __p_cdname
#define p_cdnname __p_cdnname
#define p_class __p_class
#define p_fqname __p_fqname
#define p_fqnname __p_fqnname
#define p_option __p_option
#define p_secstodate __p_secstodate
#define p_section __p_section
#define p_time __p_time
#define p_type __p_type
#define p_rcode __p_rcode
#define p_sockun __p_sockun
#define putlong __putlong
#define putshort __putshort
#define res_dnok __res_dnok
#if 0
#define res_findzonecut __res_findzonecut
#endif
#define res_findzonecut2 __res_findzonecut2
#define res_hnok __res_hnok
#define res_hostalias __res_hostalias
#define res_mailok __res_mailok
#define res_nameinquery __res_nameinquery
#define res_nclose __res_nclose
#define res_ninit __res_ninit
#define res_nmkquery __res_nmkquery
#define res_pquery __res_pquery
#define res_nquery __res_nquery
#define res_nquerydomain __res_nquerydomain
#define res_nsearch __res_nsearch
#define res_nsend __res_nsend
#if 0
#define res_nsendsigned __res_nsendsigned
#endif
#define res_nisourserver __res_nisourserver
#define res_ownok __res_ownok
#define res_queriesmatch __res_queriesmatch
#define res_randomid __res_randomid
#define sym_ntop __sym_ntop
#define sym_ntos __sym_ntos
#define sym_ston __sym_ston
#define res_nopt __res_nopt
+#define res_nopt_rdata __res_nopt_rdata
#define res_ndestroy __res_ndestroy
#define res_nametoclass __res_nametoclass
#define res_nametotype __res_nametotype
#define res_setservers __res_setservers
#define res_getservers __res_getservers
#if 0
#define res_buildprotolist __res_buildprotolist
#define res_destroyprotolist __res_destroyprotolist
#define res_destroyservicelist __res_destroyservicelist
#define res_get_nibblesuffix __res_get_nibblesuffix
#define res_get_nibblesuffix2 __res_get_nibblesuffix2
#endif
#define res_ourserver_p __res_ourserver_p
#if 0
#define res_protocolname __res_protocolname
#define res_protocolnumber __res_protocolnumber
#endif
#define res_send_setqhook __res_send_setqhook
#define res_send_setrhook __res_send_setrhook
#if 0
#define res_servicename __res_servicename
#define res_servicenumber __res_servicenumber
#endif
__BEGIN_DECLS
int res_hnok(const char *);
int res_ownok(const char *);
int res_mailok(const char *);
int res_dnok(const char *);
int sym_ston(const struct res_sym *, const char *, int *);
const char * sym_ntos(const struct res_sym *, int, int *);
const char * sym_ntop(const struct res_sym *, int, int *);
int b64_ntop(u_char const *, size_t, char *, size_t);
int b64_pton(char const *, u_char *, size_t);
int loc_aton(const char *, u_char *);
const char * loc_ntoa(const u_char *, char *);
int dn_skipname(const u_char *, const u_char *);
void putlong(u_int32_t, u_char *);
void putshort(u_int16_t, u_char *);
#ifndef __ultrix__
u_int16_t _getshort(const u_char *);
u_int32_t _getlong(const u_char *);
#endif
const char * p_class(int);
const char * p_time(u_int32_t);
const char * p_type(int);
const char * p_rcode(int);
const char * p_sockun(union res_sockaddr_union, char *, size_t);
const u_char * p_cdnname(const u_char *, const u_char *, int, FILE *);
const u_char * p_cdname(const u_char *, const u_char *, FILE *);
const u_char * p_fqnname(const u_char *, const u_char *, int, char *, int);
const u_char * p_fqname(const u_char *, const u_char *, FILE *);
const char * p_option(u_long);
char * p_secstodate(u_long);
int dn_count_labels(const char *);
int dn_comp(const char *, u_char *, int, u_char **, u_char **);
int dn_expand(const u_char *, const u_char *, const u_char *,
char *, int);
u_int res_randomid(void);
int res_nameinquery(const char *, int, int, const u_char *,
const u_char *);
int res_queriesmatch(const u_char *, const u_char *,
const u_char *, const u_char *);
const char * p_section(int, int);
/* Things involving a resolver context. */
int res_ninit(res_state);
int res_nisourserver(const res_state, const struct sockaddr_in *);
void fp_resstat(const res_state, FILE *);
void res_pquery(const res_state, const u_char *, int, FILE *);
const char * res_hostalias(const res_state, const char *, char *, size_t);
int res_nquery(res_state, const char *, int, int, u_char *, int);
int res_nsearch(res_state, const char *, int, int, u_char *, int);
int res_nquerydomain(res_state, const char *, const char *,
int, int, u_char *, int);
int res_nmkquery(res_state, int, const char *, int, int,
const u_char *, int, const u_char *,
u_char *, int);
int res_nsend(res_state, const u_char *, int, u_char *, int);
#if 0
int res_nsendsigned(res_state, const u_char *, int,
ns_tsig_key *, u_char *, int);
int res_findzonecut(res_state, const char *, ns_class, int,
char *, size_t, struct in_addr *, int);
#endif
int res_findzonecut2(res_state, const char *, ns_class, int,
char *, size_t,
union res_sockaddr_union *, int);
void res_nclose(res_state);
int res_nopt(res_state, int, u_char *, int, int);
+int res_nopt_rdata(res_state, int, u_char *, int, u_char *,
+ u_short, u_short, u_char *);
void res_send_setqhook(res_send_qhook);
void res_send_setrhook(res_send_rhook);
int __res_vinit(res_state, int);
#if 0
void res_destroyservicelist(void);
const char * res_servicename(u_int16_t, const char *);
const char * res_protocolname(int);
void res_destroyprotolist(void);
void res_buildprotolist(void);
const char * res_get_nibblesuffix(res_state);
const char * res_get_nibblesuffix2(res_state);
#endif
void res_ndestroy(res_state);
u_int16_t res_nametoclass(const char *, int *);
u_int16_t res_nametotype(const char *, int *);
void res_setservers(res_state, const union res_sockaddr_union *,
int);
int res_getservers(res_state, union res_sockaddr_union *, int);
__END_DECLS
#endif /* !_RESOLV_H_ */
/*! \file */
Index: projects/arpv2_merge_1/lib/libc/include/isc/eventlib.h
===================================================================
--- projects/arpv2_merge_1/lib/libc/include/isc/eventlib.h (revision 186114)
+++ projects/arpv2_merge_1/lib/libc/include/isc/eventlib.h (revision 186115)
@@ -1,204 +1,206 @@
/*
* Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
* Copyright (c) 1995-1999 by Internet Software Consortium
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
/* eventlib.h - exported interfaces for eventlib
* vix 09sep95 [initial]
*
- * $Id: eventlib.h,v 1.3.18.2 2005/07/28 07:38:07 marka Exp $
+ * $Id: eventlib.h,v 1.3.18.3 2008/01/23 02:12:01 marka Exp $
*/
#ifndef _EVENTLIB_H
#define _EVENTLIB_H
#include
#include
#include
#include
+
+#include
#ifndef __P
# define __EVENTLIB_P_DEFINED
# ifdef __STDC__
# define __P(x) x
# else
# define __P(x) ()
# endif
#endif
/* In the absence of branded types... */
typedef struct { void *opaque; } evConnID;
typedef struct { void *opaque; } evFileID;
typedef struct { void *opaque; } evStreamID;
typedef struct { void *opaque; } evTimerID;
typedef struct { void *opaque; } evWaitID;
typedef struct { void *opaque; } evContext;
typedef struct { void *opaque; } evEvent;
#define evInitID(id) ((id)->opaque = NULL)
#define evTestID(id) ((id).opaque != NULL)
typedef void (*evConnFunc)__P((evContext, void *, int, const void *, int,
const void *, int));
typedef void (*evFileFunc)__P((evContext, void *, int, int));
typedef void (*evStreamFunc)__P((evContext, void *, int, int));
typedef void (*evTimerFunc)__P((evContext, void *,
struct timespec, struct timespec));
typedef void (*evWaitFunc)__P((evContext, void *, const void *));
typedef struct { unsigned char mask[256/8]; } evByteMask;
#define EV_BYTEMASK_BYTE(b) ((b) / 8)
#define EV_BYTEMASK_MASK(b) (1 << ((b) % 8))
#define EV_BYTEMASK_SET(bm, b) \
((bm).mask[EV_BYTEMASK_BYTE(b)] |= EV_BYTEMASK_MASK(b))
#define EV_BYTEMASK_CLR(bm, b) \
((bm).mask[EV_BYTEMASK_BYTE(b)] &= ~EV_BYTEMASK_MASK(b))
#define EV_BYTEMASK_TST(bm, b) \
((bm).mask[EV_BYTEMASK_BYTE(b)] & EV_BYTEMASK_MASK(b))
#define EV_POLL 1
#define EV_WAIT 2
#define EV_NULL 4
#define EV_READ 1
#define EV_WRITE 2
#define EV_EXCEPT 4
#define EV_WASNONBLOCKING 8 /* Internal library use. */
/* eventlib.c */
#define evCreate __evCreate
#define evSetDebug __evSetDebug
#define evDestroy __evDestroy
#define evGetNext __evGetNext
#define evDispatch __evDispatch
#define evDrop __evDrop
#define evMainLoop __evMainLoop
#define evHighestFD __evHighestFD
#define evGetOption __evGetOption
#define evSetOption __evSetOption
int evCreate __P((evContext *));
void evSetDebug __P((evContext, int, FILE *));
int evDestroy __P((evContext));
int evGetNext __P((evContext, evEvent *, int));
int evDispatch __P((evContext, evEvent));
void evDrop __P((evContext, evEvent));
int evMainLoop __P((evContext));
int evHighestFD __P((evContext));
int evGetOption __P((evContext *, const char *, int *));
int evSetOption __P((evContext *, const char *, int));
/* ev_connects.c */
#define evListen __evListen
#define evConnect __evConnect
#define evCancelConn __evCancelConn
#define evHold __evHold
#define evUnhold __evUnhold
#define evTryAccept __evTryAccept
int evListen __P((evContext, int, int, evConnFunc, void *, evConnID *));
int evConnect __P((evContext, int, const void *, int,
evConnFunc, void *, evConnID *));
int evCancelConn __P((evContext, evConnID));
int evHold __P((evContext, evConnID));
int evUnhold __P((evContext, evConnID));
int evTryAccept __P((evContext, evConnID, int *));
/* ev_files.c */
#define evSelectFD __evSelectFD
#define evDeselectFD __evDeselectFD
int evSelectFD __P((evContext, int, int, evFileFunc, void *, evFileID *));
int evDeselectFD __P((evContext, evFileID));
/* ev_streams.c */
#define evConsIovec __evConsIovec
#define evWrite __evWrite
#define evRead __evRead
#define evTimeRW __evTimeRW
#define evUntimeRW __evUntimeRW
#define evCancelRW __evCancelRW
struct iovec evConsIovec __P((void *, size_t));
int evWrite __P((evContext, int, const struct iovec *, int,
evStreamFunc func, void *, evStreamID *));
int evRead __P((evContext, int, const struct iovec *, int,
evStreamFunc func, void *, evStreamID *));
int evTimeRW __P((evContext, evStreamID, evTimerID timer));
int evUntimeRW __P((evContext, evStreamID));
int evCancelRW __P((evContext, evStreamID));
/* ev_timers.c */
#define evConsTime __evConsTime
#define evAddTime __evAddTime
#define evSubTime __evSubTime
#define evCmpTime __evCmpTime
#define evTimeSpec __evTimeSpec
#define evTimeVal __evTimeVal
#define evNowTime __evNowTime
#define evUTCTime __evUTCTime
#define evLastEventTime __evLastEventTime
#define evSetTimer __evSetTimer
#define evClearTimer __evClearTimer
#define evConfigTimer __evConfigTimer
#define evResetTimer __evResetTimer
#define evSetIdleTimer __evSetIdleTimer
#define evClearIdleTimer __evClearIdleTimer
#define evResetIdleTimer __evResetIdleTimer
#define evTouchIdleTimer __evTouchIdleTimer
struct timespec evConsTime __P((time_t sec, long nsec));
struct timespec evAddTime __P((struct timespec, struct timespec));
struct timespec evSubTime __P((struct timespec, struct timespec));
struct timespec evNowTime __P((void));
struct timespec evUTCTime __P((void));
struct timespec evLastEventTime __P((evContext));
struct timespec evTimeSpec __P((struct timeval));
struct timeval evTimeVal __P((struct timespec));
int evCmpTime __P((struct timespec, struct timespec));
int evSetTimer __P((evContext, evTimerFunc, void *, struct timespec,
struct timespec, evTimerID *));
int evClearTimer __P((evContext, evTimerID));
int evConfigTimer __P((evContext, evTimerID, const char *param,
int value));
int evResetTimer __P((evContext, evTimerID, evTimerFunc, void *,
struct timespec, struct timespec));
int evSetIdleTimer __P((evContext, evTimerFunc, void *, struct timespec,
evTimerID *));
int evClearIdleTimer __P((evContext, evTimerID));
int evResetIdleTimer __P((evContext, evTimerID, evTimerFunc, void *,
struct timespec));
int evTouchIdleTimer __P((evContext, evTimerID));
/* ev_waits.c */
#define evWaitFor __evWaitFor
#define evDo __evDo
#define evUnwait __evUnwait
#define evDefer __evDefer
int evWaitFor __P((evContext, const void *, evWaitFunc, void *, evWaitID *));
int evDo __P((evContext, const void *));
int evUnwait __P((evContext, evWaitID));
int evDefer __P((evContext, evWaitFunc, void *));
#ifdef __EVENTLIB_P_DEFINED
# undef __P
#endif
#endif /*_EVENTLIB_H*/
/*! \file */
Property changes on: projects/arpv2_merge_1/lib/libc/include/isc/eventlib.h
___________________________________________________________________
Added: fbsd:nokeywords
## -0,0 +1 ##
+y
\ No newline at end of property
Deleted: svn:keywords
## -1 +0,0 ##
-FreeBSD=%H
\ No newline at end of property
Index: projects/arpv2_merge_1/lib/libc/include/isc/platform.h
===================================================================
--- projects/arpv2_merge_1/lib/libc/include/isc/platform.h (nonexistent)
+++ projects/arpv2_merge_1/lib/libc/include/isc/platform.h (revision 186115)
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2008 Internet Systems Consortium, Inc. ("ISC")
+ *
+ * Permission to use, copy, modify, and/or distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
+ * REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
+ * AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
+ * INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
+ * LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
+ * OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
+ * PERFORMANCE OF THIS SOFTWARE.
+ */
+
+/* $Id: platform.h.in,v 1.2.6.2 2008/01/23 02:15:02 tbox Exp $ */
+/* $FreeBSD$ */
+
+/*! \file */
+
+#ifndef ISC_PLATFORM_H
+#define ISC_PLATFORM_H
+
+/*
+ * Define if the OS does not define struct timespec.
+ */
+#undef ISC_PLATFORM_NEEDTIMESPEC
+#ifdef ISC_PLATFORM_NEEDTIMESPEC
+#include /* For time_t */
+struct timespec {
+ time_t tv_sec; /* seconds */
+ long tv_nsec; /* nanoseconds */
+};
+#endif
+
+#endif
Index: projects/arpv2_merge_1/lib/libc/inet/inet_net_pton.c
===================================================================
--- projects/arpv2_merge_1/lib/libc/inet/inet_net_pton.c (revision 186114)
+++ projects/arpv2_merge_1/lib/libc/inet/inet_net_pton.c (revision 186115)
@@ -1,416 +1,416 @@
/*
* Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
* Copyright (c) 1996,1999 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#if defined(LIBC_SCCS) && !defined(lint)
-static const char rcsid[] = "$Id: inet_net_pton.c,v 1.7.18.1 2005/04/27 05:00:53 sra Exp $";
+static const char rcsid[] = "$Id: inet_net_pton.c,v 1.7.18.2 2008/08/26 04:42:43 marka Exp $";
#endif
#include
__FBSDID("$FreeBSD$");
#include "port_before.h"
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include "port_after.h"
#ifdef SPRINTF_CHAR
# define SPRINTF(x) strlen(sprintf/**/x)
#else
# define SPRINTF(x) ((size_t)sprintf x)
#endif
/*%
* static int
* inet_net_pton_ipv4(src, dst, size)
* convert IPv4 network number from presentation to network format.
* accepts hex octets, hex strings, decimal octets, and /CIDR.
* "size" is in bytes and describes "dst".
* return:
* number of bits, either imputed classfully or specified with /CIDR,
* or -1 if some failure occurred (check errno). ENOENT means it was
* not an IPv4 network specification.
* note:
* network byte order assumed. this means 192.5.5.240/28 has
* 0b11110000 in its fourth octet.
* author:
* Paul Vixie (ISC), June 1996
*/
static int
inet_net_pton_ipv4(const char *src, u_char *dst, size_t size) {
static const char xdigits[] = "0123456789abcdef";
static const char digits[] = "0123456789";
int n, ch, tmp = 0, dirty, bits;
const u_char *odst = dst;
ch = *src++;
if (ch == '0' && (src[0] == 'x' || src[0] == 'X')
&& isascii((unsigned char)(src[1]))
&& isxdigit((unsigned char)(src[1]))) {
/* Hexadecimal: Eat nybble string. */
if (size <= 0U)
goto emsgsize;
dirty = 0;
src++; /*%< skip x or X. */
while ((ch = *src++) != '\0' && isascii(ch) && isxdigit(ch)) {
if (isupper(ch))
ch = tolower(ch);
n = strchr(xdigits, ch) - xdigits;
assert(n >= 0 && n <= 15);
if (dirty == 0)
tmp = n;
else
tmp = (tmp << 4) | n;
if (++dirty == 2) {
if (size-- <= 0U)
goto emsgsize;
*dst++ = (u_char) tmp;
dirty = 0;
}
}
if (dirty) { /*%< Odd trailing nybble? */
if (size-- <= 0U)
goto emsgsize;
*dst++ = (u_char) (tmp << 4);
}
} else if (isascii(ch) && isdigit(ch)) {
/* Decimal: eat dotted digit string. */
for (;;) {
tmp = 0;
do {
n = strchr(digits, ch) - digits;
assert(n >= 0 && n <= 9);
tmp *= 10;
tmp += n;
if (tmp > 255)
goto enoent;
} while ((ch = *src++) != '\0' &&
isascii(ch) && isdigit(ch));
if (size-- <= 0U)
goto emsgsize;
*dst++ = (u_char) tmp;
if (ch == '\0' || ch == '/')
break;
if (ch != '.')
goto enoent;
ch = *src++;
if (!isascii(ch) || !isdigit(ch))
goto enoent;
}
} else
goto enoent;
bits = -1;
if (ch == '/' && isascii((unsigned char)(src[0])) &&
isdigit((unsigned char)(src[0])) && dst > odst) {
/* CIDR width specifier. Nothing can follow it. */
ch = *src++; /*%< Skip over the /. */
bits = 0;
do {
n = strchr(digits, ch) - digits;
assert(n >= 0 && n <= 9);
bits *= 10;
bits += n;
+ if (bits > 32)
+ goto enoent;
} while ((ch = *src++) != '\0' && isascii(ch) && isdigit(ch));
if (ch != '\0')
goto enoent;
- if (bits > 32)
- goto emsgsize;
}
/* Firey death and destruction unless we prefetched EOS. */
if (ch != '\0')
goto enoent;
/* If nothing was written to the destination, we found no address. */
if (dst == odst)
goto enoent;
/* If no CIDR spec was given, infer width from net class. */
if (bits == -1) {
if (*odst >= 240) /*%< Class E */
bits = 32;
else if (*odst >= 224) /*%< Class D */
bits = 8;
else if (*odst >= 192) /*%< Class C */
bits = 24;
else if (*odst >= 128) /*%< Class B */
bits = 16;
else /*%< Class A */
bits = 8;
/* If imputed mask is narrower than specified octets, widen. */
if (bits < ((dst - odst) * 8))
bits = (dst - odst) * 8;
/*
* If there are no additional bits specified for a class D
* address adjust bits to 4.
*/
if (bits == 8 && *odst == 224)
bits = 4;
}
/* Extend network to cover the actual mask. */
while (bits > ((dst - odst) * 8)) {
if (size-- <= 0U)
goto emsgsize;
*dst++ = '\0';
}
return (bits);
enoent:
errno = ENOENT;
return (-1);
emsgsize:
errno = EMSGSIZE;
return (-1);
}
static int
getbits(const char *src, int *bitsp) {
static const char digits[] = "0123456789";
int n;
int val;
char ch;
val = 0;
n = 0;
while ((ch = *src++) != '\0') {
const char *pch;
pch = strchr(digits, ch);
if (pch != NULL) {
if (n++ != 0 && val == 0) /*%< no leading zeros */
return (0);
val *= 10;
val += (pch - digits);
if (val > 128) /*%< range */
return (0);
continue;
}
return (0);
}
if (n == 0)
return (0);
*bitsp = val;
return (1);
}
static int
getv4(const char *src, u_char *dst, int *bitsp) {
static const char digits[] = "0123456789";
u_char *odst = dst;
int n;
u_int val;
char ch;
val = 0;
n = 0;
while ((ch = *src++) != '\0') {
const char *pch;
pch = strchr(digits, ch);
if (pch != NULL) {
if (n++ != 0 && val == 0) /*%< no leading zeros */
return (0);
val *= 10;
val += (pch - digits);
if (val > 255) /*%< range */
return (0);
continue;
}
if (ch == '.' || ch == '/') {
if (dst - odst > 3) /*%< too many octets? */
return (0);
*dst++ = val;
if (ch == '/')
return (getbits(src, bitsp));
val = 0;
n = 0;
continue;
}
return (0);
}
if (n == 0)
return (0);
if (dst - odst > 3) /*%< too many octets? */
return (0);
*dst++ = val;
return (1);
}
static int
inet_net_pton_ipv6(const char *src, u_char *dst, size_t size) {
static const char xdigits_l[] = "0123456789abcdef",
xdigits_u[] = "0123456789ABCDEF";
u_char tmp[NS_IN6ADDRSZ], *tp, *endp, *colonp;
const char *xdigits, *curtok;
int ch, saw_xdigit;
u_int val;
int digits;
int bits;
size_t bytes;
int words;
int ipv4;
memset((tp = tmp), '\0', NS_IN6ADDRSZ);
endp = tp + NS_IN6ADDRSZ;
colonp = NULL;
/* Leading :: requires some special handling. */
if (*src == ':')
if (*++src != ':')
goto enoent;
curtok = src;
saw_xdigit = 0;
val = 0;
digits = 0;
bits = -1;
ipv4 = 0;
while ((ch = *src++) != '\0') {
const char *pch;
if ((pch = strchr((xdigits = xdigits_l), ch)) == NULL)
pch = strchr((xdigits = xdigits_u), ch);
if (pch != NULL) {
val <<= 4;
val |= (pch - xdigits);
if (++digits > 4)
goto enoent;
saw_xdigit = 1;
continue;
}
if (ch == ':') {
curtok = src;
if (!saw_xdigit) {
if (colonp)
goto enoent;
colonp = tp;
continue;
} else if (*src == '\0')
goto enoent;
if (tp + NS_INT16SZ > endp)
return (0);
*tp++ = (u_char) (val >> 8) & 0xff;
*tp++ = (u_char) val & 0xff;
saw_xdigit = 0;
digits = 0;
val = 0;
continue;
}
if (ch == '.' && ((tp + NS_INADDRSZ) <= endp) &&
getv4(curtok, tp, &bits) > 0) {
tp += NS_INADDRSZ;
saw_xdigit = 0;
ipv4 = 1;
break; /*%< '\\0' was seen by inet_pton4(). */
}
if (ch == '/' && getbits(src, &bits) > 0)
break;
goto enoent;
}
if (saw_xdigit) {
if (tp + NS_INT16SZ > endp)
goto enoent;
*tp++ = (u_char) (val >> 8) & 0xff;
*tp++ = (u_char) val & 0xff;
}
if (bits == -1)
bits = 128;
words = (bits + 15) / 16;
if (words < 2)
words = 2;
if (ipv4)
words = 8;
endp = tmp + 2 * words;
if (colonp != NULL) {
/*
* Since some memmove()'s erroneously fail to handle
* overlapping regions, we'll do the shift by hand.
*/
const int n = tp - colonp;
int i;
if (tp == endp)
goto enoent;
for (i = 1; i <= n; i++) {
endp[- i] = colonp[n - i];
colonp[n - i] = 0;
}
tp = endp;
}
if (tp != endp)
goto enoent;
bytes = (bits + 7) / 8;
if (bytes > size)
goto emsgsize;
memcpy(dst, tmp, bytes);
return (bits);
enoent:
errno = ENOENT;
return (-1);
emsgsize:
errno = EMSGSIZE;
return (-1);
}
/*%
* int
* inet_net_pton(af, src, dst, size)
* convert network number from presentation to network format.
* accepts hex octets, hex strings, decimal octets, and /CIDR.
* "size" is in bytes and describes "dst".
* return:
* number of bits, either imputed classfully or specified with /CIDR,
* or -1 if some failure occurred (check errno). ENOENT means it was
* not a valid network specification.
* author:
* Paul Vixie (ISC), June 1996
*/
int
inet_net_pton(int af, const char *src, void *dst, size_t size) {
switch (af) {
case AF_INET:
return (inet_net_pton_ipv4(src, dst, size));
case AF_INET6:
return (inet_net_pton_ipv6(src, dst, size));
default:
errno = EAFNOSUPPORT;
return (-1);
}
}
/*
* Weak aliases for applications that use certain private entry points,
* and fail to include .
*/
#undef inet_net_pton
__weak_reference(__inet_net_pton, inet_net_pton);
/*! \file */
Index: projects/arpv2_merge_1/lib/libc/net/rcmd.3
===================================================================
--- projects/arpv2_merge_1/lib/libc/net/rcmd.3 (revision 186114)
+++ projects/arpv2_merge_1/lib/libc/net/rcmd.3 (revision 186115)
@@ -1,298 +1,305 @@
.\" Copyright (c) 1983, 1991, 1993
.\" The Regents of the University of California. All rights reserved.
.\"
.\" Redistribution and use in source and binary forms, with or without
.\" modification, are permitted provided that the following conditions
.\" are met:
.\" 1. Redistributions of source code must retain the above copyright
.\" notice, this list of conditions and the following disclaimer.
.\" 2. Redistributions in binary form must reproduce the above copyright
.\" notice, this list of conditions and the following disclaimer in the
.\" documentation and/or other materials provided with the distribution.
.\" 4. Neither the name of the University nor the names of its contributors
.\" may be used to endorse or promote products derived from this software
.\" without specific prior written permission.
.\"
.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
.\" ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
.\" From: @(#)rcmd.3 8.1 (Berkeley) 6/4/93
.\" $FreeBSD$
.\"
.Dd March 3, 2000
.Dt RCMD 3
.Os
.Sh NAME
.Nm rcmd ,
.Nm rresvport ,
.Nm iruserok ,
.Nm ruserok ,
.Nm rcmd_af ,
.Nm rresvport_af ,
.Nm iruserok_sa
.Nd routines for returning a stream to a remote command
.Sh LIBRARY
.Lb libc
.Sh SYNOPSIS
.In unistd.h
.Ft int
.Fn rcmd "char **ahost" "int inport" "const char *locuser" "const char *remuser" "const char *cmd" "int *fd2p"
.Ft int
.Fn rresvport "int *port"
.Ft int
.Fn iruserok "u_long raddr" "int superuser" "const char *ruser" "const char *luser"
.Ft int
.Fn ruserok "const char *rhost" "int superuser" "const char *ruser" "const char *luser"
.Ft int
.Fn rcmd_af "char **ahost" "int inport" "const char *locuser" "const char *remuser" "const char *cmd" "int *fd2p" "int af"
.Ft int
.Fn rresvport_af "int *port" "int af"
.Ft int
.Fn iruserok_sa "const void *addr" "int addrlen" "int superuser" "const char *ruser" "const char *luser"
.Sh DESCRIPTION
The
.Fn rcmd
function
is used by the super-user to execute a command on
a remote machine using an authentication scheme based
on reserved port numbers.
The
.Fn rresvport
function
returns a descriptor to a socket
with an address in the privileged port space.
The
.Fn ruserok
function
is used by servers
to authenticate clients requesting service with
.Fn rcmd .
All three functions are present in the same file and are used
by the
.Xr rshd 8
server (among others).
.Pp
The
.Fn rcmd
function
looks up the host
.Fa *ahost
using
.Xr gethostbyname 3 ,
returning -1 if the host does not exist.
Otherwise
.Fa *ahost
is set to the standard name of the host
and a connection is established to a server
residing at the well-known Internet port
.Fa inport .
.Pp
If the connection succeeds,
a socket in the Internet domain of type
.Dv SOCK_STREAM
is returned to the caller, and given to the remote
command as
.Dv stdin
and
.Dv stdout .
If
.Fa fd2p
is non-zero, then an auxiliary channel to a control
process will be set up, and a descriptor for it will be placed
in
.Fa *fd2p .
The control process will return diagnostic
output from the command (unit 2) on this channel, and will also
accept bytes on this channel as being
.Ux
signal numbers, to be
forwarded to the process group of the command.
If
.Fa fd2p
is 0, then the
.Dv stderr
(unit 2 of the remote
command) will be made the same as the
.Dv stdout
and no
provision is made for sending arbitrary signals to the remote process,
although you may be able to get its attention by using out-of-band data.
.Pp
The protocol is described in detail in
.Xr rshd 8 .
.Pp
The
.Fn rresvport
function is used to obtain a socket to which an address with a Privileged
Internet port is bound.
This socket is suitable for use by
.Fn rcmd
and several other functions.
Privileged Internet ports are those in the range 0 to 1023.
Only the super-user is allowed to bind an address of this sort
to a socket.
.Pp
The
.Fn iruserok
and
.Fn ruserok
functions take a remote host's IP address or name, as returned by the
.Xr gethostbyname 3
routines, two user names and a flag indicating whether the local user's
name is that of the super-user.
Then, if the user is
.Em NOT
the super-user, it checks the
.Pa /etc/hosts.equiv
file.
If that lookup is not done, or is unsuccessful, the
.Pa .rhosts
in the local user's home directory is checked to see if the request for
service is allowed.
.Pp
If this file does not exist, is not a regular file, is owned by anyone
other than the user or the super-user, or is writable by anyone other
than the owner, the check automatically fails.
Zero is returned if the machine name is listed in the
.Dq Pa hosts.equiv
file, or the host and remote user name are found in the
.Dq Pa .rhosts
file; otherwise
.Fn iruserok
and
.Fn ruserok
return -1.
If the local domain (as obtained from
.Xr gethostname 3 )
is the same as the remote domain, only the machine name need be specified.
.Pp
The
.Fn iruserok
function is strongly preferred for security reasons.
It requires trusting the local DNS at most, while the
.Fn ruserok
function requires trusting the entire DNS, which can be spoofed.
.Pp
The functions with an
.Dq Li _af
or
.Dq Li _sa
suffix, i.e.,
.Fn rcmd_af ,
.Fn rresvport_af
and
.Fn iruserok_sa ,
work the same as the corresponding functions without a
suffix, except that they are capable of handling both IPv6 and IPv4 ports.
.Pp
The
.Dq Li _af
suffix means that the function has an additional
.Fa af
argument which is used to specify the address family,
(see below).
The
.Fa af
argument extension is implemented for functions
that have no binary address argument.
Instead, the
.Fa af
argument specifies which address family is desired.
.Pp
The
.Dq Li _sa
suffix means that the function has general socket address and
length arguments.
As the socket address is a protocol independent data structure,
IPv4 and IPv6 socket address can be passed as desired.
The
.Fa sa
argument extension is implemented for functions
that pass a protocol dependent binary address argument.
The argument needs to be replaced with a more general address structure
to support multiple address families in a general way.
.Pp
The functions with neither an
.Dq Li _af
suffix nor an
.Dq Li _sa
suffix work for IPv4 only, except for
.Fn ruserok
which can handle both IPv6 and IPv4.
To switch the address family, the
.Fa af
argument must be filled with
.Dv AF_INET ,
or
.Dv AF_INET6 .
For
.Fn rcmd_af ,
.Dv PF_UNSPEC
is also allowed.
+.Sh ENVIRONMENT
+.Bl -tag -width RSH
+.It Ev RSH
+When using the
+.Fn rcmd
+function, this variable is used as the program to run instead of
+.Xr rsh 1 .
.Sh DIAGNOSTICS
The
.Fn rcmd
function
returns a valid socket descriptor on success.
It returns -1 on error and prints a diagnostic message
on the standard error.
.Pp
The
.Fn rresvport
function
returns a valid, bound socket descriptor on success.
It returns -1 on error with the global value
.Va errno
set according to the reason for failure.
The error code
.Er EAGAIN
is overloaded to mean ``All network ports in use.''
.Sh SEE ALSO
.Xr rlogin 1 ,
.Xr rsh 1 ,
.Xr intro 2 ,
.Xr rlogind 8 ,
.Xr rshd 8
.Pp
.Rs
.%A W. Stevens
.%A M. Thomas
.%T "Advanced Socket API for IPv6"
.%O RFC2292
.Re
.Rs
.%A W. Stevens
.%A M. Thomas
.%A E. Nordmark
.%T "Advanced Socket API for IPv6"
.%O RFC3542
.Re
.Sh HISTORY
Most of these
functions appeared in
.Bx 4.2 .
The
.Fn rresvport_af
function
appeared in RFC2292, and was implemented by the WIDE project
for the Hydrangea IPv6 protocol stack kit.
The
.Fn rcmd_af
function
appeared in draft-ietf-ipngwg-rfc2292bis-01.txt,
and was implemented in the WIDE/KAME IPv6 protocol stack kit.
The
.Fn iruserok_sa
function
appeared in discussion on the IETF ipngwg mailing list,
and was implemented in
.Fx 4.0 .
Index: projects/arpv2_merge_1/lib/libc/resolv/res_debug.c
===================================================================
--- projects/arpv2_merge_1/lib/libc/resolv/res_debug.c (revision 186114)
+++ projects/arpv2_merge_1/lib/libc/resolv/res_debug.c (revision 186115)
@@ -1,1182 +1,1229 @@
/*
* Copyright (c) 1985
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Portions Copyright (c) 1993 by Digital Equipment Corporation.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies, and that
* the name of Digital Equipment Corporation not be used in advertising or
* publicity pertaining to distribution of the document or software without
* specific, written prior permission.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND DIGITAL EQUIPMENT CORP. DISCLAIMS ALL
* WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL DIGITAL EQUIPMENT
* CORPORATION BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
* DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
* PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
* ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
* SOFTWARE.
*/
/*
* Portions Copyright (c) 1995 by International Business Machines, Inc.
*
* International Business Machines, Inc. (hereinafter called IBM) grants
* permission under its copyrights to use, copy, modify, and distribute this
* Software with or without fee, provided that the above copyright notice and
* all paragraphs of this notice appear in all copies, and that the name of IBM
* not be used in connection with the marketing of any product incorporating
* the Software or modifications thereof, without specific, written prior
* permission.
*
* To the extent it has a right to do so, IBM grants an immunity from suit
* under its patents, if any, for the use, sale or manufacture of products to
* the extent that such products are used for performing Domain Name System
* dynamic updates in TCP/IP networks by means of the Software. No immunity is
* granted for any product per se or for any other function of any product.
*
* THE SOFTWARE IS PROVIDED "AS IS", AND IBM DISCLAIMS ALL WARRANTIES,
* INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
* PARTICULAR PURPOSE. IN NO EVENT SHALL IBM BE LIABLE FOR ANY SPECIAL,
* DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER ARISING
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE, EVEN
* IF IBM IS APPRISED OF THE POSSIBILITY OF SUCH DAMAGES.
*/
/*
* Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
* Portions Copyright (c) 1996-1999 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#if defined(LIBC_SCCS) && !defined(lint)
static const char sccsid[] = "@(#)res_debug.c 8.1 (Berkeley) 6/4/93";
-static const char rcsid[] = "$Id: res_debug.c,v 1.10.18.5 2005/07/28 07:38:11 marka Exp $";
+static const char rcsid[] = "$Id: res_debug.c,v 1.10.18.6 2008/04/03 23:15:15 marka Exp $";
#endif /* LIBC_SCCS and not lint */
#include
__FBSDID("$FreeBSD$");
#include "port_before.h"
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include "port_after.h"
#ifdef SPRINTF_CHAR
# define SPRINTF(x) strlen(sprintf/**/x)
#else
# define SPRINTF(x) sprintf x
#endif
extern const char *_res_opcodes[];
extern const char *_res_sectioncodes[];
/*%
* Print the current options.
*/
void
fp_resstat(const res_state statp, FILE *file) {
u_long mask;
fprintf(file, ";; res options:");
for (mask = 1; mask != 0U; mask <<= 1)
if (statp->options & mask)
fprintf(file, " %s", p_option(mask));
putc('\n', file);
}
static void
do_section(const res_state statp,
ns_msg *handle, ns_sect section,
int pflag, FILE *file)
{
int n, sflag, rrnum;
static int buflen = 2048;
char *buf;
ns_opcode opcode;
ns_rr rr;
/*
* Print answer records.
*/
sflag = (statp->pfcode & pflag);
if (statp->pfcode && !sflag)
return;
buf = malloc(buflen);
if (buf == NULL) {
fprintf(file, ";; memory allocation failure\n");
return;
}
opcode = (ns_opcode) ns_msg_getflag(*handle, ns_f_opcode);
rrnum = 0;
for (;;) {
if (ns_parserr(handle, section, rrnum, &rr)) {
if (errno != ENODEV)
fprintf(file, ";; ns_parserr: %s\n",
strerror(errno));
else if (rrnum > 0 && sflag != 0 &&
(statp->pfcode & RES_PRF_HEAD1))
putc('\n', file);
goto cleanup;
}
if (rrnum == 0 && sflag != 0 && (statp->pfcode & RES_PRF_HEAD1))
fprintf(file, ";; %s SECTION:\n",
p_section(section, opcode));
if (section == ns_s_qd)
fprintf(file, ";;\t%s, type = %s, class = %s\n",
ns_rr_name(rr),
p_type(ns_rr_type(rr)),
p_class(ns_rr_class(rr)));
else if (section == ns_s_ar && ns_rr_type(rr) == ns_t_opt) {
+ u_int16_t optcode, optlen, rdatalen = ns_rr_rdlen(rr);
u_int32_t ttl = ns_rr_ttl(rr);
+
fprintf(file,
"; EDNS: version: %u, udp=%u, flags=%04x\n",
(ttl>>16)&0xff, ns_rr_class(rr), ttl&0xffff);
+
+ while (rdatalen >= 4) {
+ const u_char *cp = ns_rr_rdata(rr);
+ int i;
+
+ GETSHORT(optcode, cp);
+ GETSHORT(optlen, cp);
+
+ if (optcode == NS_OPT_NSID) {
+ fputs("; NSID: ", file);
+ if (optlen == 0) {
+ fputs("; NSID\n", file);
+ } else {
+ fputs("; NSID: ", file);
+ for (i = 0; i < optlen; i++)
+ fprintf(file, "%02x ",
+ cp[i]);
+ fputs(" (",file);
+ for (i = 0; i < optlen; i++)
+ fprintf(file, "%c",
+ isprint(cp[i])?
+ cp[i] : '.');
+ fputs(")\n", file);
+ }
+ } else {
+ if (optlen == 0) {
+ fprintf(file, "; OPT=%u\n",
+ optcode);
+ } else {
+ fprintf(file, "; OPT=%u: ",
+ optcode);
+ for (i = 0; i < optlen; i++)
+ fprintf(file, "%02x ",
+ cp[i]);
+ fputs(" (",file);
+ for (i = 0; i < optlen; i++)
+ fprintf(file, "%c",
+ isprint(cp[i]) ?
+ cp[i] : '.');
+ fputs(")\n", file);
+ }
+ }
+ rdatalen -= 4 + optlen;
+ }
} else {
n = ns_sprintrr(handle, &rr, NULL, NULL,
buf, buflen);
if (n < 0) {
if (errno == ENOSPC) {
free(buf);
buf = NULL;
if (buflen < 131072)
buf = malloc(buflen += 1024);
if (buf == NULL) {
fprintf(file,
- ";; memory allocation failure\n");
+ ";; memory allocation failure\n");
return;
}
continue;
}
fprintf(file, ";; ns_sprintrr: %s\n",
strerror(errno));
goto cleanup;
}
fputs(buf, file);
fputc('\n', file);
}
rrnum++;
}
cleanup:
if (buf != NULL)
free(buf);
}
/*%
* Print the contents of a query.
* This is intended to be primarily a debugging routine.
*/
void
res_pquery(const res_state statp, const u_char *msg, int len, FILE *file) {
ns_msg handle;
int qdcount, ancount, nscount, arcount;
u_int opcode, rcode, id;
if (ns_initparse(msg, len, &handle) < 0) {
fprintf(file, ";; ns_initparse: %s\n", strerror(errno));
return;
}
opcode = ns_msg_getflag(handle, ns_f_opcode);
rcode = ns_msg_getflag(handle, ns_f_rcode);
id = ns_msg_id(handle);
qdcount = ns_msg_count(handle, ns_s_qd);
ancount = ns_msg_count(handle, ns_s_an);
nscount = ns_msg_count(handle, ns_s_ns);
arcount = ns_msg_count(handle, ns_s_ar);
/*
* Print header fields.
*/
if ((!statp->pfcode) || (statp->pfcode & RES_PRF_HEADX) || rcode)
fprintf(file,
";; ->>HEADER<<- opcode: %s, status: %s, id: %d\n",
_res_opcodes[opcode], p_rcode(rcode), id);
if ((!statp->pfcode) || (statp->pfcode & RES_PRF_HEADX))
putc(';', file);
if ((!statp->pfcode) || (statp->pfcode & RES_PRF_HEAD2)) {
fprintf(file, "; flags:");
if (ns_msg_getflag(handle, ns_f_qr))
fprintf(file, " qr");
if (ns_msg_getflag(handle, ns_f_aa))
fprintf(file, " aa");
if (ns_msg_getflag(handle, ns_f_tc))
fprintf(file, " tc");
if (ns_msg_getflag(handle, ns_f_rd))
fprintf(file, " rd");
if (ns_msg_getflag(handle, ns_f_ra))
fprintf(file, " ra");
if (ns_msg_getflag(handle, ns_f_z))
fprintf(file, " ??");
if (ns_msg_getflag(handle, ns_f_ad))
fprintf(file, " ad");
if (ns_msg_getflag(handle, ns_f_cd))
fprintf(file, " cd");
}
if ((!statp->pfcode) || (statp->pfcode & RES_PRF_HEAD1)) {
fprintf(file, "; %s: %d",
p_section(ns_s_qd, opcode), qdcount);
fprintf(file, ", %s: %d",
p_section(ns_s_an, opcode), ancount);
fprintf(file, ", %s: %d",
p_section(ns_s_ns, opcode), nscount);
fprintf(file, ", %s: %d",
p_section(ns_s_ar, opcode), arcount);
}
if ((!statp->pfcode) || (statp->pfcode &
(RES_PRF_HEADX | RES_PRF_HEAD2 | RES_PRF_HEAD1))) {
putc('\n',file);
}
/*
* Print the various sections.
*/
do_section(statp, &handle, ns_s_qd, RES_PRF_QUES, file);
do_section(statp, &handle, ns_s_an, RES_PRF_ANS, file);
do_section(statp, &handle, ns_s_ns, RES_PRF_AUTH, file);
do_section(statp, &handle, ns_s_ar, RES_PRF_ADD, file);
if (qdcount == 0 && ancount == 0 &&
nscount == 0 && arcount == 0)
putc('\n', file);
}
const u_char *
p_cdnname(const u_char *cp, const u_char *msg, int len, FILE *file) {
char name[MAXDNAME];
int n;
if ((n = dn_expand(msg, msg + len, cp, name, sizeof name)) < 0)
return (NULL);
if (name[0] == '\0')
putc('.', file);
else
fputs(name, file);
return (cp + n);
}
const u_char *
p_cdname(const u_char *cp, const u_char *msg, FILE *file) {
return (p_cdnname(cp, msg, PACKETSZ, file));
}
/*%
* Return a fully-qualified domain name from a compressed name (with
length supplied). */
const u_char *
p_fqnname(cp, msg, msglen, name, namelen)
const u_char *cp, *msg;
int msglen;
char *name;
int namelen;
{
int n, newlen;
if ((n = dn_expand(msg, cp + msglen, cp, name, namelen)) < 0)
return (NULL);
newlen = strlen(name);
if (newlen == 0 || name[newlen - 1] != '.') {
if (newlen + 1 >= namelen) /*%< Lack space for final dot */
return (NULL);
else
strcpy(name + newlen, ".");
}
return (cp + n);
}
/* XXX: the rest of these functions need to become length-limited, too. */
const u_char *
p_fqname(const u_char *cp, const u_char *msg, FILE *file) {
char name[MAXDNAME];
const u_char *n;
n = p_fqnname(cp, msg, MAXCDNAME, name, sizeof name);
if (n == NULL)
return (NULL);
fputs(name, file);
return (n);
}
/*%
* Names of RR classes and qclasses. Classes and qclasses are the same, except
* that C_ANY is a qclass but not a class. (You can ask for records of class
* C_ANY, but you can't have any records of that class in the database.)
*/
const struct res_sym __p_class_syms[] = {
{C_IN, "IN", (char *)0},
{C_CHAOS, "CH", (char *)0},
{C_CHAOS, "CHAOS", (char *)0},
{C_HS, "HS", (char *)0},
{C_HS, "HESIOD", (char *)0},
{C_ANY, "ANY", (char *)0},
{C_NONE, "NONE", (char *)0},
{C_IN, (char *)0, (char *)0}
};
/*%
* Names of message sections.
*/
static const struct res_sym __p_default_section_syms[] = {
{ns_s_qd, "QUERY", (char *)0},
{ns_s_an, "ANSWER", (char *)0},
{ns_s_ns, "AUTHORITY", (char *)0},
{ns_s_ar, "ADDITIONAL", (char *)0},
- {0, (char *)0, (char *)0}
+ {0, (char *)0, (char *)0}
};
static const struct res_sym __p_update_section_syms[] = {
{S_ZONE, "ZONE", (char *)0},
{S_PREREQ, "PREREQUISITE", (char *)0},
{S_UPDATE, "UPDATE", (char *)0},
{S_ADDT, "ADDITIONAL", (char *)0},
- {0, (char *)0, (char *)0}
+ {0, (char *)0, (char *)0}
};
const struct res_sym __p_key_syms[] = {
{NS_ALG_MD5RSA, "RSA", "RSA KEY with MD5 hash"},
{NS_ALG_DH, "DH", "Diffie Hellman"},
{NS_ALG_DSA, "DSA", "Digital Signature Algorithm"},
{NS_ALG_EXPIRE_ONLY, "EXPIREONLY", "No algorithm"},
{NS_ALG_PRIVATE_OID, "PRIVATE", "Algorithm obtained from OID"},
{0, NULL, NULL}
};
const struct res_sym __p_cert_syms[] = {
{cert_t_pkix, "PKIX", "PKIX (X.509v3) Certificate"},
{cert_t_spki, "SPKI", "SPKI certificate"},
{cert_t_pgp, "PGP", "PGP certificate"},
{cert_t_url, "URL", "URL Private"},
{cert_t_oid, "OID", "OID Private"},
{0, NULL, NULL}
};
/*%
* Names of RR types and qtypes. Types and qtypes are the same, except
* that T_ANY is a qtype but not a type. (You can ask for records of type
* T_ANY, but you can't have any records of that type in the database.)
*/
const struct res_sym __p_type_syms[] = {
{ns_t_a, "A", "address"},
{ns_t_ns, "NS", "name server"},
{ns_t_md, "MD", "mail destination (deprecated)"},
{ns_t_mf, "MF", "mail forwarder (deprecated)"},
{ns_t_cname, "CNAME", "canonical name"},
{ns_t_soa, "SOA", "start of authority"},
{ns_t_mb, "MB", "mailbox"},
{ns_t_mg, "MG", "mail group member"},
{ns_t_mr, "MR", "mail rename"},
{ns_t_null, "NULL", "null"},
{ns_t_wks, "WKS", "well-known service (deprecated)"},
{ns_t_ptr, "PTR", "domain name pointer"},
{ns_t_hinfo, "HINFO", "host information"},
{ns_t_minfo, "MINFO", "mailbox information"},
{ns_t_mx, "MX", "mail exchanger"},
{ns_t_txt, "TXT", "text"},
{ns_t_rp, "RP", "responsible person"},
{ns_t_afsdb, "AFSDB", "DCE or AFS server"},
{ns_t_x25, "X25", "X25 address"},
{ns_t_isdn, "ISDN", "ISDN address"},
{ns_t_rt, "RT", "router"},
{ns_t_nsap, "NSAP", "nsap address"},
{ns_t_nsap_ptr, "NSAP_PTR", "domain name pointer"},
{ns_t_sig, "SIG", "signature"},
{ns_t_key, "KEY", "key"},
{ns_t_px, "PX", "mapping information"},
{ns_t_gpos, "GPOS", "geographical position (withdrawn)"},
{ns_t_aaaa, "AAAA", "IPv6 address"},
{ns_t_loc, "LOC", "location"},
{ns_t_nxt, "NXT", "next valid name (unimplemented)"},
{ns_t_eid, "EID", "endpoint identifier (unimplemented)"},
{ns_t_nimloc, "NIMLOC", "NIMROD locator (unimplemented)"},
{ns_t_srv, "SRV", "server selection"},
{ns_t_atma, "ATMA", "ATM address (unimplemented)"},
{ns_t_tkey, "TKEY", "tkey"},
{ns_t_tsig, "TSIG", "transaction signature"},
{ns_t_ixfr, "IXFR", "incremental zone transfer"},
{ns_t_axfr, "AXFR", "zone transfer"},
{ns_t_zxfr, "ZXFR", "compressed zone transfer"},
{ns_t_mailb, "MAILB", "mailbox-related data (deprecated)"},
{ns_t_maila, "MAILA", "mail agent (deprecated)"},
{ns_t_naptr, "NAPTR", "URN Naming Authority"},
{ns_t_kx, "KX", "Key Exchange"},
{ns_t_cert, "CERT", "Certificate"},
{ns_t_a6, "A6", "IPv6 Address"},
{ns_t_dname, "DNAME", "dname"},
{ns_t_sink, "SINK", "Kitchen Sink (experimental)"},
{ns_t_opt, "OPT", "EDNS Options"},
{ns_t_any, "ANY", "\"any\""},
{0, NULL, NULL}
};
/*%
* Names of DNS rcodes.
*/
const struct res_sym __p_rcode_syms[] = {
{ns_r_noerror, "NOERROR", "no error"},
{ns_r_formerr, "FORMERR", "format error"},
{ns_r_servfail, "SERVFAIL", "server failed"},
{ns_r_nxdomain, "NXDOMAIN", "no such domain name"},
{ns_r_notimpl, "NOTIMP", "not implemented"},
{ns_r_refused, "REFUSED", "refused"},
{ns_r_yxdomain, "YXDOMAIN", "domain name exists"},
{ns_r_yxrrset, "YXRRSET", "rrset exists"},
{ns_r_nxrrset, "NXRRSET", "rrset doesn't exist"},
{ns_r_notauth, "NOTAUTH", "not authoritative"},
{ns_r_notzone, "NOTZONE", "Not in zone"},
{ns_r_max, "", ""},
{ns_r_badsig, "BADSIG", "bad signature"},
{ns_r_badkey, "BADKEY", "bad key"},
{ns_r_badtime, "BADTIME", "bad time"},
{0, NULL, NULL}
};
int
sym_ston(const struct res_sym *syms, const char *name, int *success) {
for ((void)NULL; syms->name != 0; syms++) {
if (strcasecmp (name, syms->name) == 0) {
if (success)
*success = 1;
return (syms->number);
}
}
if (success)
*success = 0;
return (syms->number); /*%< The default value. */
}
const char *
sym_ntos(const struct res_sym *syms, int number, int *success) {
char *unname = sym_ntos_unname;
for ((void)NULL; syms->name != 0; syms++) {
if (number == syms->number) {
if (success)
*success = 1;
return (syms->name);
}
}
sprintf(unname, "%d", number); /*%< XXX nonreentrant */
if (success)
*success = 0;
return (unname);
}
const char *
sym_ntop(const struct res_sym *syms, int number, int *success) {
char *unname = sym_ntop_unname;
for ((void)NULL; syms->name != 0; syms++) {
if (number == syms->number) {
if (success)
*success = 1;
return (syms->humanname);
}
}
sprintf(unname, "%d", number); /*%< XXX nonreentrant */
if (success)
*success = 0;
return (unname);
}
/*%
* Return a string for the type.
*/
const char *
p_type(int type) {
int success;
const char *result;
static char typebuf[20];
result = sym_ntos(__p_type_syms, type, &success);
if (success)
return (result);
if (type < 0 || type > 0xffff)
return ("BADTYPE");
sprintf(typebuf, "TYPE%d", type);
return (typebuf);
}
/*%
* Return a string for the type.
*/
const char *
p_section(int section, int opcode) {
const struct res_sym *symbols;
switch (opcode) {
case ns_o_update:
symbols = __p_update_section_syms;
break;
default:
symbols = __p_default_section_syms;
break;
}
return (sym_ntos(symbols, section, (int *)0));
}
/*%
* Return a mnemonic for class.
*/
const char *
p_class(int class) {
int success;
const char *result;
static char classbuf[20];
result = sym_ntos(__p_class_syms, class, &success);
if (success)
return (result);
if (class < 0 || class > 0xffff)
return ("BADCLASS");
sprintf(classbuf, "CLASS%d", class);
return (classbuf);
}
/*%
* Return a mnemonic for an option
*/
const char *
p_option(u_long option) {
char *nbuf = p_option_nbuf;
switch (option) {
case RES_INIT: return "init";
case RES_DEBUG: return "debug";
case RES_AAONLY: return "aaonly(unimpl)";
case RES_USEVC: return "usevc";
case RES_PRIMARY: return "primry(unimpl)";
case RES_IGNTC: return "igntc";
case RES_RECURSE: return "recurs";
case RES_DEFNAMES: return "defnam";
case RES_STAYOPEN: return "styopn";
case RES_DNSRCH: return "dnsrch";
case RES_INSECURE1: return "insecure1";
case RES_INSECURE2: return "insecure2";
case RES_NOALIASES: return "noaliases";
case RES_USE_INET6: return "inet6";
#ifdef RES_USE_EDNS0 /*%< KAME extension */
case RES_USE_EDNS0: return "edns0";
+ case RES_NSID: return "nsid";
#endif
#ifdef RES_USE_DNAME
case RES_USE_DNAME: return "dname";
#endif
#ifdef RES_USE_DNSSEC
case RES_USE_DNSSEC: return "dnssec";
#endif
#ifdef RES_NOTLDQUERY
case RES_NOTLDQUERY: return "no-tld-query";
#endif
#ifdef RES_NO_NIBBLE2
case RES_NO_NIBBLE2: return "no-nibble2";
#endif
/* XXX nonreentrant */
default: sprintf(nbuf, "?0x%lx?", (u_long)option);
return (nbuf);
}
}
/*%
* Return a mnemonic for a time to live.
*/
const char *
p_time(u_int32_t value) {
char *nbuf = p_time_nbuf;
if (ns_format_ttl(value, nbuf, sizeof nbuf) < 0)
sprintf(nbuf, "%u", value);
return (nbuf);
}
/*%
* Return a string for the rcode.
*/
const char *
p_rcode(int rcode) {
return (sym_ntos(__p_rcode_syms, rcode, (int *)0));
}
/*%
* Return a string for a res_sockaddr_union.
*/
const char *
p_sockun(union res_sockaddr_union u, char *buf, size_t size) {
char ret[sizeof "ffff:ffff:ffff:ffff:ffff:ffff:123.123.123.123"];
switch (u.sin.sin_family) {
case AF_INET:
inet_ntop(AF_INET, &u.sin.sin_addr, ret, sizeof ret);
break;
#ifdef HAS_INET6_STRUCTS
case AF_INET6:
inet_ntop(AF_INET6, &u.sin6.sin6_addr, ret, sizeof ret);
break;
#endif
default:
sprintf(ret, "[af%d]", u.sin.sin_family);
break;
}
if (size > 0U) {
strncpy(buf, ret, size - 1);
buf[size - 1] = '0';
}
return (buf);
}
/*%
* routines to convert between on-the-wire RR format and zone file format.
* Does not contain conversion to/from decimal degrees; divide or multiply
* by 60*60*1000 for that.
*/
static unsigned int poweroften[10] = {1, 10, 100, 1000, 10000, 100000,
1000000,10000000,100000000,1000000000};
/*% takes an XeY precision/size value, returns a string representation. */
static const char *
precsize_ntoa(prec)
u_int8_t prec;
{
char *retbuf = precsize_ntoa_retbuf;
unsigned long val;
int mantissa, exponent;
mantissa = (int)((prec >> 4) & 0x0f) % 10;
exponent = (int)((prec >> 0) & 0x0f) % 10;
val = mantissa * poweroften[exponent];
(void) sprintf(retbuf, "%lu.%.2lu", val/100, val%100);
return (retbuf);
}
/*% converts ascii size/precision X * 10**Y(cm) to 0xXY. moves pointer. */
static u_int8_t
precsize_aton(const char **strptr) {
unsigned int mval = 0, cmval = 0;
u_int8_t retval = 0;
const char *cp;
int exponent;
int mantissa;
cp = *strptr;
while (isdigit((unsigned char)*cp))
mval = mval * 10 + (*cp++ - '0');
if (*cp == '.') { /*%< centimeters */
cp++;
if (isdigit((unsigned char)*cp)) {
cmval = (*cp++ - '0') * 10;
if (isdigit((unsigned char)*cp)) {
cmval += (*cp++ - '0');
}
}
}
cmval = (mval * 100) + cmval;
for (exponent = 0; exponent < 9; exponent++)
if (cmval < poweroften[exponent+1])
break;
mantissa = cmval / poweroften[exponent];
if (mantissa > 9)
mantissa = 9;
retval = (mantissa << 4) | exponent;
*strptr = cp;
return (retval);
}
/*% converts ascii lat/lon to unsigned encoded 32-bit number. moves pointer. */
static u_int32_t
latlon2ul(const char **latlonstrptr, int *which) {
const char *cp;
u_int32_t retval;
int deg = 0, min = 0, secs = 0, secsfrac = 0;
cp = *latlonstrptr;
while (isdigit((unsigned char)*cp))
deg = deg * 10 + (*cp++ - '0');
while (isspace((unsigned char)*cp))
cp++;
if (!(isdigit((unsigned char)*cp)))
goto fndhemi;
while (isdigit((unsigned char)*cp))
min = min * 10 + (*cp++ - '0');
while (isspace((unsigned char)*cp))
cp++;
if (!(isdigit((unsigned char)*cp)))
goto fndhemi;
while (isdigit((unsigned char)*cp))
secs = secs * 10 + (*cp++ - '0');
if (*cp == '.') { /*%< decimal seconds */
cp++;
if (isdigit((unsigned char)*cp)) {
secsfrac = (*cp++ - '0') * 100;
if (isdigit((unsigned char)*cp)) {
secsfrac += (*cp++ - '0') * 10;
if (isdigit((unsigned char)*cp)) {
secsfrac += (*cp++ - '0');
}
}
}
}
while (!isspace((unsigned char)*cp)) /*%< if any trailing garbage */
cp++;
while (isspace((unsigned char)*cp))
cp++;
fndhemi:
switch (*cp) {
case 'N': case 'n':
case 'E': case 'e':
retval = ((unsigned)1<<31)
+ (((((deg * 60) + min) * 60) + secs) * 1000)
+ secsfrac;
break;
case 'S': case 's':
case 'W': case 'w':
retval = ((unsigned)1<<31)
- (((((deg * 60) + min) * 60) + secs) * 1000)
- secsfrac;
break;
default:
retval = 0; /*%< invalid value -- indicates error */
break;
}
switch (*cp) {
case 'N': case 'n':
case 'S': case 's':
*which = 1; /*%< latitude */
break;
case 'E': case 'e':
case 'W': case 'w':
*which = 2; /*%< longitude */
break;
default:
*which = 0; /*%< error */
break;
}
cp++; /*%< skip the hemisphere */
while (!isspace((unsigned char)*cp)) /*%< if any trailing garbage */
cp++;
while (isspace((unsigned char)*cp)) /*%< move to next field */
cp++;
*latlonstrptr = cp;
return (retval);
}
/*%
* converts a zone file representation in a string to an RDATA on-the-wire
* representation. */
int
loc_aton(ascii, binary)
const char *ascii;
u_char *binary;
{
const char *cp, *maxcp;
u_char *bcp;
u_int32_t latit = 0, longit = 0, alt = 0;
u_int32_t lltemp1 = 0, lltemp2 = 0;
int altmeters = 0, altfrac = 0, altsign = 1;
u_int8_t hp = 0x16; /*%< default = 1e6 cm = 10000.00m = 10km */
u_int8_t vp = 0x13; /*%< default = 1e3 cm = 10.00m */
u_int8_t siz = 0x12; /*%< default = 1e2 cm = 1.00m */
int which1 = 0, which2 = 0;
cp = ascii;
maxcp = cp + strlen(ascii);
lltemp1 = latlon2ul(&cp, &which1);
lltemp2 = latlon2ul(&cp, &which2);
switch (which1 + which2) {
case 3: /*%< 1 + 2, the only valid combination */
if ((which1 == 1) && (which2 == 2)) { /*%< normal case */
latit = lltemp1;
longit = lltemp2;
} else if ((which1 == 2) && (which2 == 1)) { /*%< reversed */
longit = lltemp1;
latit = lltemp2;
} else { /*%< some kind of brokenness */
return (0);
}
break;
default: /*%< we didn't get one of each */
return (0);
}
/* altitude */
if (*cp == '-') {
altsign = -1;
cp++;
}
if (*cp == '+')
cp++;
while (isdigit((unsigned char)*cp))
altmeters = altmeters * 10 + (*cp++ - '0');
if (*cp == '.') { /*%< decimal meters */
cp++;
if (isdigit((unsigned char)*cp)) {
altfrac = (*cp++ - '0') * 10;
if (isdigit((unsigned char)*cp)) {
altfrac += (*cp++ - '0');
}
}
}
alt = (10000000 + (altsign * (altmeters * 100 + altfrac)));
while (!isspace((unsigned char)*cp) && (cp < maxcp)) /*%< if trailing garbage or m */
cp++;
while (isspace((unsigned char)*cp) && (cp < maxcp))
cp++;
if (cp >= maxcp)
goto defaults;
siz = precsize_aton(&cp);
while (!isspace((unsigned char)*cp) && (cp < maxcp)) /*%< if trailing garbage or m */
cp++;
while (isspace((unsigned char)*cp) && (cp < maxcp))
cp++;
if (cp >= maxcp)
goto defaults;
hp = precsize_aton(&cp);
while (!isspace((unsigned char)*cp) && (cp < maxcp)) /*%< if trailing garbage or m */
cp++;
while (isspace((unsigned char)*cp) && (cp < maxcp))
cp++;
if (cp >= maxcp)
goto defaults;
vp = precsize_aton(&cp);
defaults:
bcp = binary;
*bcp++ = (u_int8_t) 0; /*%< version byte */
*bcp++ = siz;
*bcp++ = hp;
*bcp++ = vp;
PUTLONG(latit,bcp);
PUTLONG(longit,bcp);
PUTLONG(alt,bcp);
return (16); /*%< size of RR in octets */
}
/*% takes an on-the-wire LOC RR and formats it in a human readable format. */
const char *
loc_ntoa(binary, ascii)
const u_char *binary;
char *ascii;
{
static const char *error = "?";
static char tmpbuf[sizeof
"1000 60 60.000 N 1000 60 60.000 W -12345678.00m 90000000.00m 90000000.00m 90000000.00m"];
const u_char *cp = binary;
int latdeg, latmin, latsec, latsecfrac;
int longdeg, longmin, longsec, longsecfrac;
char northsouth, eastwest;
const char *altsign;
int altmeters, altfrac;
const u_int32_t referencealt = 100000 * 100;
int32_t latval, longval, altval;
u_int32_t templ;
u_int8_t sizeval, hpval, vpval, versionval;
char *sizestr, *hpstr, *vpstr;
versionval = *cp++;
if (ascii == NULL)
ascii = tmpbuf;
if (versionval) {
(void) sprintf(ascii, "; error: unknown LOC RR version");
return (ascii);
}
sizeval = *cp++;
hpval = *cp++;
vpval = *cp++;
GETLONG(templ, cp);
latval = (templ - ((unsigned)1<<31));
GETLONG(templ, cp);
longval = (templ - ((unsigned)1<<31));
GETLONG(templ, cp);
if (templ < referencealt) { /*%< below WGS 84 spheroid */
altval = referencealt - templ;
altsign = "-";
} else {
altval = templ - referencealt;
altsign = "";
}
if (latval < 0) {
northsouth = 'S';
latval = -latval;
} else
northsouth = 'N';
latsecfrac = latval % 1000;
latval = latval / 1000;
latsec = latval % 60;
latval = latval / 60;
latmin = latval % 60;
latval = latval / 60;
latdeg = latval;
if (longval < 0) {
eastwest = 'W';
longval = -longval;
} else
eastwest = 'E';
longsecfrac = longval % 1000;
longval = longval / 1000;
longsec = longval % 60;
longval = longval / 60;
longmin = longval % 60;
longval = longval / 60;
longdeg = longval;
altfrac = altval % 100;
altmeters = (altval / 100);
sizestr = strdup(precsize_ntoa(sizeval));
hpstr = strdup(precsize_ntoa(hpval));
vpstr = strdup(precsize_ntoa(vpval));
sprintf(ascii,
"%d %.2d %.2d.%.3d %c %d %.2d %.2d.%.3d %c %s%d.%.2dm %sm %sm %sm",
latdeg, latmin, latsec, latsecfrac, northsouth,
longdeg, longmin, longsec, longsecfrac, eastwest,
altsign, altmeters, altfrac,
(sizestr != NULL) ? sizestr : error,
(hpstr != NULL) ? hpstr : error,
(vpstr != NULL) ? vpstr : error);
if (sizestr != NULL)
free(sizestr);
if (hpstr != NULL)
free(hpstr);
if (vpstr != NULL)
free(vpstr);
return (ascii);
}
/*% Return the number of DNS hierarchy levels in the name. */
int
dn_count_labels(const char *name) {
int i, len, count;
len = strlen(name);
for (i = 0, count = 0; i < len; i++) {
/* XXX need to check for \. or use named's nlabels(). */
if (name[i] == '.')
count++;
}
/* don't count initial wildcard */
if (name[0] == '*')
if (count)
count--;
/* don't count the null label for root. */
/* if terminating '.' not found, must adjust */
/* count to include last label */
if (len > 0 && name[len-1] != '.')
count++;
return (count);
}
/*%
* Make dates expressed in seconds-since-Jan-1-1970 easy to read.
* SIG records are required to be printed like this, by the Secure DNS RFC.
*/
char *
p_secstodate (u_long secs) {
char *output = p_secstodate_output;
time_t clock = secs;
struct tm *time;
#ifdef HAVE_TIME_R
struct tm res;
time = gmtime_r(&clock, &res);
#else
time = gmtime(&clock);
#endif
time->tm_year += 1900;
time->tm_mon += 1;
sprintf(output, "%04d%02d%02d%02d%02d%02d",
time->tm_year, time->tm_mon, time->tm_mday,
time->tm_hour, time->tm_min, time->tm_sec);
return (output);
}
u_int16_t
res_nametoclass(const char *buf, int *successp) {
unsigned long result;
char *endptr;
int success;
result = sym_ston(__p_class_syms, buf, &success);
if (success)
goto done;
if (strncasecmp(buf, "CLASS", 5) != 0 ||
!isdigit((unsigned char)buf[5]))
goto done;
errno = 0;
result = strtoul(buf + 5, &endptr, 10);
if (errno == 0 && *endptr == '\0' && result <= 0xffffU)
success = 1;
done:
if (successp)
*successp = success;
return (result);
}
u_int16_t
res_nametotype(const char *buf, int *successp) {
unsigned long result;
char *endptr;
int success;
result = sym_ston(__p_type_syms, buf, &success);
if (success)
goto done;
if (strncasecmp(buf, "type", 4) != 0 ||
!isdigit((unsigned char)buf[4]))
goto done;
errno = 0;
result = strtoul(buf + 4, &endptr, 10);
if (errno == 0 && *endptr == '\0' && result <= 0xffffU)
success = 1;
done:
if (successp)
*successp = success;
return (result);
}
/*
* Weak aliases for applications that use certain private entry points,
* and fail to include .
*/
#undef fp_resstat
__weak_reference(__fp_resstat, fp_resstat);
#undef p_fqnname
__weak_reference(__p_fqnname, p_fqnname);
#undef sym_ston
__weak_reference(__sym_ston, sym_ston);
#undef sym_ntos
__weak_reference(__sym_ntos, sym_ntos);
#undef sym_ntop
__weak_reference(__sym_ntop, sym_ntop);
#undef dn_count_labels
__weak_reference(__dn_count_labels, dn_count_labels);
#undef p_secstodate
__weak_reference(__p_secstodate, p_secstodate);
/*! \file */
Index: projects/arpv2_merge_1/lib/libc/resolv/res_mkquery.c
===================================================================
--- projects/arpv2_merge_1/lib/libc/resolv/res_mkquery.c (revision 186114)
+++ projects/arpv2_merge_1/lib/libc/resolv/res_mkquery.c (revision 186115)
@@ -1,257 +1,303 @@
/*
* Copyright (c) 1985, 1993
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Portions Copyright (c) 1993 by Digital Equipment Corporation.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies, and that
* the name of Digital Equipment Corporation not be used in advertising or
* publicity pertaining to distribution of the document or software without
* specific, written prior permission.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND DIGITAL EQUIPMENT CORP. DISCLAIMS ALL
* WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL DIGITAL EQUIPMENT
* CORPORATION BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
* DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
* PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
* ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
* SOFTWARE.
*/
/*
* Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
* Portions Copyright (c) 1996-1999 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#if defined(LIBC_SCCS) && !defined(lint)
static const char sccsid[] = "@(#)res_mkquery.c 8.1 (Berkeley) 6/4/93";
-static const char rcsid[] = "$Id: res_mkquery.c,v 1.5.18.1 2005/04/27 05:01:11 sra Exp $";
+static const char rcsid[] = "$Id: res_mkquery.c,v 1.5.18.2 2008/04/03 23:15:15 marka Exp $";
#endif /* LIBC_SCCS and not lint */
#include
__FBSDID("$FreeBSD$");
#include "port_before.h"
#include
#include
#include
#include
#include
#include
#include
#include
#include "port_after.h"
/* Options. Leave them on. */
#define DEBUG
extern const char *_res_opcodes[];
/*%
* Form all types of queries.
* Returns the size of the result or -1.
*/
int
res_nmkquery(res_state statp,
int op, /*!< opcode of query */
const char *dname, /*!< domain name */
int class, int type, /*!< class and type of query */
const u_char *data, /*!< resource record data */
int datalen, /*!< length of data */
const u_char *newrr_in, /*!< new rr for modify or append */
u_char *buf, /*!< buffer to put query */
int buflen) /*!< size of buffer */
{
HEADER *hp;
u_char *cp, *ep;
int n;
u_char *dnptrs[20], **dpp, **lastdnptr;
UNUSED(newrr_in);
#ifdef DEBUG
if (statp->options & RES_DEBUG)
printf(";; res_nmkquery(%s, %s, %s, %s)\n",
_res_opcodes[op], dname, p_class(class), p_type(type));
#endif
/*
* Initialize header fields.
*/
if ((buf == NULL) || (buflen < HFIXEDSZ))
return (-1);
memset(buf, 0, HFIXEDSZ);
hp = (HEADER *) buf;
hp->id = htons(++statp->id);
hp->opcode = op;
hp->rd = (statp->options & RES_RECURSE) != 0U;
hp->rcode = NOERROR;
cp = buf + HFIXEDSZ;
ep = buf + buflen;
dpp = dnptrs;
*dpp++ = buf;
*dpp++ = NULL;
lastdnptr = dnptrs + sizeof dnptrs / sizeof dnptrs[0];
/*
* perform opcode specific processing
*/
switch (op) {
case QUERY: /*FALLTHROUGH*/
case NS_NOTIFY_OP:
if (ep - cp < QFIXEDSZ)
return (-1);
if ((n = dn_comp(dname, cp, ep - cp - QFIXEDSZ, dnptrs,
lastdnptr)) < 0)
return (-1);
cp += n;
ns_put16(type, cp);
cp += INT16SZ;
ns_put16(class, cp);
cp += INT16SZ;
hp->qdcount = htons(1);
if (op == QUERY || data == NULL)
break;
/*
* Make an additional record for completion domain.
*/
if ((ep - cp) < RRFIXEDSZ)
return (-1);
n = dn_comp((const char *)data, cp, ep - cp - RRFIXEDSZ,
dnptrs, lastdnptr);
if (n < 0)
return (-1);
cp += n;
ns_put16(T_NULL, cp);
cp += INT16SZ;
ns_put16(class, cp);
cp += INT16SZ;
ns_put32(0, cp);
cp += INT32SZ;
ns_put16(0, cp);
cp += INT16SZ;
hp->arcount = htons(1);
break;
case IQUERY:
/*
* Initialize answer section
*/
if (ep - cp < 1 + RRFIXEDSZ + datalen)
return (-1);
*cp++ = '\0'; /*%< no domain name */
ns_put16(type, cp);
cp += INT16SZ;
ns_put16(class, cp);
cp += INT16SZ;
ns_put32(0, cp);
cp += INT32SZ;
ns_put16(datalen, cp);
cp += INT16SZ;
if (datalen) {
memcpy(cp, data, datalen);
cp += datalen;
}
hp->ancount = htons(1);
break;
default:
return (-1);
}
return (cp - buf);
}
#ifdef RES_USE_EDNS0
/* attach OPT pseudo-RR, as documented in RFC2671 (EDNS0). */
-#ifndef T_OPT
-#define T_OPT 41
-#endif
int
res_nopt(res_state statp,
int n0, /*%< current offset in buffer */
u_char *buf, /*%< buffer to put query */
int buflen, /*%< size of buffer */
int anslen) /*%< UDP answer buffer size */
{
HEADER *hp;
u_char *cp, *ep;
u_int16_t flags = 0;
#ifdef DEBUG
if ((statp->options & RES_DEBUG) != 0U)
printf(";; res_nopt()\n");
#endif
hp = (HEADER *) buf;
cp = buf + n0;
ep = buf + buflen;
if ((ep - cp) < 1 + RRFIXEDSZ)
return (-1);
- *cp++ = 0; /*%< "." */
- ns_put16(T_OPT, cp); /*%< TYPE */
+ *cp++ = 0; /*%< "." */
+ ns_put16(ns_t_opt, cp); /*%< TYPE */
cp += INT16SZ;
if (anslen > 0xffff)
anslen = 0xffff; /* limit to 16bit value */
- ns_put16(anslen & 0xffff, cp); /*%< CLASS = UDP payload size */
+ ns_put16(anslen & 0xffff, cp); /*%< CLASS = UDP payload size */
cp += INT16SZ;
- *cp++ = NOERROR; /*%< extended RCODE */
- *cp++ = 0; /*%< EDNS version */
+ *cp++ = NOERROR; /*%< extended RCODE */
+ *cp++ = 0; /*%< EDNS version */
+
if (statp->options & RES_USE_DNSSEC) {
#ifdef DEBUG
if (statp->options & RES_DEBUG)
printf(";; res_opt()... ENDS0 DNSSEC\n");
#endif
flags |= NS_OPT_DNSSEC_OK;
}
ns_put16(flags, cp);
cp += INT16SZ;
- ns_put16(0, cp); /*%< RDLEN */
+
+ ns_put16(0U, cp); /*%< RDLEN */
cp += INT16SZ;
+
hp->arcount = htons(ntohs(hp->arcount) + 1);
+
+ return (cp - buf);
+}
+
+/*
+ * Construct variable data (RDATA) block for OPT psuedo-RR, append it
+ * to the buffer, then update the RDLEN field (previously set to zero by
+ * res_nopt()) with the new RDATA length.
+ */
+int
+res_nopt_rdata(res_state statp,
+ int n0, /*%< current offset in buffer */
+ u_char *buf, /*%< buffer to put query */
+ int buflen, /*%< size of buffer */
+ u_char *rdata, /*%< ptr to start of opt rdata */
+ u_short code, /*%< OPTION-CODE */
+ u_short len, /*%< OPTION-LENGTH */
+ u_char *data) /*%< OPTION_DATA */
+{
+ register u_char *cp, *ep;
+
+#ifdef DEBUG
+ if ((statp->options & RES_DEBUG) != 0U)
+ printf(";; res_nopt_rdata()\n");
+#endif
+
+ cp = buf + n0;
+ ep = buf + buflen;
+
+ if ((ep - cp) < (4 + len))
+ return (-1);
+
+ if (rdata < (buf + 2) || rdata >= ep)
+ return (-1);
+
+ ns_put16(code, cp);
+ cp += INT16SZ;
+
+ ns_put16(len, cp);
+ cp += INT16SZ;
+
+ memcpy(cp, data, len);
+ cp += len;
+
+ len = cp - rdata;
+ ns_put16(len, rdata - 2); /* Update RDLEN field */
return (cp - buf);
}
#endif
/*! \file */
Index: projects/arpv2_merge_1/lib/libc/resolv/res_query.c
===================================================================
--- projects/arpv2_merge_1/lib/libc/resolv/res_query.c (revision 186114)
+++ projects/arpv2_merge_1/lib/libc/resolv/res_query.c (revision 186115)
@@ -1,481 +1,489 @@
/*
* Copyright (c) 1988, 1993
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Portions Copyright (c) 1993 by Digital Equipment Corporation.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies, and that
* the name of Digital Equipment Corporation not be used in advertising or
* publicity pertaining to distribution of the document or software without
* specific, written prior permission.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND DIGITAL EQUIPMENT CORP. DISCLAIMS ALL
* WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL DIGITAL EQUIPMENT
* CORPORATION BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
* DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
* PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
* ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
* SOFTWARE.
*/
/*
* Copyright (c) 2004 by Internet Systems Consortium, Inc. ("ISC")
* Portions Copyright (c) 1996-1999 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#if defined(LIBC_SCCS) && !defined(lint)
static const char sccsid[] = "@(#)res_query.c 8.1 (Berkeley) 6/4/93";
-static const char rcsid[] = "$Id: res_query.c,v 1.7.18.1 2005/04/27 05:01:11 sra Exp $";
+static const char rcsid[] = "$Id: res_query.c,v 1.7.18.2 2008/04/03 23:15:15 marka Exp $";
#endif /* LIBC_SCCS and not lint */
#include
__FBSDID("$FreeBSD$");
#include "port_before.h"
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include "port_after.h"
/* Options. Leave them on. */
#define DEBUG
#if PACKETSZ > 1024
#define MAXPACKET PACKETSZ
#else
#define MAXPACKET 1024
#endif
/*%
* Formulate a normal query, send, and await answer.
* Returned answer is placed in supplied buffer "answer".
* Perform preliminary check of answer, returning success only
* if no error is indicated and the answer count is nonzero.
* Return the size of the response on success, -1 on error.
* Error number is left in H_ERRNO.
*
* Caller must parse answer and determine whether it answers the question.
*/
int
res_nquery(res_state statp,
const char *name, /*%< domain name */
int class, int type, /*%< class and type of query */
u_char *answer, /*%< buffer to put answer */
int anslen) /*%< size of answer buffer */
{
u_char buf[MAXPACKET];
HEADER *hp = (HEADER *) answer;
- int n;
u_int oflags;
+ u_char *rdata;
+ int n;
oflags = statp->_flags;
again:
hp->rcode = NOERROR; /*%< default */
#ifdef DEBUG
if (statp->options & RES_DEBUG)
printf(";; res_query(%s, %d, %d)\n", name, class, type);
#endif
n = res_nmkquery(statp, QUERY, name, class, type, NULL, 0, NULL,
buf, sizeof(buf));
#ifdef RES_USE_EDNS0
if (n > 0 && (statp->_flags & RES_F_EDNS0ERR) == 0 &&
- (statp->options & (RES_USE_EDNS0|RES_USE_DNSSEC)) != 0U)
+ (statp->options & (RES_USE_EDNS0|RES_USE_DNSSEC|RES_NSID))) {
n = res_nopt(statp, n, buf, sizeof(buf), anslen);
+ rdata = &buf[n];
+ if (n > 0 && (statp->options & RES_NSID) != 0U) {
+ n = res_nopt_rdata(statp, n, buf, sizeof(buf), rdata,
+ NS_OPT_NSID, 0, NULL);
+ }
+ }
#endif
if (n <= 0) {
#ifdef DEBUG
if (statp->options & RES_DEBUG)
printf(";; res_query: mkquery failed\n");
#endif
RES_SET_H_ERRNO(statp, NO_RECOVERY);
return (n);
}
+
n = res_nsend(statp, buf, n, answer, anslen);
if (n < 0) {
#ifdef RES_USE_EDNS0
/* if the query choked with EDNS0, retry without EDNS0 */
if ((statp->options & (RES_USE_EDNS0|RES_USE_DNSSEC)) != 0U &&
((oflags ^ statp->_flags) & RES_F_EDNS0ERR) != 0) {
statp->_flags |= RES_F_EDNS0ERR;
if (statp->options & RES_DEBUG)
printf(";; res_nquery: retry without EDNS0\n");
goto again;
}
#endif
#ifdef DEBUG
if (statp->options & RES_DEBUG)
printf(";; res_query: send error\n");
#endif
RES_SET_H_ERRNO(statp, TRY_AGAIN);
return (n);
}
if (hp->rcode != NOERROR || ntohs(hp->ancount) == 0) {
#ifdef DEBUG
if (statp->options & RES_DEBUG)
printf(";; rcode = (%s), counts = an:%d ns:%d ar:%d\n",
p_rcode(hp->rcode),
ntohs(hp->ancount),
ntohs(hp->nscount),
ntohs(hp->arcount));
#endif
switch (hp->rcode) {
case NXDOMAIN:
RES_SET_H_ERRNO(statp, HOST_NOT_FOUND);
break;
case SERVFAIL:
RES_SET_H_ERRNO(statp, TRY_AGAIN);
break;
case NOERROR:
RES_SET_H_ERRNO(statp, NO_DATA);
break;
case FORMERR:
case NOTIMP:
case REFUSED:
default:
RES_SET_H_ERRNO(statp, NO_RECOVERY);
break;
}
return (-1);
}
return (n);
}
/*%
* Formulate a normal query, send, and retrieve answer in supplied buffer.
* Return the size of the response on success, -1 on error.
* If enabled, implement search rules until answer or unrecoverable failure
* is detected. Error code, if any, is left in H_ERRNO.
*/
int
res_nsearch(res_state statp,
const char *name, /*%< domain name */
int class, int type, /*%< class and type of query */
u_char *answer, /*%< buffer to put answer */
int anslen) /*%< size of answer */
{
const char *cp, * const *domain;
HEADER *hp = (HEADER *) answer;
char tmp[NS_MAXDNAME];
u_int dots;
int trailing_dot, ret, saved_herrno;
int got_nodata = 0, got_servfail = 0, root_on_list = 0;
int tried_as_is = 0;
int searched = 0;
errno = 0;
RES_SET_H_ERRNO(statp, HOST_NOT_FOUND); /*%< True if we never query. */
dots = 0;
for (cp = name; *cp != '\0'; cp++)
dots += (*cp == '.');
trailing_dot = 0;
if (cp > name && *--cp == '.')
trailing_dot++;
/* If there aren't any dots, it could be a user-level alias. */
if (!dots && (cp = res_hostalias(statp, name, tmp, sizeof tmp))!= NULL)
return (res_nquery(statp, cp, class, type, answer, anslen));
/*
* If there are enough dots in the name, let's just give it a
* try 'as is'. The threshold can be set with the "ndots" option.
* Also, query 'as is', if there is a trailing dot in the name.
*/
saved_herrno = -1;
if (dots >= statp->ndots || trailing_dot) {
ret = res_nquerydomain(statp, name, NULL, class, type,
answer, anslen);
if (ret > 0 || trailing_dot)
return (ret);
if (errno == ECONNREFUSED) {
RES_SET_H_ERRNO(statp, TRY_AGAIN);
return (-1);
}
switch (statp->res_h_errno) {
case NO_DATA:
case HOST_NOT_FOUND:
break;
case TRY_AGAIN:
if (hp->rcode == SERVFAIL)
break;
/* FALLTHROUGH */
default:
return (-1);
}
saved_herrno = statp->res_h_errno;
tried_as_is++;
}
/*
* We do at least one level of search if
* - there is no dot and RES_DEFNAME is set, or
* - there is at least one dot, there is no trailing dot,
* and RES_DNSRCH is set.
*/
if ((!dots && (statp->options & RES_DEFNAMES) != 0U) ||
(dots && !trailing_dot && (statp->options & RES_DNSRCH) != 0U)) {
int done = 0;
for (domain = (const char * const *)statp->dnsrch;
*domain && !done;
domain++) {
searched = 1;
if (domain[0][0] == '\0' ||
(domain[0][0] == '.' && domain[0][1] == '\0'))
root_on_list++;
if (root_on_list && tried_as_is)
continue;
ret = res_nquerydomain(statp, name, *domain,
class, type,
answer, anslen);
if (ret > 0)
return (ret);
/*
* If no server present, give up.
* If name isn't found in this domain,
* keep trying higher domains in the search list
* (if that's enabled).
* On a NO_DATA error, keep trying, otherwise
* a wildcard entry of another type could keep us
* from finding this entry higher in the domain.
* If we get some other error (negative answer or
* server failure), then stop searching up,
* but try the input name below in case it's
* fully-qualified.
*/
if (errno == ECONNREFUSED) {
RES_SET_H_ERRNO(statp, TRY_AGAIN);
return (-1);
}
switch (statp->res_h_errno) {
case NO_DATA:
got_nodata++;
/* FALLTHROUGH */
case HOST_NOT_FOUND:
/* keep trying */
break;
case TRY_AGAIN:
/*
* This can occur due to a server failure
* (that is, all listed servers have failed),
* or all listed servers have timed out.
* ((HEADER *)answer)->rcode may not be set
* to SERVFAIL in the case of a timeout.
*
* Either way we must return TRY_AGAIN in
* order to avoid non-deterministic
* return codes.
* For example, loaded name servers or races
* against network startup/validation (dhcp,
* ppp, etc) can cause the search to timeout
* on one search element, e.g. 'fu.bar.com',
* and return a definitive failure on the
* next search element, e.g. 'fu.'.
*/
got_servfail++;
if (hp->rcode == SERVFAIL) {
/* try next search element, if any */
break;
}
/* FALLTHROUGH */
default:
/* anything else implies that we're done */
done++;
}
/* if we got here for some reason other than DNSRCH,
* we only wanted one iteration of the loop, so stop.
*/
if ((statp->options & RES_DNSRCH) == 0U)
done++;
}
}
switch (statp->res_h_errno) {
case NO_DATA:
case HOST_NOT_FOUND:
break;
case TRY_AGAIN:
if (hp->rcode == SERVFAIL)
break;
/* FALLTHROUGH */
default:
goto giveup;
}
/*
* If the query has not already been tried as is then try it
* unless RES_NOTLDQUERY is set and there were no dots.
*/
if ((dots || !searched || (statp->options & RES_NOTLDQUERY) == 0U) &&
!(tried_as_is || root_on_list)) {
ret = res_nquerydomain(statp, name, NULL, class, type,
answer, anslen);
if (ret > 0)
return (ret);
}
/* if we got here, we didn't satisfy the search.
* if we did an initial full query, return that query's H_ERRNO
* (note that we wouldn't be here if that query had succeeded).
* else if we ever got a nodata, send that back as the reason.
* else send back meaningless H_ERRNO, that being the one from
* the last DNSRCH we did.
*/
giveup:
if (saved_herrno != -1)
RES_SET_H_ERRNO(statp, saved_herrno);
else if (got_nodata)
RES_SET_H_ERRNO(statp, NO_DATA);
else if (got_servfail)
RES_SET_H_ERRNO(statp, TRY_AGAIN);
return (-1);
}
/*%
* Perform a call on res_query on the concatenation of name and domain,
* removing a trailing dot from name if domain is NULL.
*/
int
res_nquerydomain(res_state statp,
const char *name,
const char *domain,
int class, int type, /*%< class and type of query */
u_char *answer, /*%< buffer to put answer */
int anslen) /*%< size of answer */
{
char nbuf[MAXDNAME];
const char *longname = nbuf;
int n, d;
#ifdef DEBUG
if (statp->options & RES_DEBUG)
printf(";; res_nquerydomain(%s, %s, %d, %d)\n",
name, domain?domain:"", class, type);
#endif
if (domain == NULL) {
/*
* Check for trailing '.';
* copy without '.' if present.
*/
n = strlen(name);
if (n >= MAXDNAME) {
RES_SET_H_ERRNO(statp, NO_RECOVERY);
return (-1);
}
n--;
if (n >= 0 && name[n] == '.') {
strncpy(nbuf, name, n);
nbuf[n] = '\0';
} else
longname = name;
} else {
n = strlen(name);
d = strlen(domain);
if (n + d + 1 >= MAXDNAME) {
RES_SET_H_ERRNO(statp, NO_RECOVERY);
return (-1);
}
sprintf(nbuf, "%s.%s", name, domain);
}
return (res_nquery(statp, longname, class, type, answer, anslen));
}
const char *
res_hostalias(const res_state statp, const char *name, char *dst, size_t siz) {
char *file, *cp1, *cp2;
char buf[BUFSIZ];
FILE *fp;
if (statp->options & RES_NOALIASES)
return (NULL);
if (issetugid())
return (NULL);
file = getenv("HOSTALIASES");
if (file == NULL || (fp = fopen(file, "r")) == NULL)
return (NULL);
setbuf(fp, NULL);
buf[sizeof(buf) - 1] = '\0';
while (fgets(buf, sizeof(buf), fp)) {
for (cp1 = buf; *cp1 && !isspace((unsigned char)*cp1); ++cp1)
;
if (!*cp1)
break;
*cp1 = '\0';
if (ns_samename(buf, name) == 1) {
while (isspace((unsigned char)*++cp1))
;
if (!*cp1)
break;
for (cp2 = cp1 + 1; *cp2 &&
!isspace((unsigned char)*cp2); ++cp2)
;
*cp2 = '\0';
strncpy(dst, cp1, siz - 1);
dst[siz - 1] = '\0';
fclose(fp);
return (dst);
}
}
fclose(fp);
return (NULL);
}
/*! \file */
Index: projects/arpv2_merge_1/lib/libc/resolv/res_send.c
===================================================================
--- projects/arpv2_merge_1/lib/libc/resolv/res_send.c (revision 186114)
+++ projects/arpv2_merge_1/lib/libc/resolv/res_send.c (revision 186115)
@@ -1,1167 +1,1181 @@
/*
* Copyright (c) 1985, 1989, 1993
* The Regents of the University of California. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 4. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Portions Copyright (c) 1993 by Digital Equipment Corporation.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies, and that
* the name of Digital Equipment Corporation not be used in advertising or
* publicity pertaining to distribution of the document or software without
* specific, written prior permission.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND DIGITAL EQUIPMENT CORP. DISCLAIMS ALL
* WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES
* OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL DIGITAL EQUIPMENT
* CORPORATION BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
* DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
* PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS
* ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
* SOFTWARE.
*/
/*
* Copyright (c) 2005 by Internet Systems Consortium, Inc. ("ISC")
* Portions Copyright (c) 1996-1999 by Internet Software Consortium.
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#if defined(LIBC_SCCS) && !defined(lint)
static const char sccsid[] = "@(#)res_send.c 8.1 (Berkeley) 6/4/93";
-static const char rcsid[] = "$Id: res_send.c,v 1.9.18.8 2006/10/16 23:00:58 marka Exp $";
+static const char rcsid[] = "$Id: res_send.c,v 1.9.18.10 2008/01/27 02:06:26 marka Exp $";
#endif /* LIBC_SCCS and not lint */
#include
__FBSDID("$FreeBSD$");
/*! \file
* \brief
* Send query to name server and wait for reply.
*/
#include "port_before.h"
#ifndef USE_KQUEUE
#include "fd_setsize.h"
#endif
#include "namespace.h"
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include "port_after.h"
#ifdef USE_KQUEUE
#include
#else
#ifdef USE_POLL
#ifdef HAVE_STROPTS_H
#include
#endif
#include
#endif /* USE_POLL */
#endif
#include "un-namespace.h"
/* Options. Leave them on. */
#define DEBUG
#include "res_debug.h"
#include "res_private.h"
#define EXT(res) ((res)->_u._ext)
#if !defined(USE_POLL) && !defined(USE_KQUEUE)
static const int highestFD = FD_SETSIZE - 1;
#endif
/* Forward. */
static int get_salen(const struct sockaddr *);
static struct sockaddr * get_nsaddr(res_state, size_t);
static int send_vc(res_state, const u_char *, int,
u_char *, int, int *, int);
static int send_dg(res_state,
#ifdef USE_KQUEUE
int kq,
#endif
const u_char *, int,
u_char *, int, int *, int, int,
int *, int *);
static void Aerror(const res_state, FILE *, const char *, int,
const struct sockaddr *, int);
static void Perror(const res_state, FILE *, const char *, int);
static int sock_eq(struct sockaddr *, struct sockaddr *);
#if defined(NEED_PSELECT) && !defined(USE_POLL) && !defined(USE_KQUEUE)
static int pselect(int, void *, void *, void *,
struct timespec *,
const sigset_t *);
#endif
void res_pquery(const res_state, const u_char *, int, FILE *);
static const int niflags = NI_NUMERICHOST | NI_NUMERICSERV;
/* Public. */
/*%
* looks up "ina" in _res.ns_addr_list[]
*
* returns:
*\li 0 : not found
*\li >0 : found
*
* author:
*\li paul vixie, 29may94
*/
int
res_ourserver_p(const res_state statp, const struct sockaddr *sa) {
const struct sockaddr_in *inp, *srv;
const struct sockaddr_in6 *in6p, *srv6;
int ns;
switch (sa->sa_family) {
case AF_INET:
inp = (const struct sockaddr_in *)sa;
for (ns = 0; ns < statp->nscount; ns++) {
srv = (struct sockaddr_in *)get_nsaddr(statp, ns);
if (srv->sin_family == inp->sin_family &&
srv->sin_port == inp->sin_port &&
(srv->sin_addr.s_addr == INADDR_ANY ||
srv->sin_addr.s_addr == inp->sin_addr.s_addr))
return (1);
}
break;
case AF_INET6:
if (EXT(statp).ext == NULL)
break;
in6p = (const struct sockaddr_in6 *)sa;
for (ns = 0; ns < statp->nscount; ns++) {
srv6 = (struct sockaddr_in6 *)get_nsaddr(statp, ns);
if (srv6->sin6_family == in6p->sin6_family &&
srv6->sin6_port == in6p->sin6_port &&
#ifdef HAVE_SIN6_SCOPE_ID
(srv6->sin6_scope_id == 0 ||
srv6->sin6_scope_id == in6p->sin6_scope_id) &&
#endif
(IN6_IS_ADDR_UNSPECIFIED(&srv6->sin6_addr) ||
IN6_ARE_ADDR_EQUAL(&srv6->sin6_addr, &in6p->sin6_addr)))
return (1);
}
break;
default:
break;
}
return (0);
}
/*%
* look for (name,type,class) in the query section of packet (buf,eom)
*
* requires:
*\li buf + HFIXEDSZ <= eom
*
* returns:
*\li -1 : format error
*\li 0 : not found
*\li >0 : found
*
* author:
*\li paul vixie, 29may94
*/
int
res_nameinquery(const char *name, int type, int class,
const u_char *buf, const u_char *eom)
{
const u_char *cp = buf + HFIXEDSZ;
int qdcount = ntohs(((const HEADER*)buf)->qdcount);
while (qdcount-- > 0) {
char tname[MAXDNAME+1];
int n, ttype, tclass;
n = dn_expand(buf, eom, cp, tname, sizeof tname);
if (n < 0)
return (-1);
cp += n;
if (cp + 2 * INT16SZ > eom)
return (-1);
ttype = ns_get16(cp); cp += INT16SZ;
tclass = ns_get16(cp); cp += INT16SZ;
if (ttype == type && tclass == class &&
ns_samename(tname, name) == 1)
return (1);
}
return (0);
}
/*%
* is there a 1:1 mapping of (name,type,class)
* in (buf1,eom1) and (buf2,eom2)?
*
* returns:
*\li -1 : format error
*\li 0 : not a 1:1 mapping
*\li >0 : is a 1:1 mapping
*
* author:
*\li paul vixie, 29may94
*/
int
res_queriesmatch(const u_char *buf1, const u_char *eom1,
const u_char *buf2, const u_char *eom2)
{
const u_char *cp = buf1 + HFIXEDSZ;
int qdcount = ntohs(((const HEADER*)buf1)->qdcount);
if (buf1 + HFIXEDSZ > eom1 || buf2 + HFIXEDSZ > eom2)
return (-1);
/*
* Only header section present in replies to
* dynamic update packets.
*/
if ((((const HEADER *)buf1)->opcode == ns_o_update) &&
(((const HEADER *)buf2)->opcode == ns_o_update))
return (1);
if (qdcount != ntohs(((const HEADER*)buf2)->qdcount))
return (0);
while (qdcount-- > 0) {
char tname[MAXDNAME+1];
int n, ttype, tclass;
n = dn_expand(buf1, eom1, cp, tname, sizeof tname);
if (n < 0)
return (-1);
cp += n;
if (cp + 2 * INT16SZ > eom1)
return (-1);
ttype = ns_get16(cp); cp += INT16SZ;
tclass = ns_get16(cp); cp += INT16SZ;
if (!res_nameinquery(tname, ttype, tclass, buf2, eom2))
return (0);
}
return (1);
}
int
res_nsend(res_state statp,
const u_char *buf, int buflen, u_char *ans, int anssiz)
{
- int gotsomewhere, terrno, try, v_circuit, resplen, ns, n;
+ int gotsomewhere, terrno, tries, v_circuit, resplen, ns, n;
#ifdef USE_KQUEUE
int kq;
#endif
char abuf[NI_MAXHOST];
/* No name servers or res_init() failure */
if (statp->nscount == 0 || EXT(statp).ext == NULL) {
errno = ESRCH;
return (-1);
}
if (anssiz < HFIXEDSZ) {
errno = EINVAL;
return (-1);
}
DprintQ((statp->options & RES_DEBUG) || (statp->pfcode & RES_PRF_QUERY),
(stdout, ";; res_send()\n"), buf, buflen);
v_circuit = (statp->options & RES_USEVC) || buflen > PACKETSZ;
gotsomewhere = 0;
terrno = ETIMEDOUT;
#ifdef USE_KQUEUE
if ((kq = kqueue()) < 0) {
Perror(statp, stderr, "kqueue", errno);
return (-1);
}
#endif
/*
* If the ns_addr_list in the resolver context has changed, then
* invalidate our cached copy and the associated timing data.
*/
if (EXT(statp).nscount != 0) {
int needclose = 0;
struct sockaddr_storage peer;
ISC_SOCKLEN_T peerlen;
if (EXT(statp).nscount != statp->nscount)
needclose++;
else
for (ns = 0; ns < statp->nscount; ns++) {
if (statp->nsaddr_list[ns].sin_family &&
!sock_eq((struct sockaddr *)&statp->nsaddr_list[ns],
(struct sockaddr *)&EXT(statp).ext->nsaddrs[ns])) {
needclose++;
break;
}
if (EXT(statp).nssocks[ns] == -1)
continue;
peerlen = sizeof(peer);
if (_getsockname(EXT(statp).nssocks[ns],
(struct sockaddr *)&peer, &peerlen) < 0) {
needclose++;
break;
}
if (!sock_eq((struct sockaddr *)&peer,
get_nsaddr(statp, ns))) {
needclose++;
break;
}
}
if (needclose) {
res_nclose(statp);
EXT(statp).nscount = 0;
}
}
/*
* Maybe initialize our private copy of the ns_addr_list.
*/
if (EXT(statp).nscount == 0) {
for (ns = 0; ns < statp->nscount; ns++) {
EXT(statp).nstimes[ns] = RES_MAXTIME;
EXT(statp).nssocks[ns] = -1;
if (!statp->nsaddr_list[ns].sin_family)
continue;
EXT(statp).ext->nsaddrs[ns].sin =
statp->nsaddr_list[ns];
}
EXT(statp).nscount = statp->nscount;
}
/*
* Some resolvers want to even out the load on their nameservers.
* Note that RES_BLAST overrides RES_ROTATE.
*/
if ((statp->options & RES_ROTATE) != 0U &&
(statp->options & RES_BLAST) == 0U) {
union res_sockaddr_union inu;
struct sockaddr_in ina;
int lastns = statp->nscount - 1;
int fd;
u_int16_t nstime;
if (EXT(statp).ext != NULL)
inu = EXT(statp).ext->nsaddrs[0];
ina = statp->nsaddr_list[0];
fd = EXT(statp).nssocks[0];
nstime = EXT(statp).nstimes[0];
for (ns = 0; ns < lastns; ns++) {
if (EXT(statp).ext != NULL)
EXT(statp).ext->nsaddrs[ns] =
EXT(statp).ext->nsaddrs[ns + 1];
statp->nsaddr_list[ns] = statp->nsaddr_list[ns + 1];
EXT(statp).nssocks[ns] = EXT(statp).nssocks[ns + 1];
EXT(statp).nstimes[ns] = EXT(statp).nstimes[ns + 1];
}
if (EXT(statp).ext != NULL)
EXT(statp).ext->nsaddrs[lastns] = inu;
statp->nsaddr_list[lastns] = ina;
EXT(statp).nssocks[lastns] = fd;
EXT(statp).nstimes[lastns] = nstime;
}
/*
* Send request, RETRY times, or until successful.
*/
- for (try = 0; try < statp->retry; try++) {
+ for (tries = 0; tries < statp->retry; tries++) {
for (ns = 0; ns < statp->nscount; ns++) {
struct sockaddr *nsap;
int nsaplen;
nsap = get_nsaddr(statp, ns);
nsaplen = get_salen(nsap);
statp->_flags &= ~RES_F_LASTMASK;
statp->_flags |= (ns << RES_F_LASTSHIFT);
same_ns:
if (statp->qhook) {
int done = 0, loops = 0;
do {
res_sendhookact act;
act = (*statp->qhook)(&nsap, &buf, &buflen,
ans, anssiz, &resplen);
switch (act) {
case res_goahead:
done = 1;
break;
case res_nextns:
res_nclose(statp);
goto next_ns;
case res_done:
#ifdef USE_KQUEUE
_close(kq);
#endif
return (resplen);
case res_modified:
/* give the hook another try */
if (++loops < 42) /*doug adams*/
break;
/*FALLTHROUGH*/
case res_error:
/*FALLTHROUGH*/
default:
goto fail;
}
} while (!done);
}
Dprint(((statp->options & RES_DEBUG) &&
getnameinfo(nsap, nsaplen, abuf, sizeof(abuf),
NULL, 0, niflags) == 0),
(stdout, ";; Querying server (# %d) address = %s\n",
ns + 1, abuf));
if (v_circuit) {
/* Use VC; at most one attempt per server. */
- try = statp->retry;
+ tries = statp->retry;
n = send_vc(statp, buf, buflen, ans, anssiz, &terrno,
ns);
if (n < 0)
goto fail;
if (n == 0)
goto next_ns;
resplen = n;
} else {
/* Use datagrams. */
n = send_dg(statp,
#ifdef USE_KQUEUE
kq,
#endif
buf, buflen, ans, anssiz, &terrno,
- ns, try, &v_circuit, &gotsomewhere);
+ ns, tries, &v_circuit, &gotsomewhere);
if (n < 0)
goto fail;
if (n == 0)
goto next_ns;
if (v_circuit)
goto same_ns;
resplen = n;
}
Dprint((statp->options & RES_DEBUG) ||
((statp->pfcode & RES_PRF_REPLY) &&
(statp->pfcode & RES_PRF_HEAD1)),
(stdout, ";; got answer:\n"));
DprintQ((statp->options & RES_DEBUG) ||
(statp->pfcode & RES_PRF_REPLY),
(stdout, "%s", ""),
ans, (resplen > anssiz) ? anssiz : resplen);
/*
* If we have temporarily opened a virtual circuit,
* or if we haven't been asked to keep a socket open,
* close the socket.
*/
if ((v_circuit && (statp->options & RES_USEVC) == 0U) ||
(statp->options & RES_STAYOPEN) == 0U) {
res_nclose(statp);
}
if (statp->rhook) {
int done = 0, loops = 0;
do {
res_sendhookact act;
act = (*statp->rhook)(nsap, buf, buflen,
ans, anssiz, &resplen);
switch (act) {
case res_goahead:
case res_done:
done = 1;
break;
case res_nextns:
res_nclose(statp);
goto next_ns;
case res_modified:
/* give the hook another try */
if (++loops < 42) /*doug adams*/
break;
/*FALLTHROUGH*/
case res_error:
/*FALLTHROUGH*/
default:
goto fail;
}
} while (!done);
}
#ifdef USE_KQUEUE
_close(kq);
#endif
return (resplen);
next_ns: ;
} /*foreach ns*/
} /*foreach retry*/
res_nclose(statp);
#ifdef USE_KQUEUE
_close(kq);
#endif
if (!v_circuit) {
if (!gotsomewhere)
errno = ECONNREFUSED; /*%< no nameservers found */
else
errno = ETIMEDOUT; /*%< no answer obtained */
} else
errno = terrno;
return (-1);
fail:
res_nclose(statp);
#ifdef USE_KQUEUE
_close(kq);
#endif
return (-1);
}
/* Private */
static int
get_salen(sa)
const struct sockaddr *sa;
{
#ifdef HAVE_SA_LEN
/* There are people do not set sa_len. Be forgiving to them. */
if (sa->sa_len)
return (sa->sa_len);
#endif
if (sa->sa_family == AF_INET)
return (sizeof(struct sockaddr_in));
else if (sa->sa_family == AF_INET6)
return (sizeof(struct sockaddr_in6));
else
return (0); /*%< unknown, die on connect */
}
/*%
* pick appropriate nsaddr_list for use. see res_init() for initialization.
*/
static struct sockaddr *
get_nsaddr(statp, n)
res_state statp;
size_t n;
{
if (!statp->nsaddr_list[n].sin_family && EXT(statp).ext) {
/*
* - EXT(statp).ext->nsaddrs[n] holds an address that is larger
* than struct sockaddr, and
* - user code did not update statp->nsaddr_list[n].
*/
return (struct sockaddr *)(void *)&EXT(statp).ext->nsaddrs[n];
} else {
/*
* - user code updated statp->nsaddr_list[n], or
* - statp->nsaddr_list[n] has the same content as
* EXT(statp).ext->nsaddrs[n].
*/
return (struct sockaddr *)(void *)&statp->nsaddr_list[n];
}
}
static int
send_vc(res_state statp,
const u_char *buf, int buflen, u_char *ans, int anssiz,
int *terrno, int ns)
{
const HEADER *hp = (const HEADER *) buf;
HEADER *anhp = (HEADER *) ans;
struct sockaddr *nsap;
int nsaplen;
int truncating, connreset, resplen, n;
struct iovec iov[2];
u_short len;
u_char *cp;
void *tmp;
+#ifdef SO_NOSIGPIPE
+ int on = 1;
+#endif
nsap = get_nsaddr(statp, ns);
nsaplen = get_salen(nsap);
connreset = 0;
same_ns:
truncating = 0;
/* Are we still talking to whom we want to talk to? */
if (statp->_vcsock >= 0 && (statp->_flags & RES_F_VC) != 0) {
struct sockaddr_storage peer;
ISC_SOCKLEN_T size = sizeof peer;
if (_getpeername(statp->_vcsock,
(struct sockaddr *)&peer, &size) < 0 ||
!sock_eq((struct sockaddr *)&peer, nsap)) {
res_nclose(statp);
statp->_flags &= ~RES_F_VC;
}
}
if (statp->_vcsock < 0 || (statp->_flags & RES_F_VC) == 0) {
if (statp->_vcsock >= 0)
res_nclose(statp);
statp->_vcsock = _socket(nsap->sa_family, SOCK_STREAM, 0);
#if !defined(USE_POLL) && !defined(USE_KQUEUE)
if (statp->_vcsock > highestFD) {
res_nclose(statp);
errno = ENOTSOCK;
}
#endif
if (statp->_vcsock < 0) {
switch (errno) {
case EPROTONOSUPPORT:
#ifdef EPFNOSUPPORT
case EPFNOSUPPORT:
#endif
case EAFNOSUPPORT:
Perror(statp, stderr, "socket(vc)", errno);
return (0);
default:
*terrno = errno;
Perror(statp, stderr, "socket(vc)", errno);
return (-1);
}
}
+#ifdef SO_NOSIGPIPE
+ /*
+ * Disable generation of SIGPIPE when writing to a closed
+ * socket. Write should return -1 and set errno to EPIPE
+ * instead.
+ *
+ * Push on even if setsockopt(SO_NOSIGPIPE) fails.
+ */
+ (void)_setsockopt(statp->_vcsock, SOL_SOCKET, SO_NOSIGPIPE, &on,
+ sizeof(on));
+#endif
errno = 0;
if (_connect(statp->_vcsock, nsap, nsaplen) < 0) {
*terrno = errno;
Aerror(statp, stderr, "connect/vc", errno, nsap,
nsaplen);
res_nclose(statp);
return (0);
}
statp->_flags |= RES_F_VC;
}
/*
* Send length & message
*/
ns_put16((u_short)buflen, (u_char*)&len);
iov[0] = evConsIovec(&len, INT16SZ);
DE_CONST(buf, tmp);
iov[1] = evConsIovec(tmp, buflen);
if (_writev(statp->_vcsock, iov, 2) != (INT16SZ + buflen)) {
*terrno = errno;
Perror(statp, stderr, "write failed", errno);
res_nclose(statp);
return (0);
}
/*
* Receive length & response
*/
read_len:
cp = ans;
len = INT16SZ;
while ((n = _read(statp->_vcsock, (char *)cp, (int)len)) > 0) {
cp += n;
if ((len -= n) == 0)
break;
}
if (n <= 0) {
*terrno = errno;
Perror(statp, stderr, "read failed", errno);
res_nclose(statp);
/*
* A long running process might get its TCP
* connection reset if the remote server was
* restarted. Requery the server instead of
* trying a new one. When there is only one
* server, this means that a query might work
* instead of failing. We only allow one reset
* per query to prevent looping.
*/
if (*terrno == ECONNRESET && !connreset) {
connreset = 1;
res_nclose(statp);
goto same_ns;
}
res_nclose(statp);
return (0);
}
resplen = ns_get16(ans);
if (resplen > anssiz) {
Dprint(statp->options & RES_DEBUG,
(stdout, ";; response truncated\n")
);
truncating = 1;
len = anssiz;
} else
len = resplen;
if (len < HFIXEDSZ) {
/*
* Undersized message.
*/
Dprint(statp->options & RES_DEBUG,
(stdout, ";; undersized: %d\n", len));
*terrno = EMSGSIZE;
res_nclose(statp);
return (0);
}
cp = ans;
while (len != 0 &&
(n = _read(statp->_vcsock, (char *)cp, (int)len)) > 0) {
cp += n;
len -= n;
}
if (n <= 0) {
*terrno = errno;
Perror(statp, stderr, "read(vc)", errno);
res_nclose(statp);
return (0);
}
if (truncating) {
/*
* Flush rest of answer so connection stays in synch.
*/
anhp->tc = 1;
len = resplen - anssiz;
while (len != 0) {
char junk[PACKETSZ];
n = _read(statp->_vcsock, junk,
(len > sizeof junk) ? sizeof junk : len);
if (n > 0)
len -= n;
else
break;
}
}
/*
* If the calling applicating has bailed out of
* a previous call and failed to arrange to have
* the circuit closed or the server has got
* itself confused, then drop the packet and
* wait for the correct one.
*/
if (hp->id != anhp->id) {
DprintQ((statp->options & RES_DEBUG) ||
(statp->pfcode & RES_PRF_REPLY),
(stdout, ";; old answer (unexpected):\n"),
ans, (resplen > anssiz) ? anssiz: resplen);
goto read_len;
}
/*
* All is well, or the error is fatal. Signal that the
* next nameserver ought not be tried.
*/
return (resplen);
}
static int
send_dg(res_state statp,
#ifdef USE_KQUEUE
int kq,
#endif
const u_char *buf, int buflen, u_char *ans,
- int anssiz, int *terrno, int ns, int try, int *v_circuit,
+ int anssiz, int *terrno, int ns, int tries, int *v_circuit,
int *gotsomewhere)
{
const HEADER *hp = (const HEADER *) buf;
HEADER *anhp = (HEADER *) ans;
const struct sockaddr *nsap;
int nsaplen;
struct timespec now, timeout, finish;
struct sockaddr_storage from;
ISC_SOCKLEN_T fromlen;
int resplen, seconds, n, s;
#ifdef USE_KQUEUE
struct kevent kv;
#else
#ifdef USE_POLL
int polltimeout;
struct pollfd pollfd;
#else
fd_set dsmask;
#endif
#endif
nsap = get_nsaddr(statp, ns);
nsaplen = get_salen(nsap);
if (EXT(statp).nssocks[ns] == -1) {
EXT(statp).nssocks[ns] = _socket(nsap->sa_family,
SOCK_DGRAM, 0);
#if !defined(USE_POLL) && !defined(USE_KQUEUE)
if (EXT(statp).nssocks[ns] > highestFD) {
res_nclose(statp);
errno = ENOTSOCK;
}
#endif
if (EXT(statp).nssocks[ns] < 0) {
switch (errno) {
case EPROTONOSUPPORT:
#ifdef EPFNOSUPPORT
case EPFNOSUPPORT:
#endif
case EAFNOSUPPORT:
Perror(statp, stderr, "socket(dg)", errno);
return (0);
default:
*terrno = errno;
Perror(statp, stderr, "socket(dg)", errno);
return (-1);
}
}
#ifndef CANNOT_CONNECT_DGRAM
/*
* On a 4.3BSD+ machine (client and server,
* actually), sending to a nameserver datagram
* port with no nameserver will cause an
* ICMP port unreachable message to be returned.
* If our datagram socket is "connected" to the
* server, we get an ECONNREFUSED error on the next
* socket operation, and select returns if the
* error message is received. We can thus detect
* the absence of a nameserver without timing out.
*
* When the option "insecure1" is specified, we'd
* rather expect to see responses from an "unknown"
* address. In order to let the kernel accept such
* responses, do not connect the socket here.
* XXX: or do we need an explicit option to disable
* connecting?
*/
if (!(statp->options & RES_INSECURE1) &&
_connect(EXT(statp).nssocks[ns], nsap, nsaplen) < 0) {
Aerror(statp, stderr, "connect(dg)", errno, nsap,
nsaplen);
res_nclose(statp);
return (0);
}
#endif /* !CANNOT_CONNECT_DGRAM */
Dprint(statp->options & RES_DEBUG,
(stdout, ";; new DG socket\n"))
}
s = EXT(statp).nssocks[ns];
#ifndef CANNOT_CONNECT_DGRAM
if (statp->options & RES_INSECURE1) {
if (_sendto(s,
(const char*)buf, buflen, 0, nsap, nsaplen) != buflen) {
Aerror(statp, stderr, "sendto", errno, nsap, nsaplen);
res_nclose(statp);
return (0);
}
} else if (send(s, (const char*)buf, buflen, 0) != buflen) {
Perror(statp, stderr, "send", errno);
res_nclose(statp);
return (0);
}
#else /* !CANNOT_CONNECT_DGRAM */
if (_sendto(s, (const char*)buf, buflen, 0, nsap, nsaplen) != buflen)
{
Aerror(statp, stderr, "sendto", errno, nsap, nsaplen);
res_nclose(statp);
return (0);
}
#endif /* !CANNOT_CONNECT_DGRAM */
/*
* Wait for reply.
*/
- seconds = (statp->retrans << try);
+ seconds = (statp->retrans << tries);
if (ns > 0)
seconds /= statp->nscount;
if (seconds <= 0)
seconds = 1;
now = evNowTime();
timeout = evConsTime(seconds, 0);
finish = evAddTime(now, timeout);
goto nonow;
wait:
now = evNowTime();
nonow:
#ifndef USE_POLL
if (evCmpTime(finish, now) > 0)
timeout = evSubTime(finish, now);
else
timeout = evConsTime(0, 0);
#ifdef USE_KQUEUE
EV_SET(&kv, s, EVFILT_READ, EV_ADD | EV_ONESHOT, 0, 0, 0);
n = _kevent(kq, &kv, 1, &kv, 1, &timeout);
#else
FD_ZERO(&dsmask);
FD_SET(s, &dsmask);
n = pselect(s + 1, &dsmask, NULL, NULL, &timeout, NULL);
#endif
#else
timeout = evSubTime(finish, now);
if (timeout.tv_sec < 0)
timeout = evConsTime(0, 0);
polltimeout = 1000*timeout.tv_sec +
timeout.tv_nsec/1000000;
pollfd.fd = s;
pollfd.events = POLLRDNORM;
n = poll(&pollfd, 1, polltimeout);
#endif /* USE_POLL */
if (n == 0) {
Dprint(statp->options & RES_DEBUG, (stdout, ";; timeout\n"));
*gotsomewhere = 1;
return (0);
}
if (n < 0) {
if (errno == EINTR)
goto wait;
#ifdef USE_KQUEUE
Perror(statp, stderr, "kevent", errno);
#else
#ifndef USE_POLL
Perror(statp, stderr, "select", errno);
#else
Perror(statp, stderr, "poll", errno);
#endif /* USE_POLL */
#endif
res_nclose(statp);
return (0);
}
#ifdef USE_KQUEUE
if (kv.ident != s)
goto wait;
#endif
errno = 0;
fromlen = sizeof(from);
resplen = _recvfrom(s, (char*)ans, anssiz,0,
(struct sockaddr *)&from, &fromlen);
if (resplen <= 0) {
Perror(statp, stderr, "recvfrom", errno);
res_nclose(statp);
return (0);
}
*gotsomewhere = 1;
if (resplen < HFIXEDSZ) {
/*
* Undersized message.
*/
Dprint(statp->options & RES_DEBUG,
(stdout, ";; undersized: %d\n",
resplen));
*terrno = EMSGSIZE;
res_nclose(statp);
return (0);
}
if (hp->id != anhp->id) {
/*
* response from old query, ignore it.
* XXX - potential security hazard could
* be detected here.
*/
DprintQ((statp->options & RES_DEBUG) ||
(statp->pfcode & RES_PRF_REPLY),
(stdout, ";; old answer:\n"),
ans, (resplen > anssiz) ? anssiz : resplen);
goto wait;
}
if (!(statp->options & RES_INSECURE1) &&
!res_ourserver_p(statp, (struct sockaddr *)&from)) {
/*
* response from wrong server? ignore it.
* XXX - potential security hazard could
* be detected here.
*/
DprintQ((statp->options & RES_DEBUG) ||
(statp->pfcode & RES_PRF_REPLY),
(stdout, ";; not our server:\n"),
ans, (resplen > anssiz) ? anssiz : resplen);
goto wait;
}
#ifdef RES_USE_EDNS0
if (anhp->rcode == FORMERR && (statp->options & RES_USE_EDNS0) != 0U) {
/*
* Do not retry if the server do not understand EDNS0.
* The case has to be captured here, as FORMERR packet do not
* carry query section, hence res_queriesmatch() returns 0.
*/
DprintQ(statp->options & RES_DEBUG,
(stdout, "server rejected query with EDNS0:\n"),
ans, (resplen > anssiz) ? anssiz : resplen);
/* record the error */
statp->_flags |= RES_F_EDNS0ERR;
res_nclose(statp);
return (0);
}
#endif
if (!(statp->options & RES_INSECURE2) &&
!res_queriesmatch(buf, buf + buflen,
ans, ans + anssiz)) {
/*
* response contains wrong query? ignore it.
* XXX - potential security hazard could
* be detected here.
*/
DprintQ((statp->options & RES_DEBUG) ||
(statp->pfcode & RES_PRF_REPLY),
(stdout, ";; wrong query name:\n"),
ans, (resplen > anssiz) ? anssiz : resplen);
goto wait;
}
if (anhp->rcode == SERVFAIL ||
anhp->rcode == NOTIMP ||
anhp->rcode == REFUSED) {
DprintQ(statp->options & RES_DEBUG,
(stdout, "server rejected query:\n"),
ans, (resplen > anssiz) ? anssiz : resplen);
res_nclose(statp);
/* don't retry if called from dig */
if (!statp->pfcode)
return (0);
}
if (!(statp->options & RES_IGNTC) && anhp->tc) {
/*
* To get the rest of answer,
* use TCP with same server.
*/
Dprint(statp->options & RES_DEBUG,
(stdout, ";; truncated answer\n"));
*v_circuit = 1;
res_nclose(statp);
return (1);
}
/*
* All is well, or the error is fatal. Signal that the
* next nameserver ought not be tried.
*/
return (resplen);
}
static void
Aerror(const res_state statp, FILE *file, const char *string, int error,
const struct sockaddr *address, int alen)
{
int save = errno;
char hbuf[NI_MAXHOST];
char sbuf[NI_MAXSERV];
alen = alen;
if ((statp->options & RES_DEBUG) != 0U) {
if (getnameinfo(address, alen, hbuf, sizeof(hbuf),
sbuf, sizeof(sbuf), niflags)) {
strncpy(hbuf, "?", sizeof(hbuf) - 1);
hbuf[sizeof(hbuf) - 1] = '\0';
strncpy(sbuf, "?", sizeof(sbuf) - 1);
sbuf[sizeof(sbuf) - 1] = '\0';
}
fprintf(file, "res_send: %s ([%s].%s): %s\n",
string, hbuf, sbuf, strerror(error));
}
errno = save;
}
static void
Perror(const res_state statp, FILE *file, const char *string, int error) {
int save = errno;
if ((statp->options & RES_DEBUG) != 0U)
fprintf(file, "res_send: %s: %s\n",
string, strerror(error));
errno = save;
}
static int
sock_eq(struct sockaddr *a, struct sockaddr *b) {
struct sockaddr_in *a4, *b4;
struct sockaddr_in6 *a6, *b6;
if (a->sa_family != b->sa_family)
return 0;
switch (a->sa_family) {
case AF_INET:
a4 = (struct sockaddr_in *)a;
b4 = (struct sockaddr_in *)b;
return a4->sin_port == b4->sin_port &&
a4->sin_addr.s_addr == b4->sin_addr.s_addr;
case AF_INET6:
a6 = (struct sockaddr_in6 *)a;
b6 = (struct sockaddr_in6 *)b;
return a6->sin6_port == b6->sin6_port &&
#ifdef HAVE_SIN6_SCOPE_ID
a6->sin6_scope_id == b6->sin6_scope_id &&
#endif
IN6_ARE_ADDR_EQUAL(&a6->sin6_addr, &b6->sin6_addr);
default:
return 0;
}
}
#if defined(NEED_PSELECT) && !defined(USE_POLL) && !defined(USE_KQUEUE)
/* XXX needs to move to the porting library. */
static int
pselect(int nfds, void *rfds, void *wfds, void *efds,
struct timespec *tsp, const sigset_t *sigmask)
{
struct timeval tv, *tvp;
sigset_t sigs;
int n;
if (tsp) {
tvp = &tv;
tv = evTimeVal(*tsp);
} else
tvp = NULL;
if (sigmask)
sigprocmask(SIG_SETMASK, sigmask, &sigs);
n = select(nfds, rfds, wfds, efds, tvp);
if (sigmask)
sigprocmask(SIG_SETMASK, &sigs, NULL);
if (tsp)
*tsp = evTimeSpec(tv);
return (n);
}
#endif
Index: projects/arpv2_merge_1/sbin/atacontrol/atacontrol.8
===================================================================
--- projects/arpv2_merge_1/sbin/atacontrol/atacontrol.8 (revision 186114)
+++ projects/arpv2_merge_1/sbin/atacontrol/atacontrol.8 (revision 186115)
@@ -1,374 +1,379 @@
.\"
.\" Copyright (c) 2000,2001,2002 Søren Schmidt
.\" All rights reserved.
.\"
.\" Redistribution and use in source and binary forms, with or without
.\" modification, are permitted provided that the following conditions
.\" are met:
.\" 1. Redistributions of source code must retain the above copyright
.\" notice, this list of conditions and the following disclaimer.
.\" 2. Redistributions in binary form must reproduce the above copyright
.\" notice, this list of conditions and the following disclaimer in the
.\" documentation and/or other materials provided with the distribution.
.\"
.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
.\" SUCH DAMAGE.
.\"
.\" $FreeBSD$
.\"
-.Dd June 25, 2008
+.Dd December 14, 2008
.Dt ATACONTROL 8
.Os
.Sh NAME
.Nm atacontrol
.Nd ATA device driver control program
.Sh SYNOPSIS
.Nm
.Aq Ar command
.Ar args
.Pp
.Nm
.Ic attach
.Ar channel
.Nm
.Ic detach
.Ar channel
.Nm
.Ic reinit
.Ar channel
.Nm
.Ic create
.Ar type Oo Ar interleave Oc Ar disk0 ... diskN
.Nm
.Ic delete
.Ar raid
.Nm
.Ic addspare
.Ar raid disk
.Nm
.Ic rebuild
.Ar raid
.Nm
.Ic status
.Ar raid
.Nm
.Ic mode
.Ar device
+.Op Ar mode
.Nm
.Ic info
.Ar channel
.Nm
.Ic cap
.Ar device
.Nm
.Ic spindown
.Ar device
.Op Ar seconds
.Nm
.Ic list
.Sh DESCRIPTION
The
.Nm
utility is a control program that provides the user access and control to the
.Fx
.Xr ata 4
subsystem.
.Pp
The
.Nm
utility
can cause severe system crashes and loss of data if used improperly.
Please
exercise caution when using this command!
.Pp
The
.Ar channel
argument is the ATA channel device (e.g., ata0) on which to operate.
The following commands are supported:
-.Bl -tag -width "rebuild"
+.Bl -tag -width ".Ic addspare"
.It Ic attach
Attach an ATA
.Ar channel .
Devices on the channel are probed and attached as
is done on boot.
.It Ic detach
Detach an ATA
.Ar channel .
Devices on the channel are removed from the kernel,
and all outstanding transfers etc.\& are returned back to the system marked
as failed.
.It Ic reinit
Reinitialize an ATA
.Ar channel .
Both devices on the channel are reset and
initialized to the parameters the ATA driver has stored internally.
Devices that have gone bad and no longer respond to the probe, or devices
that have physically been removed, are removed from the kernel.
Likewise are devices that show up during a reset, probed and attached.
.It Ic create
Create a
.Ar type
ATA RAID.
The type can be
.Cm RAID0
(stripe),
.Cm RAID1
(mirror),
.Cm RAID0+1 ,
.Cm SPAN
or
.Cm JBOD .
In case the RAID has a
.Cm RAID0
component,
the
.Ar interleave
must be specified in number of sectors.
The RAID will be created
of the individual disks named
.Bk -words
.Ar disk0 ... diskN .
.Ek
.Pp
Although the ATA driver allows for creating an ATA RAID on disks with any
controller, there are restrictions.
It is only possible to boot on
an array if it is either located on a
.Dq real
ATA RAID controller like
the Promise or Highpoint controllers, or if the RAID declared is of
.Cm RAID1
or
.Cm SPAN
type; in case of a
.Cm SPAN ,
the partition to boot must
reside on the first disk in the SPAN.
.It Ic delete
Delete a RAID array on a RAID capable ATA controller.
.It Ic addspare
Add a spare disk to an existing RAID.
.It Ic rebuild
Rebuild a RAID1 array on a RAID capable ATA controller.
.It Ic status
Get the status of an ATA RAID.
.It Ic mode
-Without the mode argument, the current transfer modes of the
+Without the
+.Ar mode
+argument, the current transfer mode of the
device are printed.
-If the mode argument is given, the ATA driver
+If the
+.Ar mode
+argument is given, the ATA driver
is asked to change the transfer mode to the one given.
The ATA driver
will reject modes that are not supported by the hardware.
Modes are given like
.Dq Li PIO3 ,
.Dq Li udma2 ,
.Dq Li udma100 ,
case does not matter.
.Pp
Currently supported modes are:
.Cm PIO0 , PIO1 , PIO2 , PIO3 , PIO4 ,
.Cm WDMA2 ,
.Cm UDMA2
(alias
.Cm UDMA33 ) ,
.Cm UDMA4
(alias
.Cm UDMA66 ) ,
.Cm UDMA5
(alias
.Cm UDMA100 )
and
.Cm UDMA6
(alias
.Cm UDMA133 ) .
-The device name and manufacture/version strings are shown.
.It Ic cap
Show detailed info about the device on
.Ar device .
.It Ic spindown
Set or report timeout after which the
-.Ar device
+.Ar device
will be spun down.
To arm the timeout the device needs at least one more request after
setting the timeout.
To disable spindown, set the timeout to zero.
No further actions are needed in this case.
.It Ic info
Show info about the attached devices on the
.Ar channel .
+The device name and manufacture/version strings are shown.
.It Ic list
Show info about all attached devices on all active controllers.
.El
.Sh EXAMPLES
To get information on devices attached to a channel,
use the command line:
.Pp
.Dl "atacontrol info ata0"
.Pp
To see the devices' current access modes, use the command line:
.Pp
.Dl "atacontrol mode ad0"
.Pp
which results in the modes of the devices being displayed as a string
like this:
.Pp
.Dl "current mode = UDMA100"
.Pp
You can set the mode with
.Nm
and a string like the above,
for example:
.Pp
.Dl "atacontrol mode ad0 PIO4"
.Pp
The new modes are set as soon as the
.Nm
command returns.
.Pp
The atacontrol command can also be used to create purely software
RAID arrays in systems that do NOT have a "real" hardware RAID card
such as a Highpoint or Promise card.
A common scenario is a 1U server such as the HP DL320 G4 or G5.
These servers contain a SATA controller that has 2 channels that can
contain 2 disks per channel, but the servers are wired to only place
a single SATA drive on each channel.
These servers do have a "pseudo" RAID BIOS but it uses a proprietary
format that is not compatible with the ata driver, and thus their
RAID bios must be switched off.
Another common scenario would be a Promise UDMA100 controller card
that did not contain the Fasttrack RAID BIOS, but did contain 2
UDMA channels.
1 disk would be attached to one channel and the other disk would be
attached to the other channel.
It is NOT recommended to create such arrays on a primary/secondary
pair on a SINGLE channel since the throughput of the mirror would be
severely compromised, the ability to rebuild the array in the event
of a disk failure would be greatly complicated, and if a disk
controller electronics failed it could wedge the channel and take
both disks in the mirror offline.
(which would defeat the purpose of having a mirror in the first place)
.Pp
A quick and dirty way to create such a mirrored array on a new
system is to boot off the FreeBSD install CD, do a minimal scratch
install, abort out of the post install questions, and at the command
line issue the command:
.Pp
.Dl "atacontrol create RAID1 ad4 ad6"
.Pp
then immediately issue a reboot and boot from the installation CD
again, and during the installation, you will now see "ar0" listed
as a disk to install on, and install on that instead of ad4, ad6, etc.
.Pp
To get information about the status of a RAID array in the system
use the command line:
.Pp
.Dl "atacontrol status ar0"
.Pp
A typical output showing good health on a RAID array might be as
follows:
.Pp
.Dl "ar0: ATA RAID1 subdisks: ad4 ad6 status: READY"
.Pp
If a disk drive in a RAID1 array dies the system will mark the disk
in a DOWN state and change the array status to DEGRADED.
This can ALSO happen in rare instances due to a power fluctuation or
other event causing the system to not shutdown properly.
In that case the output will look like the following:
.Pp
.Dl "ar0: ATA RAID1 subdisks: ad4 DOWN status: DEGRADED"
.Pp
For a mirrored RAID1 system the server WILL ALLOW you to remove a
dead SATA disk drive (if the drive is in a hot-swap tray) without
freezing up the system, so you can remove the disk and while you are
obtaining a replacement the server can run from the active disk.
The only caveat is that if the active disk is ad6, the system most
likely will NOT be able to be rebooted since most systems only
support booting from the first disk drive.
.Pp
To deactivate the DOWN disk ad6 to allow for it to be ejected, use
the following:
.Pp
.Dl "atacontrol detach ata3"
.Pp
then eject or remove the disk.
Note that this only works if the 2 disks in the mirror are on separate
channels (which is the standard setup for 1-U servers like the HP DL320).
When the new disk drive is obtained, make sure it is blank, then shut
the system down.
At this point, if the system has a RAID array card like a Highpoint or
Promise controller, you may then boot it into the BIOS of the card and use
the manufacturers RAID array rebuild utilities to rebuild the array.
.Pp
If the system has a pure software array and is not using a "real" ATA
RAID controller, then shut the system down, make sure that the disk
that was still working is moved to the bootable position (channel 0
or whatever the BIOS allows the system to boot from) and the blank disk
-is placed in the secondary position, then boot the system into
+is placed in the secondary position, then boot the system into
single-user mode and issue the command:
.Pp
.Dl "atacontrol addspare ar0 ad6"
.Dl "atacontrol rebuild ar0"
.Pp
If the disk drive did NOT fail and the RAID array became unmirrored due
to a software glitch or improper shutdown, then a slightly different
process must be followed.
Begin by issuing the detach command (this shows the detach for disk ad6,
the primary master on channel 3):
.Pp
.Dl "atacontrol detach ata3"
.Pp
then reboot the system into single-user mode.
(don't just init the system, reboot it so that both disks get probed)
You will probably see TWO mirrored RAID arrays appear during the boot
messages, ar0 and ar1.
Issue the command:
.Pp
.Dl "atacontrol delete ar1"
.Dl "atacontrol addspare ar0 ad6"
.Pp
Now a status command will show the array rebuilding.
.Pp
To spin down a disk after 30 minutes run
.Pp
.Dl "atacontrol spindown ad6 1800"
.Dl "dd if=/dev/ad6 of=/dev/null count=1"
.Pp
While any IO on the disk will arm the timer, using
.Xr dd 1
on the raw device will work in all cases, as when the disk is not
opened at all.
You can check the current setting with
.Pp
.Dl "atacontrol spindown ad6"
.Pp
You should not set a spindown timeout on a disk with
.Pa /
or syslog logging on it as the disk will be worn out spinning down and
up all the time.
.Sh SEE ALSO
.Xr ata 4
.Sh HISTORY
The
.Nm
utility first appeared in
.Fx 4.6 .
.Sh AUTHORS
.An -nosplit
The
.Nm
utility was written by
.An S\(/oren Schmidt
.Aq sos@FreeBSD.org .
.Pp
This manual page was written by
.An S\(/oren Schmidt
.Aq sos@FreeBSD.org .
Index: projects/arpv2_merge_1/sbin/devd/devd.cc
===================================================================
--- projects/arpv2_merge_1/sbin/devd/devd.cc (revision 186114)
+++ projects/arpv2_merge_1/sbin/devd/devd.cc (revision 186115)
@@ -1,965 +1,965 @@
/*-
* Copyright (c) 2002-2003 M. Warner Losh.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* DEVD control daemon.
*/
// TODO list:
// o devd.conf and devd man pages need a lot of help:
// - devd needs to document the unix domain socket
// - devd.conf needs more details on the supported statements.
#include
__FBSDID("$FreeBSD$");
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include
#include