xref: /netbsd-src/usr.bin/eject/am_glue.c (revision 355e79354d4f6278ab674b1ad4f0c485640af557)
1*355e7935Syamt /*	$NetBSD: am_glue.c,v 1.4 2010/06/23 18:07:59 yamt Exp $	*/
252f56a8cSchristos 
352f56a8cSchristos /*-
452f56a8cSchristos  * Copyright (c) 1999 The NetBSD Foundation, Inc.
552f56a8cSchristos  * All rights reserved.
652f56a8cSchristos  *
752f56a8cSchristos  * Redistribution and use in source and binary forms, with or without
852f56a8cSchristos  * modification, are permitted provided that the following conditions
952f56a8cSchristos  * are met:
1052f56a8cSchristos  * 1. Redistributions of source code must retain the above copyright
1152f56a8cSchristos  *    notice, this list of conditions and the following disclaimer.
1252f56a8cSchristos  * 2. Redistributions in binary form must reproduce the above copyright
1352f56a8cSchristos  *    notice, this list of conditions and the following disclaimer in the
1452f56a8cSchristos  *    documentation and/or other materials provided with the distribution.
1552f56a8cSchristos  *
1652f56a8cSchristos  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
1752f56a8cSchristos  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
1852f56a8cSchristos  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
1952f56a8cSchristos  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
2052f56a8cSchristos  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
2152f56a8cSchristos  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
2252f56a8cSchristos  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
2352f56a8cSchristos  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
2452f56a8cSchristos  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
2552f56a8cSchristos  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
2652f56a8cSchristos  * POSSIBILITY OF SUCH DAMAGE.
2752f56a8cSchristos  */
2852f56a8cSchristos 
2952f56a8cSchristos #include <sys/cdefs.h>
3052f56a8cSchristos #ifndef lint
31*355e7935Syamt __RCSID("$NetBSD: am_glue.c,v 1.4 2010/06/23 18:07:59 yamt Exp $");
3252f56a8cSchristos #endif /* not lint */
3352f56a8cSchristos 
3452f56a8cSchristos #ifdef HAVE_CONFIG_H
3552f56a8cSchristos # include <config.h>
3652f56a8cSchristos #endif /* HAVE_CONFIG_H */
3752f56a8cSchristos #include <am_defs.h>
3852f56a8cSchristos #include <amu.h>
392bd4c53fSchristos #include <rpc/pmap_prot.h>
402bd4c53fSchristos #include <rpc/pmap_clnt.h>
4152f56a8cSchristos 
42*355e7935Syamt #include <stdbool.h>
43*355e7935Syamt 
4452f56a8cSchristos #include "am_glue.h"
4552f56a8cSchristos 
4652f56a8cSchristos static CLIENT *clnt;
4752f56a8cSchristos 
482bd4c53fSchristos static struct timeval tv = { 5, 0 };
4952f56a8cSchristos /*
5052f56a8cSchristos  * Appease lint: Properly typecast some numbers defined in
5152f56a8cSchristos  * src/extern/bsd/am-utils/dist/include/amq_defs.h.
5252f56a8cSchristos  */
5352f56a8cSchristos #define	xAMQ_PROGRAM		(rpcprog_t)AMQ_PROGRAM
5452f56a8cSchristos #define xAMQ_VERSION		(rpcvers_t)AMQ_VERSION
5552f56a8cSchristos #define xAMQPROC_SYNC_UMNT	(rpcproc_t)AMQPROC_SYNC_UMNT
5652f56a8cSchristos 
572bd4c53fSchristos static int
ping_pmap(void)582bd4c53fSchristos ping_pmap(void)
592bd4c53fSchristos {
602bd4c53fSchristos 	u_short port = 0;
612bd4c53fSchristos 	CLIENT *cl;
622bd4c53fSchristos 	struct pmap parms;
632bd4c53fSchristos 	struct sockaddr_in si;
642bd4c53fSchristos 	int s = -1, rv;
65f0e3fdffSchristos 	static struct timeval pingtv = { 1, 0 };
662bd4c53fSchristos 
672bd4c53fSchristos 	(void)memset(&si, 0, sizeof(si));
682bd4c53fSchristos 	si.sin_family = AF_INET;
692bd4c53fSchristos 	si.sin_len = sizeof(si);
702bd4c53fSchristos 	si.sin_addr.s_addr = htonl(INADDR_LOOPBACK);
712bd4c53fSchristos 	si.sin_port = htons(PMAPPORT);
722bd4c53fSchristos 
73f0e3fdffSchristos 	if ((cl = clntudp_bufcreate(&si, PMAPPROG, PMAPVERS, pingtv,
742bd4c53fSchristos 	    &s, RPCSMALLMSGSIZE, RPCSMALLMSGSIZE)) == NULL)
752bd4c53fSchristos 		return -1;
762bd4c53fSchristos 
772bd4c53fSchristos 	parms.pm_prog = PMAPPROG;
782bd4c53fSchristos 	parms.pm_vers = PMAPVERS;
792bd4c53fSchristos 	parms.pm_prot = IPPROTO_UDP;
802bd4c53fSchristos 	parms.pm_port = 0;  /* not needed or used */
812bd4c53fSchristos 
822bd4c53fSchristos 	rv = CLNT_CALL(cl, (rpcproc_t)PMAPPROC_GETPORT,
832bd4c53fSchristos 	    (xdrproc_t)xdr_pmap, &parms,
84f0e3fdffSchristos 	    (xdrproc_t)xdr_u_short, &port, pingtv) == RPC_SUCCESS ? 0 : -1;
852bd4c53fSchristos 
862bd4c53fSchristos 	CLNT_DESTROY(cl);
872bd4c53fSchristos 	return rv;
882bd4c53fSchristos }
892bd4c53fSchristos 
90*355e7935Syamt static void
am_init(void)9152f56a8cSchristos am_init(void)
9252f56a8cSchristos {
9352f56a8cSchristos 	static const char *server = "localhost";
94*355e7935Syamt 	static bool called;
95*355e7935Syamt 
96*355e7935Syamt 	if (called)
97*355e7935Syamt 		return;
98*355e7935Syamt 	called = true;
9952f56a8cSchristos 
1002bd4c53fSchristos 	if (ping_pmap() == -1)
1012bd4c53fSchristos 		return;
10252f56a8cSchristos 	/*
10352f56a8cSchristos 	 * Create RPC endpoint
10452f56a8cSchristos 	 */
10552f56a8cSchristos 	/* try tcp first */
10652f56a8cSchristos 	clnt = clnt_create(server, xAMQ_PROGRAM, xAMQ_VERSION, "tcp");
10752f56a8cSchristos 	if (clnt != NULL)
10852f56a8cSchristos 		return;
10952f56a8cSchristos 
11052f56a8cSchristos 	/* try udp next */
11152f56a8cSchristos 	clnt = clnt_create(server, xAMQ_PROGRAM, xAMQ_VERSION, "udp");
11252f56a8cSchristos 	if (clnt != NULL)	/* set udp timeout */
11352f56a8cSchristos 		(void)clnt_control(clnt, CLSET_RETRY_TIMEOUT, (void *)&tv);
11452f56a8cSchristos }
11552f56a8cSchristos 
11652f56a8cSchristos int
am_unmount(const char * dirname)11752f56a8cSchristos am_unmount(const char *dirname)
11852f56a8cSchristos {
11952f56a8cSchristos 	static struct timeval timeout = { ALLOWED_MOUNT_TIME, 0 };
12052f56a8cSchristos 	amq_sync_umnt result;
12152f56a8cSchristos 
122*355e7935Syamt 	am_init();
123*355e7935Syamt 
12452f56a8cSchristos 	if (clnt == NULL)
12552f56a8cSchristos 		return AMQ_UMNT_FAILED;
12652f56a8cSchristos 
12752f56a8cSchristos 	if (clnt_call(clnt, xAMQPROC_SYNC_UMNT, xdr_amq_string, &dirname,
12852f56a8cSchristos 	    xdr_amq_sync_umnt, (void *)&result, timeout) != RPC_SUCCESS)
12952f56a8cSchristos 		return AMQ_UMNT_SERVER;
13052f56a8cSchristos 
13152f56a8cSchristos 	return result.au_etype;
13252f56a8cSchristos }
133