Example #1
0
/*
 * __nis_path
 *
 * Given two path strings, *from and *to, work out the list of names
 * between them. The length of that path and the pointer to the list
 * of pointers to the name strings are returned to the caller using
 * path_length and namesp. As the names list is a pointer to a list of
 * pointers, the caller must pass the address of the pointer to the
 * pointer to the list of pointers, hence the unusual "char ***"
 * type. It is the callers responsibility to free **namesp.
 */
nis_error
__nis_path(char *from, char *to, int *path_length, char ***namesp)
{
	int i;
	int n;
	int start;
	int end;
	int st, dircmp, lastdircmp;
	char *tfrom = from;
	char *tto = to;
	char **names;

	dircmp = st = nis_dir_cmp(from, to);
	if (st == BAD_NAME)
		return (NIS_BADNAME);

	/* figure out how long path is */
	n = 0;
	if (st == HIGHER_NAME) {
		while ((dircmp = nis_dir_cmp(from, to)) == HIGHER_NAME) {
			n++;
			to = nis_domain_of(to);
		}
		if (dircmp != SAME_NAME) {
			/* Unrecoverable error */
			dircmp = BAD_NAME;
		}
	} else if (st == LOWER_NAME) {
		from = nis_domain_of(from);
		while ((dircmp = nis_dir_cmp(from, to)) == LOWER_NAME) {
			n++;
			from = nis_domain_of(from);
		}
		if (dircmp != SAME_NAME) {
			/* Unrecoverable error */
			dircmp = BAD_NAME;
		}
		n++;	/* include actual target */
	} else if (st == NOT_SEQUENTIAL) {
		/* names are not sequential */
		from = nis_domain_of(from);
		while ((dircmp = nis_dir_cmp(from, to)) == NOT_SEQUENTIAL) {
			n++;
			from = nis_domain_of(from);
		}
		n++;	/* include common parent */
		lastdircmp = dircmp; /* Handle HIGHER or LOWER */
		while ((dircmp = nis_dir_cmp(from, to)) == lastdircmp) {
			n++;
			lastdircmp = dircmp;
			to = nis_domain_of(to);
		}
		if (dircmp != SAME_NAME) {
			/* Unrecoverable error */
			dircmp = BAD_NAME;
		}
	}

	if (dircmp == BAD_NAME) {
		syslog(LOG_WARNING, "__nis_path: Unable to walk "
		    "from %s to %s", tfrom, tto);
		return (NIS_BADNAME);
	}

	names = malloc(n * sizeof (char *));
	if (names == NULL)
		return (NIS_NOMEMORY);

	start = 0;
	end = n;
	from = tfrom;
	to = tto;

	/*
	 * Go through again, this time storing names.
	 * We shouldn't need to check the loops will terminate
	 * on the SAME_NAME condition as we've already checked for
	 * errors in the previous loop.
	 */
	if (st == HIGHER_NAME) {
		while (nis_dir_cmp(from, to) != SAME_NAME) {
			names[--end] = strdup(to);
			to = nis_domain_of(to);
		}
	} else if (st == LOWER_NAME) {
		from = nis_domain_of(from);
		while (nis_dir_cmp(from, to) != SAME_NAME) {
			names[start++] = strdup(from);
			from = nis_domain_of(from);
		}
		names[start++] = strdup(to);	/* include actual target */
	} else if (st == NOT_SEQUENTIAL) {
		/* names are not sequential */
		from = nis_domain_of(from);
		while (nis_dir_cmp(from, to) == NOT_SEQUENTIAL) {
			names[start++] = strdup(from);
			from = nis_domain_of(from);
		}
		names[start++] = strdup(from);	/* include common parent */
		while (nis_dir_cmp(from, to) != SAME_NAME) {
			names[--end] = strdup(to);
			to = nis_domain_of(to);
		}
	}

	/* make sure all of the allocations were successful */
	for (i = 0; i < n; i++) {
		if (names[i] == NULL) {
			__nis_path_free(names, n);
			names = NULL;
			break;
		}
	}

	/* Set the return values */

	*path_length = n;
	*namesp = names;

	return (NIS_SUCCESS);
}
Example #2
0
/*
 * Convert host to network-name
 * This routine returns following netnames given the host and domain
 * arguments defined below: (domainname=y.z)
 *	  Arguments
 *	host	domain		netname
 *	----	------		-------
 *	-	-		[email protected] (hostname=m)
 *	-	a.b		[email protected] (hostname=m)
 *	-	-		[email protected] (hostname=m.w.x)
 *	-	a.b		[email protected] (hostname=m.w.x)
 *	h	-		[email protected]
 *	h	a.b		[email protected]
 *	h.w.x	-		[email protected]
 *	h.w.x	a.b		[email protected]
 */
int
host2netname(char netname[MAXNETNAMELEN + 1], const char *host,
							const char *domain)
{
	char *p;
	char hostname[MAXHOSTNAMELEN + 1];
	char domainname[MAXHOSTNAMELEN + 1];
	char *dot_in_host;
	int i;
	size_t len;

	netname[0] = '\0';  /* make null first (no need for memset) */

	if (host == NULL) {
		(void) strncpy(hostname, nis_local_host(), sizeof (hostname));
		p = (char *)strchr(hostname, '.');
		if (p) {
			*p++ = '\0';
			/* if no domain passed, use tail of nis_local_host() */
			if (domain == NULL) {
				domain = p;
			}
		}
	} else {
		len = strlen(host);
		if (len >= sizeof (hostname)) {
			return (0);
		}
		(void) strcpy(hostname, host);
	}

	dot_in_host = (char *)strchr(hostname, '.');
	if (domain == NULL) {
		p = dot_in_host;
		if (p) {
			p = (char *)nis_domain_of(hostname);
			len = strlen(p);
			if (len >= sizeof (domainname)) {
				return (0);
			}
			(void) strcpy(domainname, p);
		} else {
			domainname[0] = NULL;
			if (getdomainname(domainname, MAXHOSTNAMELEN) < 0)
				return (0);
		}
	} else {
		len = strlen(domain);
		if (len >= sizeof (domainname)) {
			return (0);
		}
		(void) strcpy(domainname, domain);
	}

	i = strlen(domainname);
	if (i == 0)
		/* No domainname */
		return (0);
	if (domainname[i - 1] == '.')
		domainname[i - 1] = 0;

	if (dot_in_host) {  /* strip off rest of name */
		*dot_in_host = '\0';
	}

	if ((strlen(domainname) + strlen(hostname) + OPSYS_LEN + 3)
	    > (size_t)MAXNETNAMELEN) {
		return (0);
	}

	(void) snprintf(netname, MAXNETNAMELEN + 1,
	    "%s.%s@%s", OPSYS, hostname, domainname);
	return (1);
}