10Sstevel@tonic-gate /* 2*11038SRao.Shoaib@Sun.COM * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 3*11038SRao.Shoaib@Sun.COM * Use is subject to license terms. 40Sstevel@tonic-gate */ 50Sstevel@tonic-gate 60Sstevel@tonic-gate /* 70Sstevel@tonic-gate * As of BIND 8.2.2, ISC (a) removed res_mkupdate(), res_update(), and 80Sstevel@tonic-gate * res_mkupdrec() from what they consider the supported interface. The 90Sstevel@tonic-gate * functions still exist, but their calling interface has changed, since 100Sstevel@tonic-gate * the ns_updrec structure has changed. 110Sstevel@tonic-gate * 120Sstevel@tonic-gate * It seems probable that res_mkupdate() etc. will return, though possibly 130Sstevel@tonic-gate * with other changes, in some future BIND release. In order to avoid 140Sstevel@tonic-gate * going to PSARC twice (once to remove the functions, and then again to 150Sstevel@tonic-gate * add them back), we retain the old interface as a wrapper around the 160Sstevel@tonic-gate * new one. 170Sstevel@tonic-gate */ 180Sstevel@tonic-gate 190Sstevel@tonic-gate #include <port_before.h> 200Sstevel@tonic-gate 210Sstevel@tonic-gate #include <malloc.h> 220Sstevel@tonic-gate #include <strings.h> 230Sstevel@tonic-gate #include <sys/types.h> 240Sstevel@tonic-gate #include <netinet/in.h> 250Sstevel@tonic-gate 26*11038SRao.Shoaib@Sun.COM /* get the Solaris ns_updrec before any renaming happens */ 27*11038SRao.Shoaib@Sun.COM #include <arpa/nameser.h> 28*11038SRao.Shoaib@Sun.COM 29*11038SRao.Shoaib@Sun.COM /* get the __ISC_ns_updrec */ 300Sstevel@tonic-gate #include <res_update.h> 31*11038SRao.Shoaib@Sun.COM 32*11038SRao.Shoaib@Sun.COM #include <port_after.h> 33*11038SRao.Shoaib@Sun.COM 34*11038SRao.Shoaib@Sun.COM /* un-rename ns_updrec and res_* functions so we can wrap them */ 350Sstevel@tonic-gate #undef ns_updrec 360Sstevel@tonic-gate #undef res_mkupdate 370Sstevel@tonic-gate #undef res_update 380Sstevel@tonic-gate #undef res_mkupdrec 390Sstevel@tonic-gate #undef res_freeupdrec 40*11038SRao.Shoaib@Sun.COM #undef res_nmkupdate 41*11038SRao.Shoaib@Sun.COM #undef res_nupdate 420Sstevel@tonic-gate 430Sstevel@tonic-gate void res_freeupdrec(ns_updrec *); 440Sstevel@tonic-gate 450Sstevel@tonic-gate static int 460Sstevel@tonic-gate old2new(ns_updrec *old, __ISC_ns_updrec *new) { 470Sstevel@tonic-gate 480Sstevel@tonic-gate if (old->r_dname != 0) { 490Sstevel@tonic-gate if ((new->r_dname = strdup(old->r_dname)) == 0) 500Sstevel@tonic-gate return (-1); 510Sstevel@tonic-gate } else { 520Sstevel@tonic-gate new->r_dname = 0; 530Sstevel@tonic-gate } 540Sstevel@tonic-gate 550Sstevel@tonic-gate new->r_glink.prev = 560Sstevel@tonic-gate new->r_glink.next = 570Sstevel@tonic-gate new->r_link.prev = 580Sstevel@tonic-gate new->r_link.next = 0; 590Sstevel@tonic-gate 600Sstevel@tonic-gate new->r_section = old->r_section; 610Sstevel@tonic-gate new->r_class = old->r_class; 620Sstevel@tonic-gate new->r_type = old->r_type; 630Sstevel@tonic-gate new->r_ttl = old->r_ttl; 640Sstevel@tonic-gate new->r_data = old->r_data; 650Sstevel@tonic-gate new->r_size = old->r_size; 660Sstevel@tonic-gate new->r_opcode = old->r_opcode; 670Sstevel@tonic-gate new->r_dp = old->r_dp; 680Sstevel@tonic-gate new->r_deldp = old->r_deldp; 690Sstevel@tonic-gate new->r_zone = old->r_zone; 700Sstevel@tonic-gate 710Sstevel@tonic-gate return (0); 720Sstevel@tonic-gate } 730Sstevel@tonic-gate 740Sstevel@tonic-gate 750Sstevel@tonic-gate static int 760Sstevel@tonic-gate new2old(__ISC_ns_updrec *new, ns_updrec *old) { 770Sstevel@tonic-gate /* XXX r_prev and r_next unchanged */ 780Sstevel@tonic-gate if (new->r_dname != 0) { 790Sstevel@tonic-gate if ((old->r_dname = strdup(new->r_dname)) == 0) 800Sstevel@tonic-gate return (-1); 810Sstevel@tonic-gate } else { 820Sstevel@tonic-gate old->r_dname = 0; 830Sstevel@tonic-gate } 840Sstevel@tonic-gate old->r_section = new->r_section; 850Sstevel@tonic-gate old->r_class = new->r_class; 860Sstevel@tonic-gate old->r_type = new->r_type; 870Sstevel@tonic-gate old->r_ttl = new->r_ttl; 880Sstevel@tonic-gate old->r_data = new->r_data; 890Sstevel@tonic-gate old->r_size = new->r_size; 900Sstevel@tonic-gate old->r_opcode = new->r_opcode; 910Sstevel@tonic-gate old->r_grpnext = 0; /* XXX */ 920Sstevel@tonic-gate old->r_dp = new->r_dp; 930Sstevel@tonic-gate old->r_deldp = new->r_deldp; 940Sstevel@tonic-gate old->r_zone = new->r_zone; 950Sstevel@tonic-gate 960Sstevel@tonic-gate return (0); 970Sstevel@tonic-gate } 980Sstevel@tonic-gate 990Sstevel@tonic-gate 1000Sstevel@tonic-gate static void 1010Sstevel@tonic-gate delete_list(__ISC_ns_updrec *list) { 1020Sstevel@tonic-gate 1030Sstevel@tonic-gate __ISC_ns_updrec *next; 1040Sstevel@tonic-gate 1050Sstevel@tonic-gate for (; list != 0; list = next) { 1060Sstevel@tonic-gate next = list->r_link.next; 1070Sstevel@tonic-gate __ISC_res_freeupdrec(list); 1080Sstevel@tonic-gate } 1090Sstevel@tonic-gate } 1100Sstevel@tonic-gate 1110Sstevel@tonic-gate 1120Sstevel@tonic-gate static __ISC_ns_updrec * 113*11038SRao.Shoaib@Sun.COM copy_list(ns_updrec *old, int do_glink) { 1140Sstevel@tonic-gate 1150Sstevel@tonic-gate __ISC_ns_updrec *list = 0, *r, *p; 1160Sstevel@tonic-gate 1170Sstevel@tonic-gate if (old == 0) 1180Sstevel@tonic-gate return (0); 1190Sstevel@tonic-gate 1200Sstevel@tonic-gate for (p = 0; old != 0; old = old->r_next, p = r) { 1210Sstevel@tonic-gate if ((r = calloc(1, sizeof (*r))) == 0 || 1220Sstevel@tonic-gate old2new(old, r) != 0) { 1230Sstevel@tonic-gate free(r); 1240Sstevel@tonic-gate delete_list(list); 1250Sstevel@tonic-gate return (0); 1260Sstevel@tonic-gate } 1270Sstevel@tonic-gate r->r_link.prev = p; 1280Sstevel@tonic-gate r->r_link.next = 0; 129*11038SRao.Shoaib@Sun.COM /* res_update and res_nupdate want r_glink set up like this */ 130*11038SRao.Shoaib@Sun.COM if (do_glink) { 131*11038SRao.Shoaib@Sun.COM r->r_glink.prev = p; 132*11038SRao.Shoaib@Sun.COM r->r_glink.next = 0; 133*11038SRao.Shoaib@Sun.COM } else { 134*11038SRao.Shoaib@Sun.COM r->r_glink.prev = (void *)-1; 135*11038SRao.Shoaib@Sun.COM r->r_glink.next = (void *)-1; 136*11038SRao.Shoaib@Sun.COM } 137*11038SRao.Shoaib@Sun.COM if (p != 0) { 1380Sstevel@tonic-gate p->r_link.next = r; 139*11038SRao.Shoaib@Sun.COM if (do_glink) { 140*11038SRao.Shoaib@Sun.COM p->r_glink.next = r; 141*11038SRao.Shoaib@Sun.COM } 142*11038SRao.Shoaib@Sun.COM } else { 1430Sstevel@tonic-gate list = r; 144*11038SRao.Shoaib@Sun.COM } 1450Sstevel@tonic-gate } 1460Sstevel@tonic-gate return (list); 1470Sstevel@tonic-gate } 1480Sstevel@tonic-gate 1490Sstevel@tonic-gate 1500Sstevel@tonic-gate int 151*11038SRao.Shoaib@Sun.COM res_mkupdate(ns_updrec *rrecp_in, uchar_t *buf, int length) { 1520Sstevel@tonic-gate 1530Sstevel@tonic-gate __ISC_ns_updrec *r; 1540Sstevel@tonic-gate int ret; 1550Sstevel@tonic-gate 156*11038SRao.Shoaib@Sun.COM if ((r = copy_list(rrecp_in, 1)) == 0) 1570Sstevel@tonic-gate return (-1); 1580Sstevel@tonic-gate 1590Sstevel@tonic-gate ret = __ISC_res_mkupdate(r, buf, length); 1600Sstevel@tonic-gate 1610Sstevel@tonic-gate delete_list(r); 1620Sstevel@tonic-gate 1630Sstevel@tonic-gate return (ret); 1640Sstevel@tonic-gate } 1650Sstevel@tonic-gate 166*11038SRao.Shoaib@Sun.COM int 167*11038SRao.Shoaib@Sun.COM res_nmkupdate(res_state statp, ns_updrec *rrecp_in, uchar_t *buf, int length) { 168*11038SRao.Shoaib@Sun.COM 169*11038SRao.Shoaib@Sun.COM __ISC_ns_updrec *r; 170*11038SRao.Shoaib@Sun.COM int ret; 171*11038SRao.Shoaib@Sun.COM 172*11038SRao.Shoaib@Sun.COM if ((r = copy_list(rrecp_in, 1)) == 0) 173*11038SRao.Shoaib@Sun.COM return (-1); 174*11038SRao.Shoaib@Sun.COM 175*11038SRao.Shoaib@Sun.COM ret = __ISC_res_nmkupdate(statp, r, buf, length); 176*11038SRao.Shoaib@Sun.COM 177*11038SRao.Shoaib@Sun.COM delete_list(r); 178*11038SRao.Shoaib@Sun.COM 179*11038SRao.Shoaib@Sun.COM return (ret); 180*11038SRao.Shoaib@Sun.COM } 181*11038SRao.Shoaib@Sun.COM 1820Sstevel@tonic-gate 1830Sstevel@tonic-gate int 1840Sstevel@tonic-gate res_update(ns_updrec *rrecp_in) { 1850Sstevel@tonic-gate 1860Sstevel@tonic-gate __ISC_ns_updrec *r; 1870Sstevel@tonic-gate int ret; 1880Sstevel@tonic-gate 189*11038SRao.Shoaib@Sun.COM if ((r = copy_list(rrecp_in, 0)) == 0) 1900Sstevel@tonic-gate return (-1); 1910Sstevel@tonic-gate 1920Sstevel@tonic-gate ret = __ISC_res_update(r); 1930Sstevel@tonic-gate 1940Sstevel@tonic-gate delete_list(r); 1950Sstevel@tonic-gate 1960Sstevel@tonic-gate return (ret); 1970Sstevel@tonic-gate } 1980Sstevel@tonic-gate 199*11038SRao.Shoaib@Sun.COM int 200*11038SRao.Shoaib@Sun.COM res_nupdate(res_state statp, ns_updrec *rrecp_in, ns_tsig_key *key) { 201*11038SRao.Shoaib@Sun.COM 202*11038SRao.Shoaib@Sun.COM __ISC_ns_updrec *r; 203*11038SRao.Shoaib@Sun.COM int ret; 204*11038SRao.Shoaib@Sun.COM 205*11038SRao.Shoaib@Sun.COM if ((r = copy_list(rrecp_in, 0)) == 0) 206*11038SRao.Shoaib@Sun.COM return (-1); 207*11038SRao.Shoaib@Sun.COM 208*11038SRao.Shoaib@Sun.COM ret = __ISC_res_nupdate(statp, r, key); 209*11038SRao.Shoaib@Sun.COM 210*11038SRao.Shoaib@Sun.COM delete_list(r); 211*11038SRao.Shoaib@Sun.COM 212*11038SRao.Shoaib@Sun.COM return (ret); 213*11038SRao.Shoaib@Sun.COM } 214*11038SRao.Shoaib@Sun.COM 2150Sstevel@tonic-gate 2160Sstevel@tonic-gate 2170Sstevel@tonic-gate ns_updrec * 2180Sstevel@tonic-gate res_mkupdrec(int section, const char *dname, uint_t class, uint_t type, 2190Sstevel@tonic-gate uint_t ttl) { 2200Sstevel@tonic-gate 2210Sstevel@tonic-gate __ISC_ns_updrec *n; 2220Sstevel@tonic-gate ns_updrec *o; 2230Sstevel@tonic-gate 2240Sstevel@tonic-gate n = __ISC_res_mkupdrec(section, dname, class, type, ttl); 2250Sstevel@tonic-gate if (n == 0) 2260Sstevel@tonic-gate return (0); 2270Sstevel@tonic-gate 2280Sstevel@tonic-gate if ((o = calloc(1, sizeof (*o))) != 0) { 2290Sstevel@tonic-gate if (new2old(n, o) != 0) { 2300Sstevel@tonic-gate res_freeupdrec(o); 2310Sstevel@tonic-gate o = 0; 2320Sstevel@tonic-gate } 2330Sstevel@tonic-gate } 2340Sstevel@tonic-gate 2350Sstevel@tonic-gate __ISC_res_freeupdrec(n); 2360Sstevel@tonic-gate 2370Sstevel@tonic-gate return (o); 2380Sstevel@tonic-gate } 2390Sstevel@tonic-gate 2400Sstevel@tonic-gate 2410Sstevel@tonic-gate void 2420Sstevel@tonic-gate res_freeupdrec(ns_updrec *rrecp) { 2430Sstevel@tonic-gate if (rrecp == 0) 2440Sstevel@tonic-gate return; 2450Sstevel@tonic-gate /* Note: freeing r_dp is the caller's responsibility. */ 2460Sstevel@tonic-gate if (rrecp->r_dname != NULL) 2470Sstevel@tonic-gate free(rrecp->r_dname); 2480Sstevel@tonic-gate free(rrecp); 2490Sstevel@tonic-gate } 250