12f172c55SRobert Thurlow /*
22f172c55SRobert Thurlow * CDDL HEADER START
32f172c55SRobert Thurlow *
42f172c55SRobert Thurlow * The contents of this file are subject to the terms of the
52f172c55SRobert Thurlow * Common Development and Distribution License (the "License").
62f172c55SRobert Thurlow * You may not use this file except in compliance with the License.
72f172c55SRobert Thurlow *
82f172c55SRobert Thurlow * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
92f172c55SRobert Thurlow * or http://www.opensolaris.org/os/licensing.
102f172c55SRobert Thurlow * See the License for the specific language governing permissions
112f172c55SRobert Thurlow * and limitations under the License.
122f172c55SRobert Thurlow *
132f172c55SRobert Thurlow * When distributing Covered Code, include this CDDL HEADER in each
142f172c55SRobert Thurlow * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
152f172c55SRobert Thurlow * If applicable, add the following below this CDDL HEADER, with the
162f172c55SRobert Thurlow * fields enclosed by brackets "[]" replaced with your own identifying
172f172c55SRobert Thurlow * information: Portions Copyright [yyyy] [name of copyright owner]
182f172c55SRobert Thurlow *
192f172c55SRobert Thurlow * CDDL HEADER END
202f172c55SRobert Thurlow */
212f172c55SRobert Thurlow /*
222f172c55SRobert Thurlow * Copyright 2009 Sun Microsystems, Inc. All rights reserved.
232f172c55SRobert Thurlow * Use is subject to license terms.
242f172c55SRobert Thurlow */
252f172c55SRobert Thurlow
262f172c55SRobert Thurlow
272f172c55SRobert Thurlow /*
282f172c55SRobert Thurlow * Helper routines for nfsmapid and autod daemon
292f172c55SRobert Thurlow * to translate hostname to IP address and Netinfo.
302f172c55SRobert Thurlow */
312f172c55SRobert Thurlow #include <stdio.h>
322f172c55SRobert Thurlow #include <stdlib.h>
332f172c55SRobert Thurlow #include <alloca.h>
342f172c55SRobert Thurlow #include <signal.h>
352f172c55SRobert Thurlow #include <libintl.h>
362f172c55SRobert Thurlow #include <limits.h>
372f172c55SRobert Thurlow #include <errno.h>
382f172c55SRobert Thurlow #include <sys/types.h>
392f172c55SRobert Thurlow #include <string.h>
402f172c55SRobert Thurlow #include <memory.h>
412f172c55SRobert Thurlow #include <pwd.h>
422f172c55SRobert Thurlow #include <grp.h>
432f172c55SRobert Thurlow #include <door.h>
442f172c55SRobert Thurlow #include <syslog.h>
452f172c55SRobert Thurlow #include <fcntl.h>
462f172c55SRobert Thurlow #include <unistd.h>
472f172c55SRobert Thurlow #include <assert.h>
482f172c55SRobert Thurlow #include <deflt.h>
492f172c55SRobert Thurlow #include <netdir.h>
502f172c55SRobert Thurlow #include <nfs/nfs4.h>
512f172c55SRobert Thurlow #include <nfs/nfssys.h>
522f172c55SRobert Thurlow #include <nfs/nfsid_map.h>
532f172c55SRobert Thurlow #include <nfs/mapid.h>
542f172c55SRobert Thurlow #include <nfs/nfs_sec.h>
552f172c55SRobert Thurlow #include <sys/sdt.h>
562f172c55SRobert Thurlow #include <sys/idmap.h>
572f172c55SRobert Thurlow #include <idmap.h>
582f172c55SRobert Thurlow #include <sys/fs/autofs.h>
592f172c55SRobert Thurlow #include "nfs_resolve.h"
602f172c55SRobert Thurlow
612f172c55SRobert Thurlow void
free_knconf(struct knetconfig * k)622f172c55SRobert Thurlow free_knconf(struct knetconfig *k)
632f172c55SRobert Thurlow {
642f172c55SRobert Thurlow if (k == NULL)
652f172c55SRobert Thurlow return;
662f172c55SRobert Thurlow if (k->knc_protofmly)
672f172c55SRobert Thurlow free(k->knc_protofmly);
682f172c55SRobert Thurlow if (k->knc_proto)
692f172c55SRobert Thurlow free(k->knc_proto);
702f172c55SRobert Thurlow free(k);
712f172c55SRobert Thurlow }
722f172c55SRobert Thurlow
732f172c55SRobert Thurlow struct knetconfig *
get_knconf(struct netconfig * nconf)742f172c55SRobert Thurlow get_knconf(struct netconfig *nconf)
752f172c55SRobert Thurlow {
762f172c55SRobert Thurlow struct stat stbuf;
772f172c55SRobert Thurlow struct knetconfig *k = NULL;
782f172c55SRobert Thurlow int len;
792f172c55SRobert Thurlow
802f172c55SRobert Thurlow if (stat(nconf->nc_device, &stbuf) < 0) {
812f172c55SRobert Thurlow syslog(LOG_ERR, "get_knconf: stat %s: %m", nconf->nc_device);
822f172c55SRobert Thurlow return (NULL);
832f172c55SRobert Thurlow }
842f172c55SRobert Thurlow k = (struct knetconfig *)malloc(sizeof (*k));
852f172c55SRobert Thurlow if (k == NULL)
862f172c55SRobert Thurlow goto nomem;
872f172c55SRobert Thurlow k->knc_semantics = nconf->nc_semantics;
882f172c55SRobert Thurlow
892f172c55SRobert Thurlow len = strlen(nconf->nc_protofmly);
902f172c55SRobert Thurlow if (len <= 0)
912f172c55SRobert Thurlow goto err_out;
922f172c55SRobert Thurlow k->knc_protofmly = malloc(KNC_STRSIZE);
932f172c55SRobert Thurlow if (k->knc_protofmly == NULL)
942f172c55SRobert Thurlow goto nomem;
952f172c55SRobert Thurlow bzero(k->knc_protofmly, KNC_STRSIZE);
962f172c55SRobert Thurlow bcopy(nconf->nc_protofmly, k->knc_protofmly, len);
972f172c55SRobert Thurlow
982f172c55SRobert Thurlow len = strlen(nconf->nc_proto);
992f172c55SRobert Thurlow if (len <= 0)
1002f172c55SRobert Thurlow goto err_out;
1012f172c55SRobert Thurlow k->knc_proto = malloc(KNC_STRSIZE);
1022f172c55SRobert Thurlow if (k->knc_proto == NULL)
1032f172c55SRobert Thurlow goto nomem;
1042f172c55SRobert Thurlow bzero(k->knc_proto, KNC_STRSIZE);
1052f172c55SRobert Thurlow bcopy(nconf->nc_proto, k->knc_proto, len);
1062f172c55SRobert Thurlow
1072f172c55SRobert Thurlow k->knc_rdev = stbuf.st_rdev;
1082f172c55SRobert Thurlow
1092f172c55SRobert Thurlow return (k);
1102f172c55SRobert Thurlow
1112f172c55SRobert Thurlow nomem:
1122f172c55SRobert Thurlow syslog(LOG_ERR, "get_knconf: no memory");
1132f172c55SRobert Thurlow err_out:
1142f172c55SRobert Thurlow if (k != NULL)
1152f172c55SRobert Thurlow (void) free_knconf(k);
1162f172c55SRobert Thurlow return (NULL);
1172f172c55SRobert Thurlow }
1182f172c55SRobert Thurlow
1192f172c55SRobert Thurlow /*
1202f172c55SRobert Thurlow * Get the information needed for an NFSv4.x referral. This
1212f172c55SRobert Thurlow * information includes the netbuf, netname and knconfig.
1222f172c55SRobert Thurlow */
1232f172c55SRobert Thurlow struct nfs_fsl_info *
get_nfs4ref_info(char * host,int port,int nfsver)1242f172c55SRobert Thurlow get_nfs4ref_info(char *host, int port, int nfsver)
1252f172c55SRobert Thurlow {
1262f172c55SRobert Thurlow char netname[MAXNETNAMELEN + 1];
1272f172c55SRobert Thurlow enum clnt_stat cstat;
1282f172c55SRobert Thurlow struct nfs_fsl_info *fsl_retp = NULL;
1292f172c55SRobert Thurlow struct netconfig *netconf = NULL;
1302f172c55SRobert Thurlow char *nametemp, *namex = NULL;
1312f172c55SRobert Thurlow struct netbuf *nb = NULL;
1322f172c55SRobert Thurlow NCONF_HANDLE *nc = NULL;
1332f172c55SRobert Thurlow
1342f172c55SRobert Thurlow fsl_retp = calloc(1, sizeof (struct nfs_fsl_info));
1352f172c55SRobert Thurlow if (fsl_retp == NULL) {
1362f172c55SRobert Thurlow syslog(LOG_ERR, "get_nfs4ref_info: no memory\n");
1372f172c55SRobert Thurlow return (NULL);
1382f172c55SRobert Thurlow }
1392f172c55SRobert Thurlow
1402f172c55SRobert Thurlow nametemp = malloc(MAXNETNAMELEN + 1);
1412f172c55SRobert Thurlow if (nametemp == NULL) {
1422f172c55SRobert Thurlow free(fsl_retp);
1432f172c55SRobert Thurlow return (NULL);
1442f172c55SRobert Thurlow }
1452f172c55SRobert Thurlow host2netname(nametemp, host, NULL);
1462f172c55SRobert Thurlow namex = calloc(1, strlen(nametemp) + 1);
1472f172c55SRobert Thurlow if (namex == NULL) {
1482f172c55SRobert Thurlow free(nametemp);
1492f172c55SRobert Thurlow free(fsl_retp);
1502f172c55SRobert Thurlow return (NULL);
1512f172c55SRobert Thurlow }
1522f172c55SRobert Thurlow strncpy(namex, nametemp, strlen(nametemp));
1532f172c55SRobert Thurlow free(nametemp);
1542f172c55SRobert Thurlow fsl_retp->netname = namex;
1552f172c55SRobert Thurlow fsl_retp->netnm_len = strlen(namex) + 1;
1562f172c55SRobert Thurlow
1572f172c55SRobert Thurlow fsl_retp->addr = resolve_netconf(host, NFS_PROGRAM, nfsver,
1582f172c55SRobert Thurlow &netconf, port, NULL, NULL, TRUE, NULL, &cstat);
1592f172c55SRobert Thurlow
1602f172c55SRobert Thurlow if (netconf == NULL || fsl_retp->addr == NULL)
1612f172c55SRobert Thurlow goto done;
1622f172c55SRobert Thurlow
1632f172c55SRobert Thurlow fsl_retp->knconf = get_knconf(netconf);
1642f172c55SRobert Thurlow if (fsl_retp->knconf == NULL)
1652f172c55SRobert Thurlow goto done;
1662f172c55SRobert Thurlow fsl_retp->knconf_len = (sizeof (struct knetconfig) +
1672f172c55SRobert Thurlow (KNC_STRSIZE * 2));
1682f172c55SRobert Thurlow fsl_retp->netbuf_len = (sizeof (struct netbuf) +
1692f172c55SRobert Thurlow fsl_retp->addr->maxlen);
1702f172c55SRobert Thurlow return (fsl_retp);
1712f172c55SRobert Thurlow done:
1722f172c55SRobert Thurlow free_nfs4ref_info(fsl_retp);
1732f172c55SRobert Thurlow return (NULL);
1742f172c55SRobert Thurlow }
1752f172c55SRobert Thurlow
1762f172c55SRobert Thurlow void
free_nfs4ref_info(struct nfs_fsl_info * fsl_retp)1772f172c55SRobert Thurlow free_nfs4ref_info(struct nfs_fsl_info *fsl_retp)
1782f172c55SRobert Thurlow {
1792f172c55SRobert Thurlow if (fsl_retp == NULL)
1802f172c55SRobert Thurlow return;
1812f172c55SRobert Thurlow free_knconf(fsl_retp->knconf);
1822f172c55SRobert Thurlow free(fsl_retp->netname);
1832f172c55SRobert Thurlow if (fsl_retp->addr != NULL) {
1842f172c55SRobert Thurlow free(fsl_retp->addr->buf);
1852f172c55SRobert Thurlow free(fsl_retp->addr);
1862f172c55SRobert Thurlow }
1872f172c55SRobert Thurlow free(fsl_retp);
1882f172c55SRobert Thurlow }
1892f172c55SRobert Thurlow
1902f172c55SRobert Thurlow void
cleanup_tli_parms(struct t_bind * tbind,int fd)1912f172c55SRobert Thurlow cleanup_tli_parms(struct t_bind *tbind, int fd)
1922f172c55SRobert Thurlow {
1932f172c55SRobert Thurlow if (tbind != NULL) {
1942f172c55SRobert Thurlow t_free((char *)tbind, T_BIND);
1952f172c55SRobert Thurlow tbind = NULL;
1962f172c55SRobert Thurlow }
1972f172c55SRobert Thurlow if (fd >= 0)
1982f172c55SRobert Thurlow (void) t_close(fd);
1992f172c55SRobert Thurlow fd = -1;
2002f172c55SRobert Thurlow }
2012f172c55SRobert Thurlow
2022f172c55SRobert Thurlow struct netbuf *
resolve_netconf(char * host,rpcprog_t prog,rpcvers_t nfsver,struct netconfig ** netconf,ushort_t port,struct t_info * tinfo,caddr_t * fhp,bool_t direct_to_server,char * fspath,enum clnt_stat * cstatp)2032f172c55SRobert Thurlow resolve_netconf(char *host, rpcprog_t prog, rpcvers_t nfsver,
2042f172c55SRobert Thurlow struct netconfig **netconf, ushort_t port,
2052f172c55SRobert Thurlow struct t_info *tinfo, caddr_t *fhp, bool_t direct_to_server,
2062f172c55SRobert Thurlow char *fspath, enum clnt_stat *cstatp)
2072f172c55SRobert Thurlow {
2082f172c55SRobert Thurlow NCONF_HANDLE *nc;
2092f172c55SRobert Thurlow struct netconfig *nconf = NULL;
2102f172c55SRobert Thurlow int nthtry = FIRST_TRY;
2112f172c55SRobert Thurlow struct netbuf *nb;
2122f172c55SRobert Thurlow enum clnt_stat cstat;
2132f172c55SRobert Thurlow
2142f172c55SRobert Thurlow nc = setnetpath();
2152f172c55SRobert Thurlow if (nc == NULL)
2162f172c55SRobert Thurlow goto done;
2172f172c55SRobert Thurlow retry:
2182f172c55SRobert Thurlow while (nconf = getnetpath(nc)) {
2192f172c55SRobert Thurlow if (nconf->nc_flag & NC_VISIBLE) {
2202f172c55SRobert Thurlow if (nthtry == FIRST_TRY) {
2212f172c55SRobert Thurlow if ((nconf->nc_semantics ==
2222f172c55SRobert Thurlow NC_TPI_COTS_ORD) ||
2232f172c55SRobert Thurlow (nconf->nc_semantics ==
2242f172c55SRobert Thurlow NC_TPI_COTS)) {
2252f172c55SRobert Thurlow if (port == 0)
2262f172c55SRobert Thurlow break;
2272f172c55SRobert Thurlow if ((strcmp(nconf->nc_protofmly,
2282f172c55SRobert Thurlow NC_INET) == 0 ||
2292f172c55SRobert Thurlow strcmp(nconf->nc_protofmly,
2302f172c55SRobert Thurlow NC_INET6) == 0) &&
2312f172c55SRobert Thurlow (strcmp(nconf->nc_proto,
2322f172c55SRobert Thurlow NC_TCP) == 0))
2332f172c55SRobert Thurlow break;
2342f172c55SRobert Thurlow }
2352f172c55SRobert Thurlow }
2362f172c55SRobert Thurlow if (nthtry == SECOND_TRY) {
2372f172c55SRobert Thurlow if (nconf->nc_semantics ==
2382f172c55SRobert Thurlow NC_TPI_CLTS) {
2392f172c55SRobert Thurlow if (port == 0)
2402f172c55SRobert Thurlow break;
2412f172c55SRobert Thurlow if ((strcmp(nconf->nc_protofmly,
2422f172c55SRobert Thurlow NC_INET) == 0 ||
2432f172c55SRobert Thurlow strcmp(nconf->nc_protofmly,
2442f172c55SRobert Thurlow NC_INET6) == 0) &&
2452f172c55SRobert Thurlow (strcmp(nconf->nc_proto,
2462f172c55SRobert Thurlow NC_UDP) == 0))
2472f172c55SRobert Thurlow break;
2482f172c55SRobert Thurlow }
2492f172c55SRobert Thurlow }
2502f172c55SRobert Thurlow }
2512f172c55SRobert Thurlow } /* while */
2522f172c55SRobert Thurlow if (nconf == NULL) {
2532f172c55SRobert Thurlow if (++nthtry <= MNT_PREF_LISTLEN) {
2542f172c55SRobert Thurlow endnetpath(nc);
2552f172c55SRobert Thurlow if ((nc = setnetpath()) == NULL)
2562f172c55SRobert Thurlow goto done;
2572f172c55SRobert Thurlow goto retry;
2582f172c55SRobert Thurlow } else
2592f172c55SRobert Thurlow return (NULL);
2602f172c55SRobert Thurlow } else {
2612f172c55SRobert Thurlow nb = get_server_addr(host, NFS_PROGRAM, nfsver,
2622f172c55SRobert Thurlow nconf, port, NULL, NULL, TRUE, NULL, &cstat);
2632f172c55SRobert Thurlow if (cstat != RPC_SUCCESS)
2642f172c55SRobert Thurlow goto retry;
2652f172c55SRobert Thurlow }
2662f172c55SRobert Thurlow done:
2672f172c55SRobert Thurlow *netconf = nconf;
2682f172c55SRobert Thurlow *cstatp = cstat;
2692f172c55SRobert Thurlow if (nc)
2702f172c55SRobert Thurlow endnetpath(nc);
2712f172c55SRobert Thurlow return (nb);
2722f172c55SRobert Thurlow }
2732f172c55SRobert Thurlow
2742f172c55SRobert Thurlow int
setup_nb_parms(struct netconfig * nconf,struct t_bind * tbind,struct t_info * tinfo,char * hostname,int fd,bool_t direct_to_server,ushort_t port,rpcprog_t prog,rpcvers_t vers,bool_t file_handle)2752f172c55SRobert Thurlow setup_nb_parms(struct netconfig *nconf, struct t_bind *tbind,
2762f172c55SRobert Thurlow struct t_info *tinfo, char *hostname, int fd, bool_t direct_to_server,
2772f172c55SRobert Thurlow ushort_t port, rpcprog_t prog, rpcvers_t vers, bool_t file_handle)
2782f172c55SRobert Thurlow {
2792f172c55SRobert Thurlow if (nconf == NULL) {
2802f172c55SRobert Thurlow return (-1);
2812f172c55SRobert Thurlow }
2822f172c55SRobert Thurlow if (direct_to_server == TRUE) {
2832f172c55SRobert Thurlow struct nd_hostserv hs;
2842f172c55SRobert Thurlow struct nd_addrlist *retaddrs;
2852f172c55SRobert Thurlow hs.h_host = hostname;
2862f172c55SRobert Thurlow
2872f172c55SRobert Thurlow if (port == 0)
2882f172c55SRobert Thurlow hs.h_serv = "nfs";
2892f172c55SRobert Thurlow else
2902f172c55SRobert Thurlow hs.h_serv = NULL;
2912f172c55SRobert Thurlow
2922f172c55SRobert Thurlow if (netdir_getbyname(nconf, &hs, &retaddrs) != ND_OK) {
2932f172c55SRobert Thurlow return (-1);
2942f172c55SRobert Thurlow }
2952f172c55SRobert Thurlow memcpy(tbind->addr.buf, retaddrs->n_addrs->buf,
2962f172c55SRobert Thurlow retaddrs->n_addrs->len);
2972f172c55SRobert Thurlow tbind->addr.len = retaddrs->n_addrs->len;
2982f172c55SRobert Thurlow tbind->addr.maxlen = retaddrs->n_addrs->maxlen;
2992f172c55SRobert Thurlow netdir_free((void *)retaddrs, ND_ADDRLIST);
3002f172c55SRobert Thurlow if (port) {
3012f172c55SRobert Thurlow /* LINTED pointer alignment */
302*8509e9caSToomas Soome if (strcmp(nconf->nc_protofmly, NC_INET) == 0)
3032f172c55SRobert Thurlow ((struct sockaddr_in *)
3042f172c55SRobert Thurlow tbind->addr.buf)->sin_port =
3052f172c55SRobert Thurlow htons((ushort_t)port);
306*8509e9caSToomas Soome else if (strcmp(nconf->nc_protofmly, NC_INET6) == 0)
3072f172c55SRobert Thurlow ((struct sockaddr_in6 *)
3082f172c55SRobert Thurlow tbind->addr.buf)->sin6_port =
3092f172c55SRobert Thurlow htons((ushort_t)port);
3102f172c55SRobert Thurlow }
3112f172c55SRobert Thurlow
3122f172c55SRobert Thurlow if (file_handle) {
3132f172c55SRobert Thurlow if (netdir_options(nconf, ND_SET_RESERVEDPORT, fd,
3142f172c55SRobert Thurlow NULL) == -1)
3152f172c55SRobert Thurlow return (-1);
3162f172c55SRobert Thurlow }
3172f172c55SRobert Thurlow } else if (!file_handle) {
3182f172c55SRobert Thurlow if (port) {
3192f172c55SRobert Thurlow /* LINTED pointer alignment */
320*8509e9caSToomas Soome if (strcmp(nconf->nc_protofmly, NC_INET) == 0)
3212f172c55SRobert Thurlow ((struct sockaddr_in *)
3222f172c55SRobert Thurlow tbind->addr.buf)->sin_port =
3232f172c55SRobert Thurlow htons((ushort_t)port);
324*8509e9caSToomas Soome else if (strcmp(nconf->nc_protofmly, NC_INET6) == 0)
3252f172c55SRobert Thurlow ((struct sockaddr_in6 *)
3262f172c55SRobert Thurlow tbind->addr.buf)->sin6_port =
3272f172c55SRobert Thurlow htons((ushort_t)port);
3282f172c55SRobert Thurlow }
3292f172c55SRobert Thurlow } else {
3302f172c55SRobert Thurlow return (-1);
3312f172c55SRobert Thurlow }
3322f172c55SRobert Thurlow return (1);
3332f172c55SRobert Thurlow }
3342f172c55SRobert Thurlow
3352f172c55SRobert Thurlow /*
3362f172c55SRobert Thurlow * Sets up TLI interface and finds the address withe netdir_getbyname().
3372f172c55SRobert Thurlow * returns the address returned from the call.
3382f172c55SRobert Thurlow * Caller frees up the memory allocated here.
3392f172c55SRobert Thurlow */
3402f172c55SRobert Thurlow struct netbuf *
get_server_addr(char * hostname,rpcprog_t prog,rpcvers_t vers,struct netconfig * nconf,ushort_t port,struct t_info * tinfo,caddr_t * fhp,bool_t direct_to_server,char * fspath,enum clnt_stat * cstat)3412f172c55SRobert Thurlow get_server_addr(char *hostname, rpcprog_t prog, rpcvers_t vers,
3422f172c55SRobert Thurlow struct netconfig *nconf, ushort_t port,
3432f172c55SRobert Thurlow struct t_info *tinfo, caddr_t *fhp, bool_t direct_to_server,
3442f172c55SRobert Thurlow char *fspath, enum clnt_stat *cstat)
3452f172c55SRobert Thurlow {
3462f172c55SRobert Thurlow int fd = -1;
3472f172c55SRobert Thurlow struct t_bind *tbind = NULL;
3482f172c55SRobert Thurlow enum clnt_stat cs = RPC_SYSTEMERROR;
3492f172c55SRobert Thurlow struct netbuf *nb = NULL;
3502f172c55SRobert Thurlow int ret = -1;
3512f172c55SRobert Thurlow
3522f172c55SRobert Thurlow if (prog == NFS_PROGRAM && vers == NFS_V4)
3532f172c55SRobert Thurlow if (strncasecmp(nconf->nc_proto, NC_UDP, strlen(NC_UDP)) == 0)
3542f172c55SRobert Thurlow goto done;
3552f172c55SRobert Thurlow
3562f172c55SRobert Thurlow if ((fd = t_open(nconf->nc_device, O_RDWR, tinfo)) < 0)
3572f172c55SRobert Thurlow goto done;
3582f172c55SRobert Thurlow
3592f172c55SRobert Thurlow if ((tbind = (struct t_bind *)t_alloc(fd, T_BIND, T_ADDR)) == NULL)
3602f172c55SRobert Thurlow goto done;
3612f172c55SRobert Thurlow
3622f172c55SRobert Thurlow if (setup_nb_parms(nconf, tbind, tinfo, hostname, fd, direct_to_server,
3632f172c55SRobert Thurlow port, prog, vers, 0) < 0)
3642f172c55SRobert Thurlow goto done;
3652f172c55SRobert Thurlow
3662f172c55SRobert Thurlow nb = (struct netbuf *)malloc(sizeof (struct netbuf));
3672f172c55SRobert Thurlow if (nb == NULL) {
3682f172c55SRobert Thurlow syslog(LOG_ERR, "no memory\n");
3692f172c55SRobert Thurlow goto done;
3702f172c55SRobert Thurlow }
3712f172c55SRobert Thurlow nb->buf = (char *)malloc(tbind->addr.maxlen);
3722f172c55SRobert Thurlow if (nb->buf == NULL) {
3732f172c55SRobert Thurlow syslog(LOG_ERR, "no memory\n");
3742f172c55SRobert Thurlow free(nb);
3752f172c55SRobert Thurlow nb = NULL;
3762f172c55SRobert Thurlow goto done;
3772f172c55SRobert Thurlow }
3782f172c55SRobert Thurlow (void) memcpy(nb->buf, tbind->addr.buf, tbind->addr.len);
3792f172c55SRobert Thurlow nb->len = tbind->addr.len;
3802f172c55SRobert Thurlow nb->maxlen = tbind->addr.maxlen;
3812f172c55SRobert Thurlow cs = RPC_SUCCESS;
3822f172c55SRobert Thurlow done:
3832f172c55SRobert Thurlow *cstat = cs;
3842f172c55SRobert Thurlow cleanup_tli_parms(tbind, fd);
3852f172c55SRobert Thurlow return (nb);
3862f172c55SRobert Thurlow }
387