Beispiel #1
0
int
openpam_configure(pam_handle_t *pamh,
	const char *service)
{
	pam_facility_t fclt;
	const char *p;

	for (p = service; *p; ++p)
		if (!is_pfcs(*p))
			return (PAM_SYSTEM_ERR);

	if (openpam_load_chain(pamh, service, PAM_FACILITY_ANY) != PAM_SUCCESS)
		goto load_err;

	for (fclt = 0; fclt < PAM_NUM_FACILITIES; ++fclt) {
		if (pamh->chains[fclt] != NULL)
			continue;
		if (openpam_load_chain(pamh, PAM_OTHER, fclt) != PAM_SUCCESS)
			goto load_err;
	}
	return (PAM_SUCCESS);
load_err:
	openpam_clear_chains(pamh->chains);
	return (PAM_SYSTEM_ERR);
}
Beispiel #2
0
/*
 * Validate a service name.
 *
 * Returns a non-zero value if the argument points to a NUL-terminated
 * string consisting entirely of characters in the POSIX portable filename
 * character set, excluding the path separator character.
 */
static int
valid_service_name(const char *name)
{
	const char *p;

	if (OPENPAM_FEATURE(RESTRICT_SERVICE_NAME)) {
		/* path separator not allowed */
		for (p = name; *p != '\0'; ++p)
			if (!is_pfcs(*p))
				return (0);
	} else {
		/* path separator allowed */
		for (p = name; *p != '\0'; ++p)
			if (!is_pfcs(*p) && *p != '/')
				return (0);
	}
	return (1);
}
Beispiel #3
0
/*
 * Parse an option.
 *
 * Returns a dynamically allocated string containing the next module
 * option, or NULL if the end of the string was reached or a disallowed
 * non-whitespace character was encountered.
 *
 * If parse_option() is successful, it updates *line to point one
 * character past the end of the option.  If it reaches the end of the
 * string, it updates *line to point to the terminating NUL character.  In
 * all other cases, it leaves *line unmodified.
 *
 * If parse_option() fails to allocate memory, it will return NULL and set
 * errno to a non-zero value.
 *
 * Allowed characters for option names are all characters in the POSIX
 * portable filename character set.  Allowed characters for option values
 * are any printable non-whitespace characters.  The option value may be
 * quoted in either single or double quotes, in which case space
 * characters and whichever quote character was not used are allowed.
 * Note that the entire value must be quoted, not just part of it.
 */
static char *
parse_option(char **line)
{
	char *nb, *ne, *vb, *ve;
	unsigned char q = 0;
	char *option;
	size_t size;

	errno = 0;
	for (nb = *line; *nb && is_lws(*nb); ++nb)
		/* nothing */ ;
	if (!*nb) {
		*line = nb;
		return (NULL);
	}
	for (ne = nb; *ne && !is_lws(*ne) && *ne != '='; ++ne)
		if (!is_pfcs(*ne))
			return (NULL);
	if (ne == nb)
		return (NULL);
	if (*ne == '=') {
		vb = ne + 1;
		if (*vb == '"' || *vb == '\'')
			q = *vb++;
		for (ve = vb;
		     *ve && *ve != q && (is_p(*ve) || (q && is_lws(*ve)));
		     ++ve)
			/* nothing */ ;
		if (q && *ve != q)
			/* non-printable character or missing endquote */
			return (NULL);
		if (q && *(ve + 1) && !is_lws(*(ve + 1)))
			/* garbage after value */
			return (NULL);
	} else {
		vb = ve = ne;
	}
	size = (ne - nb) + 1;
	if (ve > vb)
		size += (ve - vb) + 1;
	if ((option = malloc(size)) == NULL)
		return (NULL);
	strncpy(option, nb, ne - nb);
	if (ve > vb) {
		option[ne - nb] = '=';
		strncpy(option + (ne - nb) + 1, vb, ve - vb);
	}
	option[size - 1] = '\0';
	*line = q ? ve + 1 : ve;
	return (option);
}
Beispiel #4
0
/*
 * Parse the service name.
 *
 * Returns the length of the service name, or 0 if the end of the string
 * was reached or a disallowed non-whitespace character was encountered.
 *
 * If parse_service_name() is successful, it updates *service to point to
 * the first character of the service name and *line to point one
 * character past the end.  If it reaches the end of the string, it
 * updates *line to point to the terminating NUL character and leaves
 * *service unmodified.  In all other cases, it leaves both *line and
 * *service unmodified.
 *
 * Allowed characters are all characters in the POSIX portable filename
 * character set.
 */
static int
parse_service_name(char **line, char **service)
{
	char *b, *e;

	for (b = *line; *b && is_lws(*b); ++b)
		/* nothing */ ;
	if (!*b) {
		*line = b;
		return (0);
	}
	for (e = b; *e && !is_lws(*e); ++e)
		if (!is_pfcs(*e))
			return (0);
	if (e == b)
		return (0);
	*line = e;
	*service = b;
	return (e - b);
}
Beispiel #5
0
/*
 * Parse a file name.
 *
 * Returns the length of the file name, or 0 if the end of the string was
 * reached or a disallowed non-whitespace character was encountered.
 *
 * If parse_filename() is successful, it updates *filename to point to the
 * first character of the filename and *line to point one character past
 * the end.  If it reaches the end of the string, it updates *line to
 * point to the terminating NUL character and leaves *filename unmodified.
 * In all other cases, it leaves both *line and *filename unmodified.
 *
 * Allowed characters are all characters in the POSIX portable filename
 * character set, plus the path separator (forward slash).
 */
static int
parse_filename(char **line, char **filename)
{
	char *b, *e;

	for (b = *line; *b && is_lws(*b); ++b)
		/* nothing */ ;
	if (!*b) {
		*line = b;
		return (0);
	}
	for (e = b; *e && !is_lws(*e); ++e)
		if (!is_pfcs(*e) && *e != '/')
			return (0);
	if (e == b)
		return (0);
	*line = e;
	*filename = b;
	return (e - b);
}