xref: /freebsd/sbin/ggate/shared/ggate.c (revision 122abe0385259048f1dbfcf673fdd173cf26ea09)
16ac5fe48SPawel Jakub Dawidek /*-
26ac5fe48SPawel Jakub Dawidek  * Copyright (c) 2004 Pawel Jakub Dawidek <pjd@FreeBSD.org>
36ac5fe48SPawel Jakub Dawidek  * All rights reserved.
46ac5fe48SPawel Jakub Dawidek  *
56ac5fe48SPawel Jakub Dawidek  * Redistribution and use in source and binary forms, with or without
66ac5fe48SPawel Jakub Dawidek  * modification, are permitted provided that the following conditions
76ac5fe48SPawel Jakub Dawidek  * are met:
86ac5fe48SPawel Jakub Dawidek  * 1. Redistributions of source code must retain the above copyright
96ac5fe48SPawel Jakub Dawidek  *    notice, this list of conditions and the following disclaimer.
106ac5fe48SPawel Jakub Dawidek  * 2. Redistributions in binary form must reproduce the above copyright
116ac5fe48SPawel Jakub Dawidek  *    notice, this list of conditions and the following disclaimer in the
126ac5fe48SPawel Jakub Dawidek  *    documentation and/or other materials provided with the distribution.
136ac5fe48SPawel Jakub Dawidek  *
146ac5fe48SPawel Jakub Dawidek  * THIS SOFTWARE IS PROVIDED BY THE AUTHORS AND CONTRIBUTORS ``AS IS'' AND
156ac5fe48SPawel Jakub Dawidek  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
166ac5fe48SPawel Jakub Dawidek  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
176ac5fe48SPawel Jakub Dawidek  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHORS OR CONTRIBUTORS BE LIABLE
186ac5fe48SPawel Jakub Dawidek  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
196ac5fe48SPawel Jakub Dawidek  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
206ac5fe48SPawel Jakub Dawidek  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
216ac5fe48SPawel Jakub Dawidek  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
226ac5fe48SPawel Jakub Dawidek  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
236ac5fe48SPawel Jakub Dawidek  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
246ac5fe48SPawel Jakub Dawidek  * SUCH DAMAGE.
256ac5fe48SPawel Jakub Dawidek  *
266ac5fe48SPawel Jakub Dawidek  * $FreeBSD$
276ac5fe48SPawel Jakub Dawidek  */
286ac5fe48SPawel Jakub Dawidek 
296ac5fe48SPawel Jakub Dawidek #include <stdio.h>
306ac5fe48SPawel Jakub Dawidek #include <stdlib.h>
316ac5fe48SPawel Jakub Dawidek #include <unistd.h>
326ac5fe48SPawel Jakub Dawidek #include <fcntl.h>
336ac5fe48SPawel Jakub Dawidek #include <sys/param.h>
346ac5fe48SPawel Jakub Dawidek #include <sys/disk.h>
356ac5fe48SPawel Jakub Dawidek #include <sys/stat.h>
366ac5fe48SPawel Jakub Dawidek #include <sys/endian.h>
376ac5fe48SPawel Jakub Dawidek #include <sys/socket.h>
386ac5fe48SPawel Jakub Dawidek #include <sys/linker.h>
396ac5fe48SPawel Jakub Dawidek #include <sys/module.h>
406ac5fe48SPawel Jakub Dawidek #include <netinet/in.h>
416ac5fe48SPawel Jakub Dawidek #include <arpa/inet.h>
426ac5fe48SPawel Jakub Dawidek #include <signal.h>
436ac5fe48SPawel Jakub Dawidek #include <err.h>
446ac5fe48SPawel Jakub Dawidek #include <errno.h>
456ac5fe48SPawel Jakub Dawidek #include <string.h>
466ac5fe48SPawel Jakub Dawidek #include <strings.h>
476ac5fe48SPawel Jakub Dawidek #include <libgen.h>
4871ae6999SPawel Jakub Dawidek #include <libutil.h>
496ac5fe48SPawel Jakub Dawidek #include <netdb.h>
506ac5fe48SPawel Jakub Dawidek #include <syslog.h>
516ac5fe48SPawel Jakub Dawidek #include <stdarg.h>
5271ae6999SPawel Jakub Dawidek #include <stdint.h>
536ac5fe48SPawel Jakub Dawidek #include <libgeom.h>
546ac5fe48SPawel Jakub Dawidek 
556ac5fe48SPawel Jakub Dawidek #include <geom/gate/g_gate.h>
566ac5fe48SPawel Jakub Dawidek #include "ggate.h"
576ac5fe48SPawel Jakub Dawidek 
586ac5fe48SPawel Jakub Dawidek 
596ac5fe48SPawel Jakub Dawidek int g_gate_devfd = -1;
606ac5fe48SPawel Jakub Dawidek int g_gate_verbose = 0;
616ac5fe48SPawel Jakub Dawidek 
626ac5fe48SPawel Jakub Dawidek 
636ac5fe48SPawel Jakub Dawidek void
646ac5fe48SPawel Jakub Dawidek g_gate_vlog(int priority, const char *message, va_list ap)
656ac5fe48SPawel Jakub Dawidek {
666ac5fe48SPawel Jakub Dawidek 
676ac5fe48SPawel Jakub Dawidek 	if (g_gate_verbose) {
686ac5fe48SPawel Jakub Dawidek 		const char *prefix;
696ac5fe48SPawel Jakub Dawidek 
706ac5fe48SPawel Jakub Dawidek 		switch (priority) {
716ac5fe48SPawel Jakub Dawidek 		case LOG_ERR:
726ac5fe48SPawel Jakub Dawidek 			prefix = "error";
736ac5fe48SPawel Jakub Dawidek 			break;
746ac5fe48SPawel Jakub Dawidek 		case LOG_WARNING:
756ac5fe48SPawel Jakub Dawidek 			prefix = "warning";
766ac5fe48SPawel Jakub Dawidek 			break;
776ac5fe48SPawel Jakub Dawidek 		case LOG_NOTICE:
786ac5fe48SPawel Jakub Dawidek 			prefix = "notice";
796ac5fe48SPawel Jakub Dawidek 			break;
806ac5fe48SPawel Jakub Dawidek 		case LOG_INFO:
816ac5fe48SPawel Jakub Dawidek 			prefix = "info";
826ac5fe48SPawel Jakub Dawidek 			break;
836ac5fe48SPawel Jakub Dawidek 		case LOG_DEBUG:
846ac5fe48SPawel Jakub Dawidek 			prefix = "debug";
856ac5fe48SPawel Jakub Dawidek 			break;
866ac5fe48SPawel Jakub Dawidek 		default:
876ac5fe48SPawel Jakub Dawidek 			prefix = "unknown";
886ac5fe48SPawel Jakub Dawidek 		}
896ac5fe48SPawel Jakub Dawidek 
906ac5fe48SPawel Jakub Dawidek 		printf("%s: ", prefix);
916ac5fe48SPawel Jakub Dawidek 		vprintf(message, ap);
926ac5fe48SPawel Jakub Dawidek 		printf("\n");
936ac5fe48SPawel Jakub Dawidek 	} else {
946ac5fe48SPawel Jakub Dawidek 		if (priority != LOG_DEBUG)
956ac5fe48SPawel Jakub Dawidek 			vsyslog(priority, message, ap);
966ac5fe48SPawel Jakub Dawidek 	}
976ac5fe48SPawel Jakub Dawidek }
986ac5fe48SPawel Jakub Dawidek 
996ac5fe48SPawel Jakub Dawidek void
1006ac5fe48SPawel Jakub Dawidek g_gate_log(int priority, const char *message, ...)
1016ac5fe48SPawel Jakub Dawidek {
1026ac5fe48SPawel Jakub Dawidek 	va_list ap;
1036ac5fe48SPawel Jakub Dawidek 
1046ac5fe48SPawel Jakub Dawidek 	va_start(ap, message);
1056ac5fe48SPawel Jakub Dawidek 	g_gate_vlog(priority, message, ap);
1066ac5fe48SPawel Jakub Dawidek 	va_end(ap);
1076ac5fe48SPawel Jakub Dawidek }
1086ac5fe48SPawel Jakub Dawidek 
1096ac5fe48SPawel Jakub Dawidek void
1106ac5fe48SPawel Jakub Dawidek g_gate_xvlog(const char *message, va_list ap)
1116ac5fe48SPawel Jakub Dawidek {
1126ac5fe48SPawel Jakub Dawidek 
1136ac5fe48SPawel Jakub Dawidek 	g_gate_vlog(LOG_ERR, message, ap);
1146ac5fe48SPawel Jakub Dawidek 	g_gate_vlog(LOG_ERR, "Exiting.", ap);
1156ac5fe48SPawel Jakub Dawidek 	exit(EXIT_FAILURE);
1166ac5fe48SPawel Jakub Dawidek }
1176ac5fe48SPawel Jakub Dawidek 
1186ac5fe48SPawel Jakub Dawidek void
1196ac5fe48SPawel Jakub Dawidek g_gate_xlog(const char *message, ...)
1206ac5fe48SPawel Jakub Dawidek {
1216ac5fe48SPawel Jakub Dawidek 	va_list ap;
1226ac5fe48SPawel Jakub Dawidek 
1236ac5fe48SPawel Jakub Dawidek 	va_start(ap, message);
1246ac5fe48SPawel Jakub Dawidek 	g_gate_xvlog(message, ap);
1256ac5fe48SPawel Jakub Dawidek 	/* NOTREACHED */
1266ac5fe48SPawel Jakub Dawidek 	va_end(ap);
1276ac5fe48SPawel Jakub Dawidek 	exit(EXIT_FAILURE);
1286ac5fe48SPawel Jakub Dawidek }
1296ac5fe48SPawel Jakub Dawidek 
1306ac5fe48SPawel Jakub Dawidek off_t
1316ac5fe48SPawel Jakub Dawidek g_gate_mediasize(int fd)
1326ac5fe48SPawel Jakub Dawidek {
1336ac5fe48SPawel Jakub Dawidek 	off_t mediasize;
1346ac5fe48SPawel Jakub Dawidek 	struct stat sb;
1356ac5fe48SPawel Jakub Dawidek 
136122abe03SPawel Jakub Dawidek 	if (fstat(fd, &sb) == -1)
1376ac5fe48SPawel Jakub Dawidek 		g_gate_xlog("fstat(): %s.", strerror(errno));
1386ac5fe48SPawel Jakub Dawidek 	if (S_ISCHR(sb.st_mode)) {
139122abe03SPawel Jakub Dawidek 		if (ioctl(fd, DIOCGMEDIASIZE, &mediasize) == -1) {
1406ac5fe48SPawel Jakub Dawidek 			g_gate_xlog("Can't get media size: %s.",
1416ac5fe48SPawel Jakub Dawidek 			    strerror(errno));
1426ac5fe48SPawel Jakub Dawidek 		}
1436ac5fe48SPawel Jakub Dawidek 	} else if (S_ISREG(sb.st_mode)) {
1446ac5fe48SPawel Jakub Dawidek 		mediasize = sb.st_size;
1456ac5fe48SPawel Jakub Dawidek 	} else {
1466ac5fe48SPawel Jakub Dawidek 		g_gate_xlog("Unsupported file system object.");
1476ac5fe48SPawel Jakub Dawidek 	}
1486ac5fe48SPawel Jakub Dawidek 	return (mediasize);
1496ac5fe48SPawel Jakub Dawidek }
1506ac5fe48SPawel Jakub Dawidek 
1516ac5fe48SPawel Jakub Dawidek size_t
1526ac5fe48SPawel Jakub Dawidek g_gate_sectorsize(int fd)
1536ac5fe48SPawel Jakub Dawidek {
1546ac5fe48SPawel Jakub Dawidek 	size_t secsize;
1556ac5fe48SPawel Jakub Dawidek 	struct stat sb;
1566ac5fe48SPawel Jakub Dawidek 
157122abe03SPawel Jakub Dawidek 	if (fstat(fd, &sb) == -1)
1586ac5fe48SPawel Jakub Dawidek 		g_gate_xlog("fstat(): %s.", strerror(errno));
1596ac5fe48SPawel Jakub Dawidek 	if (S_ISCHR(sb.st_mode)) {
160122abe03SPawel Jakub Dawidek 		if (ioctl(fd, DIOCGSECTORSIZE, &secsize) == -1) {
1616ac5fe48SPawel Jakub Dawidek                         g_gate_xlog("Can't get sector size: %s.",
1626ac5fe48SPawel Jakub Dawidek 			    strerror(errno));
1636ac5fe48SPawel Jakub Dawidek 		}
1646ac5fe48SPawel Jakub Dawidek 	} else if (S_ISREG(sb.st_mode)) {
1656ac5fe48SPawel Jakub Dawidek 		secsize = 512;
1666ac5fe48SPawel Jakub Dawidek 	} else {
1676ac5fe48SPawel Jakub Dawidek 		g_gate_xlog("Unsupported file system object.");
1686ac5fe48SPawel Jakub Dawidek 	}
1696ac5fe48SPawel Jakub Dawidek 	return (secsize);
1706ac5fe48SPawel Jakub Dawidek }
1716ac5fe48SPawel Jakub Dawidek 
1726ac5fe48SPawel Jakub Dawidek void
1736ac5fe48SPawel Jakub Dawidek g_gate_open_device(void)
1746ac5fe48SPawel Jakub Dawidek {
1756ac5fe48SPawel Jakub Dawidek 
1766ac5fe48SPawel Jakub Dawidek 	g_gate_devfd = open("/dev/" G_GATE_CTL_NAME, O_RDWR, 0);
177122abe03SPawel Jakub Dawidek 	if (g_gate_devfd == -1)
1786ac5fe48SPawel Jakub Dawidek 		err(EXIT_FAILURE, "open(/dev/%s)", G_GATE_CTL_NAME);
1796ac5fe48SPawel Jakub Dawidek }
1806ac5fe48SPawel Jakub Dawidek 
1816ac5fe48SPawel Jakub Dawidek void
1826ac5fe48SPawel Jakub Dawidek g_gate_close_device(void)
1836ac5fe48SPawel Jakub Dawidek {
1846ac5fe48SPawel Jakub Dawidek 
1856ac5fe48SPawel Jakub Dawidek 	close(g_gate_devfd);
1866ac5fe48SPawel Jakub Dawidek }
1876ac5fe48SPawel Jakub Dawidek 
1886ac5fe48SPawel Jakub Dawidek void
1896ac5fe48SPawel Jakub Dawidek g_gate_ioctl(unsigned long req, void *data)
1906ac5fe48SPawel Jakub Dawidek {
1916ac5fe48SPawel Jakub Dawidek 
192122abe03SPawel Jakub Dawidek 	if (ioctl(g_gate_devfd, req, data) == -1) {
1936ac5fe48SPawel Jakub Dawidek 		g_gate_xlog("%s: ioctl(/dev/%s): %s.", getprogname(),
1946ac5fe48SPawel Jakub Dawidek 		    G_GATE_CTL_NAME, strerror(errno));
1956ac5fe48SPawel Jakub Dawidek 	}
1966ac5fe48SPawel Jakub Dawidek }
1976ac5fe48SPawel Jakub Dawidek 
1986ac5fe48SPawel Jakub Dawidek void
1996ac5fe48SPawel Jakub Dawidek g_gate_destroy(int unit, int force)
2006ac5fe48SPawel Jakub Dawidek {
2016ac5fe48SPawel Jakub Dawidek 	struct g_gate_ctl_destroy ggio;
2026ac5fe48SPawel Jakub Dawidek 
2036ac5fe48SPawel Jakub Dawidek 	ggio.gctl_version = G_GATE_VERSION;
2046ac5fe48SPawel Jakub Dawidek 	ggio.gctl_unit = unit;
2056ac5fe48SPawel Jakub Dawidek 	ggio.gctl_force = force;
2066ac5fe48SPawel Jakub Dawidek 	g_gate_ioctl(G_GATE_CMD_DESTROY, &ggio);
2076ac5fe48SPawel Jakub Dawidek }
2086ac5fe48SPawel Jakub Dawidek 
2096ac5fe48SPawel Jakub Dawidek int
2106ac5fe48SPawel Jakub Dawidek g_gate_openflags(unsigned ggflags)
2116ac5fe48SPawel Jakub Dawidek {
2126ac5fe48SPawel Jakub Dawidek 
2136ac5fe48SPawel Jakub Dawidek 	if ((ggflags & G_GATE_FLAG_READONLY) != 0)
2146ac5fe48SPawel Jakub Dawidek 		return (O_RDONLY);
2156ac5fe48SPawel Jakub Dawidek 	else if ((ggflags & G_GATE_FLAG_WRITEONLY) != 0)
2166ac5fe48SPawel Jakub Dawidek 		return (O_WRONLY);
2176ac5fe48SPawel Jakub Dawidek 	return (O_RDWR);
2186ac5fe48SPawel Jakub Dawidek }
2196ac5fe48SPawel Jakub Dawidek 
2206ac5fe48SPawel Jakub Dawidek void
2216ac5fe48SPawel Jakub Dawidek g_gate_load_module(void)
2226ac5fe48SPawel Jakub Dawidek {
2236ac5fe48SPawel Jakub Dawidek 
224122abe03SPawel Jakub Dawidek 	if (modfind("g_gate") == -1) {
2256ac5fe48SPawel Jakub Dawidek 		/* Not present in kernel, try loading it. */
226122abe03SPawel Jakub Dawidek 		if (kldload("geom_gate") == -1 || modfind("g_gate") == -1) {
2276ac5fe48SPawel Jakub Dawidek 			if (errno != EEXIST) {
2286ac5fe48SPawel Jakub Dawidek 				errx(EXIT_FAILURE,
2296ac5fe48SPawel Jakub Dawidek 				    "geom_gate module not available!");
2306ac5fe48SPawel Jakub Dawidek 			}
2316ac5fe48SPawel Jakub Dawidek 		}
2326ac5fe48SPawel Jakub Dawidek 	}
2336ac5fe48SPawel Jakub Dawidek }
2346ac5fe48SPawel Jakub Dawidek 
2356ac5fe48SPawel Jakub Dawidek #ifdef LIBGEOM
2366ac5fe48SPawel Jakub Dawidek static struct gclass *
2376ac5fe48SPawel Jakub Dawidek find_class(struct gmesh *mesh, const char *name)
2386ac5fe48SPawel Jakub Dawidek {
2396ac5fe48SPawel Jakub Dawidek 	struct gclass *class;
2406ac5fe48SPawel Jakub Dawidek 
2416ac5fe48SPawel Jakub Dawidek 	LIST_FOREACH(class, &mesh->lg_class, lg_class) {
2426ac5fe48SPawel Jakub Dawidek 		if (strcmp(class->lg_name, name) == 0)
2436ac5fe48SPawel Jakub Dawidek 			return (class);
2446ac5fe48SPawel Jakub Dawidek 	}
2456ac5fe48SPawel Jakub Dawidek 	return (NULL);
2466ac5fe48SPawel Jakub Dawidek }
2476ac5fe48SPawel Jakub Dawidek 
2486ac5fe48SPawel Jakub Dawidek static const char *
2496ac5fe48SPawel Jakub Dawidek get_conf(struct ggeom *gp, const char *name)
2506ac5fe48SPawel Jakub Dawidek {
2516ac5fe48SPawel Jakub Dawidek 	struct gconfig *conf;
2526ac5fe48SPawel Jakub Dawidek 
2536ac5fe48SPawel Jakub Dawidek 	LIST_FOREACH(conf, &gp->lg_config, lg_config) {
2546ac5fe48SPawel Jakub Dawidek 		if (strcmp(conf->lg_name, name) == 0)
2556ac5fe48SPawel Jakub Dawidek 			return (conf->lg_val);
2566ac5fe48SPawel Jakub Dawidek 	}
2576ac5fe48SPawel Jakub Dawidek 	return (NULL);
2586ac5fe48SPawel Jakub Dawidek }
2596ac5fe48SPawel Jakub Dawidek 
2606ac5fe48SPawel Jakub Dawidek static void
2616ac5fe48SPawel Jakub Dawidek show_config(struct ggeom *gp, int verbose)
2626ac5fe48SPawel Jakub Dawidek {
2636ac5fe48SPawel Jakub Dawidek 	struct gprovider *pp;
26471ae6999SPawel Jakub Dawidek 	char buf[5];
2656ac5fe48SPawel Jakub Dawidek 
2666ac5fe48SPawel Jakub Dawidek 	pp = LIST_FIRST(&gp->lg_provider);
2676ac5fe48SPawel Jakub Dawidek 	if (pp == NULL)
2686ac5fe48SPawel Jakub Dawidek 		return;
2696ac5fe48SPawel Jakub Dawidek 	if (!verbose) {
2706ac5fe48SPawel Jakub Dawidek 		printf("%s\n", pp->lg_name);
2716ac5fe48SPawel Jakub Dawidek 		return;
2726ac5fe48SPawel Jakub Dawidek 	}
2736ac5fe48SPawel Jakub Dawidek 	printf("       NAME: %s\n", pp->lg_name);
2746ac5fe48SPawel Jakub Dawidek 	printf("       info: %s\n", get_conf(gp, "info"));
2756ac5fe48SPawel Jakub Dawidek 	printf("     access: %s\n", get_conf(gp, "access"));
2766ac5fe48SPawel Jakub Dawidek 	printf("    timeout: %s\n", get_conf(gp, "timeout"));
2776ac5fe48SPawel Jakub Dawidek 	printf("queue_count: %s\n", get_conf(gp, "queue_count"));
2786ac5fe48SPawel Jakub Dawidek 	printf(" queue_size: %s\n", get_conf(gp, "queue_size"));
2796ac5fe48SPawel Jakub Dawidek 	printf(" references: %s\n", get_conf(gp, "ref"));
28071ae6999SPawel Jakub Dawidek 	humanize_number(buf, sizeof(buf), (int64_t)pp->lg_mediasize, "",
28171ae6999SPawel Jakub Dawidek 	    HN_AUTOSCALE, HN_B | HN_NOSPACE | HN_DECIMAL);
28271ae6999SPawel Jakub Dawidek 	printf("  mediasize: %jd (%s)\n", (intmax_t)pp->lg_mediasize, buf);
2836ac5fe48SPawel Jakub Dawidek 	printf(" sectorsize: %u\n", pp->lg_sectorsize);
2846ac5fe48SPawel Jakub Dawidek 	printf("       mode: %s\n", pp->lg_mode);
2856ac5fe48SPawel Jakub Dawidek 	printf("\n");
2866ac5fe48SPawel Jakub Dawidek }
2876ac5fe48SPawel Jakub Dawidek 
2886ac5fe48SPawel Jakub Dawidek void
2896ac5fe48SPawel Jakub Dawidek g_gate_list(int unit, int verbose)
2906ac5fe48SPawel Jakub Dawidek {
2916ac5fe48SPawel Jakub Dawidek 	struct gmesh mesh;
2926ac5fe48SPawel Jakub Dawidek 	struct gclass *class;
2936ac5fe48SPawel Jakub Dawidek 	struct ggeom *gp;
2946ac5fe48SPawel Jakub Dawidek 	char name[64];
2956ac5fe48SPawel Jakub Dawidek 	int error;
2966ac5fe48SPawel Jakub Dawidek 
2976ac5fe48SPawel Jakub Dawidek 	error = geom_gettree(&mesh);
2986ac5fe48SPawel Jakub Dawidek 	if (error != 0)
2996ac5fe48SPawel Jakub Dawidek 		exit(EXIT_FAILURE);
3006ac5fe48SPawel Jakub Dawidek 	class = find_class(&mesh, G_GATE_CLASS_NAME);
3016ac5fe48SPawel Jakub Dawidek 	if (class == NULL) {
3026ac5fe48SPawel Jakub Dawidek 		geom_deletetree(&mesh);
3036ac5fe48SPawel Jakub Dawidek 		exit(EXIT_SUCCESS);
3046ac5fe48SPawel Jakub Dawidek 	}
3056ac5fe48SPawel Jakub Dawidek 	if (unit >= 0) {
3066ac5fe48SPawel Jakub Dawidek 		snprintf(name, sizeof(name), "%s%d", G_GATE_PROVIDER_NAME,
3076ac5fe48SPawel Jakub Dawidek 		    unit);
3086ac5fe48SPawel Jakub Dawidek 	}
3096ac5fe48SPawel Jakub Dawidek 	LIST_FOREACH(gp, &class->lg_geom, lg_geom) {
3106ac5fe48SPawel Jakub Dawidek 		if (unit != -1 && strcmp(gp->lg_name, name) != 0)
3116ac5fe48SPawel Jakub Dawidek 			continue;
3126ac5fe48SPawel Jakub Dawidek 		show_config(gp, verbose);
3136ac5fe48SPawel Jakub Dawidek 	}
3146ac5fe48SPawel Jakub Dawidek 	geom_deletetree(&mesh);
3156ac5fe48SPawel Jakub Dawidek 	exit(EXIT_SUCCESS);
3166ac5fe48SPawel Jakub Dawidek }
3176ac5fe48SPawel Jakub Dawidek #endif	/* LIBGEOM */
3186ac5fe48SPawel Jakub Dawidek 
3196ac5fe48SPawel Jakub Dawidek in_addr_t
3206ac5fe48SPawel Jakub Dawidek g_gate_str2ip(const char *str)
3216ac5fe48SPawel Jakub Dawidek {
3226ac5fe48SPawel Jakub Dawidek 	struct hostent *hp;
3236ac5fe48SPawel Jakub Dawidek 	in_addr_t ip;
3246ac5fe48SPawel Jakub Dawidek 
3256ac5fe48SPawel Jakub Dawidek 	ip = inet_addr(str);
3266ac5fe48SPawel Jakub Dawidek 	if (ip != INADDR_NONE) {
3276ac5fe48SPawel Jakub Dawidek 		/* It is a valid IP address. */
3286ac5fe48SPawel Jakub Dawidek 		return (ip);
3296ac5fe48SPawel Jakub Dawidek 	}
3306ac5fe48SPawel Jakub Dawidek 	/* Check if it is a valid host name. */
3316ac5fe48SPawel Jakub Dawidek 	hp = gethostbyname(str);
3326ac5fe48SPawel Jakub Dawidek 	if (hp == NULL)
3336ac5fe48SPawel Jakub Dawidek 		return (INADDR_NONE);
33486bfa454SPawel Jakub Dawidek 	return (((struct in_addr *)(void *)hp->h_addr)->s_addr);
3356ac5fe48SPawel Jakub Dawidek }
336