Home | History | Annotate | Line # | Download | only in ypxfr
ypxfr.c revision 1.15.8.1
      1  1.15.8.1   bouyer /*	$NetBSD: ypxfr.c,v 1.15.8.1 2011/02/16 21:07:21 bouyer Exp $	*/
      2       1.1  thorpej 
      3       1.1  thorpej /*
      4       1.1  thorpej  * Copyright (c) 1994 Mats O Jansson <moj (at) stacken.kth.se>
      5       1.1  thorpej  * All rights reserved.
      6       1.1  thorpej  *
      7       1.1  thorpej  * Redistribution and use in source and binary forms, with or without
      8       1.1  thorpej  * modification, are permitted provided that the following conditions
      9       1.1  thorpej  * are met:
     10       1.1  thorpej  * 1. Redistributions of source code must retain the above copyright
     11       1.1  thorpej  *    notice, this list of conditions and the following disclaimer.
     12       1.1  thorpej  * 2. Redistributions in binary form must reproduce the above copyright
     13       1.1  thorpej  *    notice, this list of conditions and the following disclaimer in the
     14       1.1  thorpej  *    documentation and/or other materials provided with the distribution.
     15       1.1  thorpej  *
     16       1.1  thorpej  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS
     17       1.1  thorpej  * OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
     18       1.1  thorpej  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
     19       1.1  thorpej  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
     20       1.1  thorpej  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
     21       1.1  thorpej  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
     22       1.1  thorpej  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
     23       1.1  thorpej  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
     24       1.1  thorpej  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
     25       1.1  thorpej  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
     26       1.1  thorpej  * SUCH DAMAGE.
     27       1.1  thorpej  */
     28       1.6    lukem 
     29       1.6    lukem #include <sys/cdefs.h>
     30       1.6    lukem #ifndef lint
     31  1.15.8.1   bouyer __RCSID("$NetBSD: ypxfr.c,v 1.15.8.1 2011/02/16 21:07:21 bouyer Exp $");
     32       1.6    lukem #endif
     33       1.1  thorpej 
     34      1.15    lukem #include <sys/param.h>
     35       1.1  thorpej #include <sys/types.h>
     36       1.1  thorpej #include <sys/stat.h>
     37       1.1  thorpej #include <sys/socket.h>
     38       1.1  thorpej 
     39       1.1  thorpej #include <netinet/in.h>
     40       1.1  thorpej #include <arpa/inet.h>
     41       1.1  thorpej 
     42       1.4  thorpej #include <err.h>
     43       1.1  thorpej #include <netdb.h>
     44       1.1  thorpej #include <string.h>
     45       1.1  thorpej #include <stdio.h>
     46       1.1  thorpej #include <stdlib.h>
     47       1.8  thorpej #include <syslog.h>
     48       1.1  thorpej #include <unistd.h>
     49       1.1  thorpej 
     50       1.1  thorpej #include <rpc/rpc.h>
     51       1.1  thorpej #include <rpc/xdr.h>
     52       1.1  thorpej #include <rpcsvc/yp_prot.h>
     53       1.1  thorpej #include <rpcsvc/ypclnt.h>
     54       1.1  thorpej 
     55       1.1  thorpej #include "yplib_host.h"
     56       1.1  thorpej #include "ypdb.h"
     57       1.1  thorpej #include "ypdef.h"
     58       1.1  thorpej 
     59       1.1  thorpej DBM	*db;
     60       1.1  thorpej 
     61  1.15.8.1   bouyer static	int yperr2yppush(int);
     62      1.12      wiz static	int ypxfr_foreach(int, char *, int, char *, int, char *);
     63       1.1  thorpej 
     64      1.12      wiz int	main(int, char *[]);
     65      1.12      wiz int	get_local_ordernum(char *, char *, u_int *);
     66      1.12      wiz int	get_remote_ordernum(CLIENT *, char *, char *, u_int, u_int *);
     67      1.12      wiz void	get_map(CLIENT *, char *, char *, struct ypall_callback *);
     68      1.15    lukem DBM	*create_db(char *, char *, char *, size_t);
     69      1.12      wiz int	install_db(char *, char *, char *);
     70      1.12      wiz int	unlink_db(char *, char *, char *);
     71      1.12      wiz int	add_order(DBM *, u_int);
     72      1.12      wiz int	add_master(CLIENT *, char *, char *, DBM *);
     73      1.12      wiz int	add_interdomain(CLIENT *, char *, char *, DBM *);
     74      1.12      wiz int	add_secure(CLIENT *, char *, char *, DBM *);
     75      1.12      wiz int	send_clear(CLIENT *);
     76      1.12      wiz int	send_reply(CLIENT *, int, int);
     77      1.12      wiz 
     78      1.12      wiz int
     79      1.12      wiz main(int argc, char **argv)
     80       1.1  thorpej {
     81       1.1  thorpej 	int need_usage = 0, cflag = 0, fflag = 0, Cflag = 0;
     82       1.1  thorpej 	int ch;
     83       1.1  thorpej 	char *domain;
     84       1.1  thorpej 	char *host = NULL;
     85       1.1  thorpej 	char *srcdomain = NULL;
     86       1.1  thorpej 	char *tid = NULL;
     87       1.1  thorpej 	char *prog = NULL;
     88       1.1  thorpej 	char *ipadd = NULL;
     89       1.1  thorpej 	char *port = NULL;
     90       1.1  thorpej 	char *map = NULL;
     91       1.1  thorpej 	u_int ordernum, new_ordernum;
     92       1.1  thorpej 	struct ypall_callback callback;
     93       1.1  thorpej 	CLIENT *client;
     94      1.15    lukem 	char temp_map[MAXPATHLEN];
     95       1.1  thorpej 	int status, xfr_status;
     96       1.1  thorpej 
     97       1.1  thorpej 	status = YPPUSH_SUCC;
     98       1.1  thorpej 	client = NULL;
     99       1.1  thorpej 
    100       1.1  thorpej 	if (yp_get_default_domain(&domain))
    101       1.1  thorpej 		errx(1, "can't get YP domain name");
    102       1.1  thorpej 
    103       1.1  thorpej 	while ((ch = getopt(argc, argv, "cd:fh:s:C:")) != -1) {
    104       1.1  thorpej 		switch (ch) {
    105       1.1  thorpej 		case 'c':
    106       1.1  thorpej 			cflag = 1;
    107       1.1  thorpej 			break;
    108       1.1  thorpej 
    109       1.1  thorpej 		case 'd':
    110       1.1  thorpej 			domain = optarg;
    111       1.1  thorpej 			break;
    112       1.1  thorpej 
    113       1.1  thorpej 		case 'f':
    114       1.1  thorpej 			fflag = 1;
    115       1.1  thorpej 			break;
    116       1.1  thorpej 
    117       1.1  thorpej 		case 'h':
    118       1.1  thorpej 			host = optarg;
    119       1.1  thorpej 			break;
    120       1.1  thorpej 
    121       1.1  thorpej 		case 's':
    122       1.1  thorpej 			srcdomain = optarg;
    123       1.1  thorpej 			break;
    124       1.1  thorpej 
    125       1.1  thorpej 		case 'C':
    126       1.2    chuck 			if (optind + 3 >= argc) {
    127       1.2    chuck 				need_usage = 1;
    128       1.2    chuck 				optind = argc;
    129       1.2    chuck 				break;
    130       1.2    chuck 			}
    131       1.1  thorpej 			Cflag = 1;
    132       1.1  thorpej 			tid = optarg;
    133       1.1  thorpej 			prog = argv[optind++];
    134       1.1  thorpej 			ipadd = argv[optind++];
    135       1.1  thorpej 			port = argv[optind++];
    136       1.1  thorpej 			break;
    137       1.1  thorpej 
    138       1.1  thorpej 		default:
    139       1.1  thorpej 			need_usage = 1;
    140       1.1  thorpej 		}
    141       1.1  thorpej 	}
    142       1.1  thorpej 	argc -= optind; argv += optind;
    143       1.1  thorpej 
    144       1.1  thorpej 	if (argc != 1)
    145       1.1  thorpej 		need_usage = 1;
    146       1.1  thorpej 
    147       1.1  thorpej 	map = argv[0];
    148       1.1  thorpej 
    149       1.1  thorpej 	if (need_usage) {
    150       1.1  thorpej 		status = YPPUSH_BADARGS;
    151       1.1  thorpej 		fprintf(stderr, "usage: %s [-cf] [-d domain] [-h host] %s\n",
    152      1.11      cgd 		   getprogname(),
    153      1.11      cgd 		   "[-s domain] [-C tid prog ipadd port] mapname");
    154  1.15.8.1   bouyer 		exit(1);
    155       1.1  thorpej 	}
    156       1.1  thorpej 
    157       1.8  thorpej #ifdef DEBUG
    158      1.10    lukem 	openlog("ypxfr", LOG_PID, LOG_DAEMON);
    159       1.1  thorpej 
    160       1.8  thorpej 	syslog(LOG_DEBUG, "ypxfr: Arguments:");
    161       1.8  thorpej 	syslog(LOG_DEBUG, "YP clear to local: %s", (cflag) ? "no" : "yes");
    162       1.8  thorpej 	syslog(LOG_DEBUG, "   Force transfer: %s", (fflag) ? "yes" : "no");
    163       1.8  thorpej 	syslog(LOG_DEBUG, "           domain: %s", domain);
    164       1.8  thorpej 	syslog(LOG_DEBUG, "             host: %s", host);
    165       1.8  thorpej 	syslog(LOG_DEBUG, "    source domain: %s", srcdomain);
    166       1.8  thorpej 	syslog(LOG_DEBUG, "          transid: %s", tid);
    167       1.8  thorpej 	syslog(LOG_DEBUG, "             prog: %s", prog);
    168       1.8  thorpej 	syslog(LOG_DEBUG, "             port: %s", port);
    169       1.8  thorpej 	syslog(LOG_DEBUG, "            ipadd: %s", ipadd);
    170       1.8  thorpej 	syslog(LOG_DEBUG, "              map: %s", map);
    171       1.8  thorpej #endif
    172       1.1  thorpej 
    173       1.1  thorpej 	if (fflag != 0)
    174       1.1  thorpej 		ordernum = 0;
    175       1.1  thorpej 	else {
    176       1.1  thorpej 		status = get_local_ordernum(domain, map, &ordernum);
    177       1.1  thorpej 		if (status < 0)
    178       1.1  thorpej 			goto punt;
    179       1.1  thorpej 	}
    180       1.1  thorpej 
    181      1.10    lukem #ifdef DEBUG
    182       1.8  thorpej         syslog(LOG_DEBUG, "Get Master");
    183      1.10    lukem #endif
    184       1.1  thorpej 
    185       1.1  thorpej 	if (host == NULL) {
    186       1.1  thorpej 		if (srcdomain == NULL)
    187       1.5    lukem 			status = yp_master(domain, map, &host);
    188       1.1  thorpej 	        else
    189       1.5    lukem 			status = yp_master(srcdomain, map, &host);
    190       1.1  thorpej 
    191       1.1  thorpej 		if (status == 0)
    192       1.1  thorpej 			status = YPPUSH_SUCC;
    193       1.1  thorpej 		else {
    194  1.15.8.1   bouyer 			status = YPPUSH_MADDR;
    195       1.1  thorpej 			goto punt;
    196       1.1  thorpej 		}
    197       1.1  thorpej 	}
    198       1.1  thorpej 
    199      1.10    lukem #ifdef DEBUG
    200       1.8  thorpej         syslog(LOG_DEBUG, "Connect host: %s", host);
    201      1.10    lukem #endif
    202       1.1  thorpej 
    203       1.5    lukem 	client = yp_bind_host(host, YPPROG, YPVERS, 0, 1);
    204       1.1  thorpej 
    205       1.5    lukem 	status = get_remote_ordernum(client, domain, map, ordernum,
    206       1.5    lukem 	    &new_ordernum);
    207       1.1  thorpej 
    208       1.1  thorpej 
    209       1.1  thorpej 	if (status == YPPUSH_SUCC) {
    210       1.1  thorpej 		/* Create temporary db */
    211      1.15    lukem 		db = create_db(domain, map, temp_map, sizeof(temp_map));
    212       1.1  thorpej 		if (db == NULL)
    213       1.1  thorpej 			status = YPPUSH_DBM;
    214       1.1  thorpej 
    215       1.1  thorpej 	  	/* Add ORDER */
    216       1.1  thorpej 		if (status > 0)
    217       1.1  thorpej 			status = add_order(db, new_ordernum);
    218       1.1  thorpej 
    219       1.1  thorpej 		/* Add MASTER */
    220       1.1  thorpej 		if (status > 0)
    221       1.1  thorpej 			status = add_master(client, domain, map, db);
    222       1.1  thorpej 
    223       1.1  thorpej 	        /* Add INTERDOMAIN */
    224       1.1  thorpej 		if (status > 0)
    225       1.1  thorpej 			status = add_interdomain(client, domain, map, db);
    226       1.1  thorpej 
    227       1.1  thorpej 	        /* Add SECURE */
    228       1.1  thorpej 		if (status > 0)
    229       1.1  thorpej 			status = add_secure(client, domain, map, db);
    230       1.1  thorpej 
    231       1.1  thorpej 		if (status > 0) {
    232       1.4  thorpej 			callback.foreach = ypxfr_foreach;
    233       1.1  thorpej 			get_map(client, domain, map, &callback);
    234       1.1  thorpej 		}
    235       1.1  thorpej 
    236       1.1  thorpej 		/* Close db */
    237       1.1  thorpej 		if (db != NULL)
    238       1.1  thorpej 			ypdb_close(db);
    239       1.1  thorpej 
    240       1.1  thorpej 		/* Rename db */
    241       1.1  thorpej 		if (status > 0)
    242      1.15    lukem 			status = install_db(domain, map, temp_map);
    243       1.1  thorpej 		else
    244  1.15.8.1   bouyer 			(void) unlink_db(domain, map, temp_map);
    245       1.1  thorpej 	}
    246       1.1  thorpej 
    247       1.1  thorpej  punt:
    248       1.1  thorpej 	xfr_status = status;
    249       1.1  thorpej 
    250       1.1  thorpej 	if (client != NULL)
    251       1.1  thorpej 		clnt_destroy(client);
    252       1.1  thorpej 
    253       1.1  thorpej 	/* YP_CLEAR */
    254       1.1  thorpej 	if (!cflag) {
    255       1.1  thorpej 		client = yp_bind_local(YPPROG, YPVERS);
    256       1.1  thorpej 		status = send_clear(client);
    257       1.1  thorpej 		clnt_destroy(client);
    258       1.1  thorpej 	}
    259       1.1  thorpej 
    260       1.1  thorpej 	if (Cflag > 0) {
    261       1.1  thorpej 		/* Send Response */
    262       1.1  thorpej 		client = yp_bind_host(ipadd, atoi(prog), 1, atoi(port), 0);
    263       1.1  thorpej 		status = send_reply(client, xfr_status, atoi(tid));
    264       1.1  thorpej 		clnt_destroy(client);
    265       1.1  thorpej 	}
    266       1.1  thorpej 
    267       1.1  thorpej 	exit (0);
    268       1.1  thorpej }
    269       1.1  thorpej 
    270  1.15.8.1   bouyer /*
    271  1.15.8.1   bouyer  * yperr2yppush: convert error codes from functions like yp_order_host,
    272  1.15.8.1   bouyer  * yp_master_host, and yp_match_host into YPPUSH rpc status values.
    273  1.15.8.1   bouyer  */
    274  1.15.8.1   bouyer static int
    275  1.15.8.1   bouyer yperr2yppush(int yperr) {
    276  1.15.8.1   bouyer 	switch (yperr) {
    277  1.15.8.1   bouyer 	case YPERR_DOMAIN:
    278  1.15.8.1   bouyer 		return(YPPUSH_NODOM);
    279  1.15.8.1   bouyer 	case YPERR_MAP:
    280  1.15.8.1   bouyer 		return(YPPUSH_NOMAP);
    281  1.15.8.1   bouyer 	case YPERR_KEY:
    282  1.15.8.1   bouyer 		return(YPPUSH_YPERR);
    283  1.15.8.1   bouyer 	case YPERR_BADDB:
    284  1.15.8.1   bouyer 		return(YPPUSH_YPERR);
    285  1.15.8.1   bouyer 	}
    286  1.15.8.1   bouyer 
    287  1.15.8.1   bouyer 	/*
    288  1.15.8.1   bouyer 	 * generic error status for the rest (BADARGS, RPC, YPERR, RESRC,
    289  1.15.8.1   bouyer 	 * NOMORE, PMAP, YPBIND, YPSERV, NODOM, VERS, ACCESS, BUSY)
    290  1.15.8.1   bouyer 	 */
    291  1.15.8.1   bouyer 	return(YPPUSH_XFRERR);   /* generic error status */
    292  1.15.8.1   bouyer }
    293  1.15.8.1   bouyer 
    294       1.1  thorpej static int
    295      1.12      wiz ypxfr_foreach(int status, char *keystr, int keylen, char *valstr,
    296      1.12      wiz 	      int vallen, char *data)
    297       1.1  thorpej {
    298       1.1  thorpej 	datum key, val;
    299       1.1  thorpej 
    300       1.1  thorpej 	if (status == YP_NOMORE)
    301       1.1  thorpej 		return (0);
    302       1.1  thorpej 
    303       1.1  thorpej 	keystr[keylen] = '\0';
    304       1.1  thorpej 	valstr[vallen] = '\0';
    305       1.1  thorpej 
    306       1.1  thorpej 	key.dptr = keystr;
    307       1.1  thorpej 	key.dsize = strlen(keystr);
    308       1.1  thorpej 
    309       1.1  thorpej 	val.dptr = valstr;
    310       1.1  thorpej 	val.dsize = strlen(valstr);
    311       1.1  thorpej 
    312  1.15.8.1   bouyer         /* XXX: suspect... ignoring return value here */
    313       1.1  thorpej 	ypdb_store(db, key, val, YPDB_INSERT);
    314       1.1  thorpej 
    315       1.1  thorpej 	return (0);
    316       1.1  thorpej }
    317       1.1  thorpej 
    318       1.1  thorpej int
    319      1.12      wiz get_local_ordernum(char *domain, char *map, u_int *lordernum)
    320       1.1  thorpej {
    321       1.1  thorpej 	char map_path[1024];
    322       1.1  thorpej 	char order_key[] = YP_LAST_KEY;
    323       1.1  thorpej 	char order[MAX_LAST_LEN+1];
    324       1.1  thorpej 	struct stat finfo;
    325  1.15.8.1   bouyer 	DBM *ldb;
    326       1.5    lukem 	datum k, v;
    327  1.15.8.1   bouyer 	unsigned int status;
    328       1.1  thorpej 
    329       1.1  thorpej 	status = YPPUSH_SUCC;
    330       1.1  thorpej 
    331       1.1  thorpej 	snprintf(map_path, sizeof(map_path), "%s/%s", YP_DB_PATH, domain);
    332       1.1  thorpej 
    333       1.1  thorpej 	/* Make sure we serve the domain. */
    334       1.1  thorpej 	if ((stat(map_path, &finfo)) != 0 ||
    335       1.1  thorpej 	    (S_ISDIR(finfo.st_mode) == 0)) {
    336       1.4  thorpej 		warnx("domain `%s' not found locally", domain);
    337       1.1  thorpej 		status = YPPUSH_NODOM;
    338       1.1  thorpej 		goto out;
    339       1.1  thorpej 	}
    340       1.1  thorpej 
    341       1.1  thorpej 	/* Make sure we serve the map. */
    342       1.1  thorpej 	snprintf(map_path, sizeof(map_path), "%s/%s/%s%s",
    343       1.1  thorpej 	    YP_DB_PATH, domain, map, YPDB_SUFFIX);
    344       1.1  thorpej 	if (stat(map_path, &finfo) != 0) {
    345       1.1  thorpej 		status = YPPUSH_NOMAP;
    346       1.1  thorpej 		goto out;
    347       1.1  thorpej 	}
    348       1.1  thorpej 
    349       1.1  thorpej 	/* Open the map file. */
    350       1.1  thorpej 	snprintf(map_path, sizeof(map_path), "%s/%s/%s",
    351       1.1  thorpej 	    YP_DB_PATH, domain, map);
    352  1.15.8.1   bouyer 	ldb = ypdb_open(map_path);
    353  1.15.8.1   bouyer 	if (ldb == NULL) {
    354       1.1  thorpej 		status = YPPUSH_DBM;
    355       1.1  thorpej 		goto out;
    356       1.1  thorpej 	}
    357       1.1  thorpej 
    358       1.1  thorpej 	k.dptr = (char *)&order_key;
    359       1.1  thorpej 	k.dsize = YP_LAST_LEN;
    360       1.1  thorpej 
    361  1.15.8.1   bouyer 	v = ypdb_fetch(ldb, k);
    362       1.1  thorpej 
    363       1.1  thorpej 	if (v.dptr == NULL)
    364       1.1  thorpej 		*lordernum = 0;
    365       1.1  thorpej 	else {
    366       1.1  thorpej 		strncpy(order, v.dptr, v.dsize);
    367       1.1  thorpej 		order[v.dsize] = '\0';
    368       1.1  thorpej 		*lordernum = (u_int)atoi((char *)&order);
    369       1.1  thorpej 	}
    370  1.15.8.1   bouyer 	ypdb_close(ldb);
    371       1.1  thorpej 
    372       1.1  thorpej  out:
    373       1.1  thorpej 	if ((status == YPPUSH_NOMAP) || (status == YPPUSH_DBM)) {
    374       1.1  thorpej 		*lordernum = 0;
    375       1.1  thorpej 		status = YPPUSH_SUCC;
    376       1.1  thorpej 	}
    377       1.1  thorpej 
    378       1.1  thorpej 	return (status);
    379       1.1  thorpej }
    380       1.1  thorpej 
    381       1.1  thorpej int
    382      1.12      wiz get_remote_ordernum(CLIENT *client, char *domain, char *map,
    383      1.12      wiz 		    u_int lordernum, u_int *rordernum)
    384       1.1  thorpej {
    385       1.1  thorpej 	int status;
    386       1.1  thorpej 
    387       1.1  thorpej 	status = yp_order_host(client, domain, map, (int *)rordernum);
    388       1.1  thorpej 
    389       1.7     ross 	if (status == 0) {
    390       1.1  thorpej 		if (*rordernum <= lordernum)
    391       1.1  thorpej 			status = YPPUSH_AGE;
    392       1.1  thorpej 		else
    393       1.1  thorpej 			status = YPPUSH_SUCC;
    394  1.15.8.1   bouyer 	} else {
    395  1.15.8.1   bouyer 		status = yperr2yppush(status);
    396       1.7     ross 	}
    397       1.1  thorpej 
    398       1.1  thorpej 	return status;
    399       1.1  thorpej }
    400       1.1  thorpej 
    401       1.1  thorpej void
    402      1.12      wiz get_map(CLIENT *client, char *domain, char *map,
    403      1.12      wiz 	struct ypall_callback *incallback)
    404       1.1  thorpej {
    405       1.1  thorpej 
    406       1.1  thorpej 	(void)yp_all_host(client, domain, map, incallback);
    407       1.1  thorpej }
    408       1.1  thorpej 
    409       1.1  thorpej DBM *
    410      1.15    lukem create_db(char *domain, char *map, char *db_temp, size_t db_temp_len)
    411       1.1  thorpej {
    412      1.15    lukem 	static const char template[] = "ypdbXXXXXX";
    413  1.15.8.1   bouyer 	DBM *ldb;
    414       1.1  thorpej 
    415      1.15    lukem 	snprintf(db_temp, db_temp_len, "%s/%s/%s",
    416      1.15    lukem 	    YP_DB_PATH, domain, template);
    417       1.1  thorpej 
    418  1.15.8.1   bouyer 	ldb = ypdb_mktemp(db_temp);
    419       1.1  thorpej 
    420  1.15.8.1   bouyer 	return ldb;
    421       1.1  thorpej }
    422       1.1  thorpej 
    423       1.1  thorpej int
    424      1.15    lukem install_db(char *domain, char *map, char *db_temp)
    425       1.1  thorpej {
    426      1.15    lukem 	char db_name[MAXPATHLEN];
    427       1.1  thorpej 
    428       1.1  thorpej 	snprintf(db_name, sizeof(db_name), "%s/%s/%s%s",
    429       1.1  thorpej 	    YP_DB_PATH, domain, map, YPDB_SUFFIX);
    430       1.1  thorpej 
    431       1.1  thorpej 	if (rename(db_temp, db_name)) {
    432       1.1  thorpej 		warn("can't rename `%s' -> `%s'", db_temp, db_name);
    433       1.1  thorpej 		return YPPUSH_YPERR;
    434       1.1  thorpej 	}
    435       1.1  thorpej 
    436       1.1  thorpej 	return YPPUSH_SUCC;
    437       1.1  thorpej }
    438       1.1  thorpej 
    439       1.1  thorpej int
    440      1.15    lukem unlink_db(char *domain, char *map, char *db_temp)
    441       1.1  thorpej {
    442       1.1  thorpej 
    443       1.1  thorpej 	if (unlink(db_temp)) {
    444       1.1  thorpej 		warn("can't unlink `%s'", db_temp);
    445       1.1  thorpej 		return YPPUSH_YPERR;
    446       1.1  thorpej 	}
    447       1.1  thorpej 
    448       1.1  thorpej 	return YPPUSH_SUCC;
    449       1.1  thorpej }
    450       1.1  thorpej 
    451       1.1  thorpej int
    452  1.15.8.1   bouyer add_order(DBM *ldb, u_int ordernum)
    453       1.1  thorpej {
    454       1.1  thorpej 	char datestr[11];
    455       1.1  thorpej 	datum key, val;
    456       1.1  thorpej 	char keystr[] = YP_LAST_KEY;
    457       1.1  thorpej 	int status;
    458       1.1  thorpej 
    459       1.1  thorpej 	snprintf(datestr, sizeof(datestr), "%010d", ordernum);
    460       1.1  thorpej 
    461       1.1  thorpej 	key.dptr = keystr;
    462       1.1  thorpej 	key.dsize = strlen(keystr);
    463       1.1  thorpej 
    464       1.1  thorpej 	val.dptr = datestr;
    465       1.1  thorpej 	val.dsize = strlen(datestr);
    466       1.1  thorpej 
    467  1.15.8.1   bouyer 	status = ypdb_store(ldb, key, val, YPDB_INSERT);
    468       1.1  thorpej 	if(status >= 0)
    469       1.1  thorpej 		status = YPPUSH_SUCC;
    470       1.1  thorpej 	else
    471       1.1  thorpej 		status = YPPUSH_DBM;
    472       1.1  thorpej 
    473       1.1  thorpej 	return (status);
    474       1.1  thorpej }
    475       1.1  thorpej 
    476       1.1  thorpej int
    477  1.15.8.1   bouyer add_master(CLIENT *client, char *domain, char *map, DBM *ldb)
    478       1.1  thorpej {
    479       1.1  thorpej 	char keystr[] = YP_MASTER_KEY;
    480       1.1  thorpej 	char *master;
    481       1.1  thorpej 	int status;
    482       1.5    lukem 	datum key, val;
    483       1.1  thorpej 
    484       1.1  thorpej 	master = NULL;
    485       1.1  thorpej 
    486       1.1  thorpej 	/* Get MASTER */
    487       1.1  thorpej 	status = yp_master_host(client, domain, map, &master);
    488       1.1  thorpej 
    489       1.1  thorpej 	if (master != NULL) {
    490       1.1  thorpej 		key.dptr = keystr;
    491       1.1  thorpej 		key.dsize = strlen(keystr);
    492       1.1  thorpej 
    493       1.1  thorpej 		val.dptr = master;
    494       1.1  thorpej 		val.dsize = strlen(master);
    495       1.1  thorpej 
    496  1.15.8.1   bouyer 		status = ypdb_store(ldb, key, val, YPDB_INSERT);
    497       1.1  thorpej 		if (status >= 0)
    498       1.1  thorpej 			status = YPPUSH_SUCC;
    499       1.1  thorpej 		else
    500       1.1  thorpej 			status = YPPUSH_DBM;
    501  1.15.8.1   bouyer 	} else {
    502  1.15.8.1   bouyer 		status = yperr2yppush(status);
    503       1.1  thorpej 	}
    504       1.1  thorpej 
    505       1.1  thorpej 	return status;
    506       1.1  thorpej }
    507       1.1  thorpej 
    508       1.1  thorpej int
    509  1.15.8.1   bouyer add_interdomain(CLIENT *client, char *domain, char *map, DBM *ldb)
    510       1.1  thorpej {
    511       1.1  thorpej 	char keystr[] = YP_INTERDOMAIN_KEY;
    512       1.1  thorpej 	char *value;
    513       1.1  thorpej 	int vallen;
    514       1.1  thorpej 	int status;
    515       1.1  thorpej 	datum k, v;
    516       1.1  thorpej 
    517       1.1  thorpej 	/* Get INTERDOMAIN */
    518       1.1  thorpej 	k.dptr = keystr;
    519       1.1  thorpej 	k.dsize = strlen(keystr);
    520       1.1  thorpej 
    521       1.1  thorpej 	status = yp_match_host(client, domain, map,
    522       1.1  thorpej 	    k.dptr, k.dsize, &value, &vallen);
    523       1.1  thorpej 
    524  1.15.8.1   bouyer 	if (status == YPERR_KEY) {
    525  1.15.8.1   bouyer 		/* this is an optional key/val, so it may not be present */
    526  1.15.8.1   bouyer 		status = YPPUSH_SUCC;
    527  1.15.8.1   bouyer 	} else if (status == 0 && value) {
    528       1.1  thorpej 		v.dptr = value;
    529       1.1  thorpej 		v.dsize = vallen;
    530       1.1  thorpej 
    531       1.1  thorpej 		if (v.dptr != NULL) {
    532  1.15.8.1   bouyer 			status = ypdb_store(ldb, k, v, YPDB_INSERT);
    533       1.1  thorpej 			if (status >= 0)
    534       1.1  thorpej 				status = YPPUSH_SUCC;
    535       1.1  thorpej 			else
    536       1.1  thorpej 				status = YPPUSH_DBM;
    537       1.1  thorpej 		}
    538  1.15.8.1   bouyer 	} else {
    539  1.15.8.1   bouyer 		status = yperr2yppush(status);
    540       1.1  thorpej 	}
    541       1.1  thorpej 
    542       1.1  thorpej 	return status;
    543       1.1  thorpej }
    544       1.1  thorpej 
    545       1.1  thorpej int
    546  1.15.8.1   bouyer add_secure(CLIENT *client, char *domain, char *map, DBM *ldb)
    547       1.1  thorpej {
    548       1.1  thorpej 	char keystr[] = YP_SECURE_KEY;
    549       1.1  thorpej 	char *value;
    550       1.1  thorpej 	int vallen;
    551       1.1  thorpej 	int status;
    552       1.1  thorpej 	datum k, v;
    553       1.1  thorpej 
    554       1.1  thorpej 	/* Get SECURE */
    555       1.1  thorpej 	k.dptr = keystr;
    556       1.1  thorpej 	k.dsize = strlen(keystr);
    557       1.1  thorpej 
    558       1.1  thorpej 	status = yp_match_host(client, domain, map,
    559       1.1  thorpej 	    k.dptr, k.dsize, &value, &vallen);
    560       1.1  thorpej 
    561  1.15.8.1   bouyer 	if (status == YPERR_KEY) {
    562  1.15.8.1   bouyer 		/* this is an optional key/val, so it may not be present */
    563  1.15.8.1   bouyer 		status = YPPUSH_SUCC;
    564  1.15.8.1   bouyer 	} else if (status == 0 && value != 0) {
    565       1.1  thorpej 		v.dptr = value;
    566       1.1  thorpej 		v.dsize = vallen;
    567       1.1  thorpej 
    568       1.1  thorpej 		if (v.dptr != NULL) {
    569  1.15.8.1   bouyer 			status = ypdb_store(ldb, k, v, YPDB_INSERT);
    570       1.1  thorpej 			if (status >= 0)
    571       1.1  thorpej 				status = YPPUSH_SUCC;
    572       1.1  thorpej 			else
    573       1.1  thorpej 				status = YPPUSH_DBM;
    574       1.1  thorpej 		}
    575  1.15.8.1   bouyer 	} else {
    576  1.15.8.1   bouyer 		status = yperr2yppush(status);
    577       1.1  thorpej 	}
    578       1.1  thorpej 
    579       1.1  thorpej 	return status;
    580       1.1  thorpej }
    581       1.1  thorpej 
    582       1.1  thorpej int
    583      1.12      wiz send_clear(CLIENT *client)
    584       1.1  thorpej {
    585       1.1  thorpej 	struct timeval tv;
    586       1.1  thorpej 	int r;
    587       1.1  thorpej 	int status;
    588       1.1  thorpej 
    589       1.1  thorpej 	status = YPPUSH_SUCC;
    590       1.1  thorpej 
    591       1.1  thorpej 	tv.tv_sec = 10;
    592       1.1  thorpej 	tv.tv_usec = 0;
    593       1.1  thorpej 
    594       1.1  thorpej 	/* Send CLEAR */
    595       1.1  thorpej 	r = clnt_call(client, YPPROC_CLEAR, xdr_void, 0, xdr_void, 0, tv);
    596       1.1  thorpej 	if (r != RPC_SUCCESS) {
    597       1.1  thorpej 		clnt_perror(client, "yp_clear: clnt_call");
    598       1.1  thorpej 		status = YPPUSH_RPC;
    599       1.1  thorpej 	}
    600       1.1  thorpej 
    601       1.1  thorpej 	return status;
    602       1.1  thorpej }
    603       1.1  thorpej 
    604       1.1  thorpej int
    605      1.12      wiz send_reply(CLIENT *client, int status, int tid)
    606       1.1  thorpej {
    607       1.1  thorpej 	struct timeval tv;
    608       1.1  thorpej 	struct ypresp_xfr resp;
    609       1.1  thorpej 	int r;
    610       1.1  thorpej 
    611       1.1  thorpej 	tv.tv_sec = 10;
    612       1.1  thorpej 	tv.tv_usec = 0;
    613       1.1  thorpej 
    614       1.1  thorpej 	resp.transid = tid;
    615       1.1  thorpej 	resp.xfrstat = status;
    616       1.1  thorpej 
    617       1.1  thorpej 	/* Send XFRRESP */
    618       1.1  thorpej 	r = clnt_call(client, YPPUSHPROC_XFRRESP, xdr_ypresp_xfr, &resp,
    619       1.1  thorpej 	    xdr_void, 0, tv);
    620       1.1  thorpej 	if (r != RPC_SUCCESS) {
    621       1.1  thorpej 		clnt_perror(client, "yppushresp_xdr: clnt_call");
    622       1.1  thorpej 		status = YPPUSH_RPC;
    623       1.1  thorpej 	}
    624       1.1  thorpej 
    625       1.1  thorpej 	return status;
    626       1.1  thorpej }
    627