pax_global_header00006660000000000000000000000064134347672360014531gustar00rootroot0000000000000052 comment=71b24e3ac92d76e9d6397b2b94ecccdf94414ffd libnfsidmap-regex-1.0/000077500000000000000000000000001343476723600147715ustar00rootroot00000000000000libnfsidmap-regex-1.0/.gitignore000066400000000000000000000006561343476723600167700ustar00rootroot00000000000000# Prerequisites *.d # Object files *.o *.ko *.obj *.elf # Linker output *.ilk *.map *.exp # Precompiled Headers *.gch *.pch # Libraries *.lib *.a *.la *.lo # Shared objects (inc. Windows DLLs) *.dll *.so *.so.* *.dylib # Executables *.exe *.out *.app *.i*86 *.x86_64 *.hex # Debug files *.dSYM/ *.su *.idb *.pdb # Kernel Module Compile Results *.mod* *.cmd .tmp_versions/ modules.order Module.symvers Mkfile.old dkms.conf libnfsidmap-regex-1.0/AUTHORS000066400000000000000000000000521343476723600160360ustar00rootroot00000000000000Stefan Walter libnfsidmap-regex-1.0/ChangeLog000066400000000000000000000000561343476723600165440ustar00rootroot000000000000002017-05-26: started 2017-06-20: first release libnfsidmap-regex-1.0/LICENSE000066400000000000000000000030751343476723600160030ustar00rootroot00000000000000BSD 3-Clause License Copyright (c) 2017 Stefan Walter . Copyright (c) 2008 David Härdeman . All rights reserved. Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met: * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer. * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution. * Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. libnfsidmap-regex-1.0/Makefile.am000066400000000000000000000004741343476723600170320ustar00rootroot00000000000000ACLOCAL_AMFLAGS = -I m4 lib_LTLIBRARIES = regex.la regex_la_SOURCES = regex.c regex_la_LDFLAGS = -module -avoid-version regex_la_CFLAGS = $(AM_CFLAGS) regex_la_LIBADD = -lnfsidmap -lini_config man5_MANS = libnfsidmap-regex.5 EXTRA_DIST = $(man5_MANS) nfsidmap_internal.h pkgconfigdir=$(libdir)/pkgconfig libnfsidmap-regex-1.0/NEWS000066400000000000000000000000341343476723600154650ustar00rootroot00000000000000There is currently no news. libnfsidmap-regex-1.0/README000066400000000000000000000002351343476723600156510ustar00rootroot00000000000000Plugin for libnfsidmap that uses regular expressions to parse remote user and group names. See 'man libnfsidmap-regex' for more details after installation. libnfsidmap-regex-1.0/README.md000066400000000000000000000062171343476723600162560ustar00rootroot00000000000000## NAME regex - libnfsidmap plugin using regex based mapping ## SYNOPSIS Plugin for libnfsidmap. Uses regex to map NFSv4 names to and from ids. ## DESCRIPTION The regex plugin parses NFSv4 user and groups names using regex to extract the local user or group. NFSv4 names are created by adding constant strings before and after the local user and group names. It additionally supports an additional configuration file for static group mappings. ## CONFIGURATION The configuration for the plugin is in a new `[Regex]` section in `/etc/idmapd.conf` that may contain lines of the form variable = value The recognized variables are as follows: ### [Regex] section variables #### User-Regex Regular expression that extracts the local user name from an NFSv4 name. Several expressions can be concatenated with '|'. The first match will be used. #### Group-Regex Regular expression that extracts the local group name from an NFSv4 name. Several expressions can be concatenated with '|'. The first match will be used. #### Prepend-Before-User Constant string to put before a local user name when building an NFSv4 name. (Default: none) #### Append-After-User Constant string to put after a local user name when building an NFSv4 name. (Default: none) #### Prepend-Before-Group Constant string to put before a local group name when building an NFSv4 name. (Default: none) #### Append-After-Group Constant string to put before a local group name when building an NFSv4 name. (Default: none) #### Group-Name-Prefix Constant string that is prepended to a local group name when converting it to an NFSv4 name. If an NFSv4 group name has this prefix it is removed when converting it to a local group name. Is not applied if a static group mapping matches. This allows to organize the group name space in a central directory that is used for a central NFS4 server and use short group names in the local directory used in organizational units. #### Group-Map-File File name of an INI style file containing static group mappings. (Default: /etc/idmapd.conf) #### Group-Map-Section Section in the static group mapping file that contains the mappings. The name must be all lower case. The section name in the file is case sensitive. (Default: groups) ## STATIC MAPPING The Group-Map-File and Group-Map-Section variables can be used to define a section containing mappings of the form nfs4 group = local group The default is to have a `[Groups]` section in the `/etc/idmapd.conf` file. For both the NFS4 and local group name the Group-Name-Prefix prefix is not applied or removed. ## EXAMPLES An example `[Regex]` and `[Groups]` section in the `/etc/idmapd.conf` file: [Regex] User-Regex = ^EXAMPLE\([^@]+)@EXAMPLE.ORG$ Group-Regex = ^([^@]+)@EXAMPLE.ORG@EXAMPLE.ORG$|^EXAMPLE\([^@]+)@EXAMPLE.ORG$ Prepend-Before-User = EXAMPLE Append-After-User = @EXAMPLE.ORG #Prepend-Before-Group = Append-After-Group = @example.org@example.org Group-Name-Prefix = sales- [Groups] domain users = users ## SEE ALSO idmapd.conf(5) ## BUGS Report bugs to libnfsidmap-regex-1.0/autogen.sh000077500000000000000000000001131343476723600167650ustar00rootroot00000000000000#! /bin/sh libtoolize aclocal \ && automake --add-missing \ && autoconf libnfsidmap-regex-1.0/configure.ac000066400000000000000000000016051343476723600172610ustar00rootroot00000000000000# Process this file with autoconf to produce a configure script. AC_PREREQ([2.63]) AC_INIT([libnfsidmap-regex],[0.1],[stefan.walter@inf.ethz.ch]) AC_CONFIG_MACRO_DIR([m4]) AM_INIT_AUTOMAKE LT_INIT # Checks for programs. AC_PROG_CC # Checks for header files. AC_HEADER_STDC AC_CHECK_HEADERS([nfsidmap.h stdlib.h string.h unistd.h errno.h]) # Checks for typedefs, structures, and compiler characteristics. AC_TYPE_UID_T AC_TYPE_SIZE_T # Checks for library functions. AC_FUNC_MALLOC AC_CHECK_FUNCS([strchr strdup]) #Set the NFSv4 idmapd library install path AC_ARG_ENABLE([nfsidmaplibdir], [AS_HELP_STRING([--enable-nfsidmaplibdir], [Where to install libnfsidmap libraries ($libdir/libnfsidmap)])], [nfsidmaplibdir=$enableval], [nfsidmaplibdir=$libdir/libnfsidmap]) AC_SUBST(nfsidmaplibdir) AC_CONFIG_FILES([Makefile]) AC_OUTPUT libnfsidmap-regex-1.0/libnfsidmap-regex.5000066400000000000000000000071341343476723600204640ustar00rootroot00000000000000.\" .\" libnfsidmap-regex(5) .\" .\" COPYRIGHT (c) 2017 .\" ETH Zurich .\" ALL RIGHTS RESERVED .\" .TH libnfsidmap-regex 5 "29 May 2017" .SH NAME regex \- libnfsidmap plugin using regex based mapping .SH SYNOPSIS Plugin for libnfsidmap. Uses regex to map NFSv4 names to and from ids. .SH DESCRIPTION The .B regex plugin parses NFSv4 user and groups names using regex to extract the local user or group. NFSv4 names are created by adding constant strings before and after the local user and group names. It additionally supports an additional configuration file for static group mappings. .SH CONFIGURATION The configuration for the plugin is in a new [Regex] section in .I /etc/idmapd.conf that may contain lines of the form .nf variable = value .fi The recognized variables are as follows: .SS "[Regex] section variables" .nf .fi .TP .B User-Regex Regular expression that extracts the local user name from an NFSv4 name. Several expressions can be concatenated with '|'. The first match will be used. .TP .B Group-Regex Regular expression that extracts the local group name from an NFSv4 name. Several expressions can be concatenated with '|'. The first match will be used. .TP .B Prepend-Before-User Constant string to put before a local user name when building an NFSv4 name. (Default: none) .TP .B Append-After-User Constant string to put after a local user name when building an NFSv4 name. (Default: none) .TP .B Prepend-Before-Group Constant string to put before a local group name when building an NFSv4 name. (Default: none) .TP .B Append-After-Group Constant string to put before a local group name when building an NFSv4 name. (Default: none) .TP .B Group-Name-Prefix Constant string that is prepended to a local group name when converting it to an NFSv4 name. If an NFSv4 group name has this prefix it is removed when converting it to a local group name. IS not applied if a static group mapping matches. This allows to organize the group name space in a central directory that is used for a central NFS4 server and use short group names in the local directory used in organizational units. .TP .B Group-Name-No-Prefix-Regex Regular expression to exclude groups from adding and removing the prefix set by Group-Name-Prefix. The regular expression must match both the remote and local group names. (Default: none) .TP .B Group-Map-File File name of an INI style file containing static group mappings. (Default: /etc/idmapd.conf) .TP .B Group-Map-Section Section in the static group mapping file that contains the mappings. The name must be all lower case. The section name in the file is case sensitive. (Default: groups) .nf .SH STATIC MAPPING The .B Group-Map-File and .B Group-Map-Section variables can be used to define a section containing mappings of the form .nf nfs4 group = local group .fi The default is to have a .B [Groups] section in the .I /etc/idmapd.conf file. For both the NFS4 and local group name the .B Group-Name-Prefix prefix is not applied or removed. .nf .SH EXAMPLES An example .B [Regex] and .B [Groups] section in the .I /etc/idmapd.conf file: .nf [Regex] User-Regex = ^EXAMPLE\\([^@]+)@EXAMPLE.ORG$ Group-Regex = ^([^@]+)@EXAMPLE.ORG@EXAMPLE.ORG$|^EXAMPLE\\([^@]+)@EXAMPLE.ORG$ Prepend-Before-User = EXAMPLE\ Append-After-User = @EXAMPLE.ORG #Prepend-Before-Group = Append-After-Group = @example.org@example.org Group-Name-Prefix = sales- Group-Name-No-Prefix-Regex = -group$ [Groups] domain users = users .fi .SH SEE ALSO .BR idmapd.conf (5) .\".SH COMPATIBILITY .\".SH STANDARDS .\".SH ACKNOWLEDGEMENTS .\".SH AUTHORS .\".SH HISTORY .SH BUGS Report bugs to .\".SH CAVEATS libnfsidmap-regex-1.0/libnfsidmap-regex.spec000066400000000000000000000025071343476723600212510ustar00rootroot00000000000000%define work_name %{name}-%{version} %define build_timestamp %(date +"%Y%m%d") Name: libnfsidmap-regex Version: %{build_timestamp} Release: 1 License: BSD Url: https://github.com/isginf/libnfsidmap-regex BuildRequires: coreutils git libnfsidmap-devel BuildRequires: libtool automake autoconf libini_config-devel Requires: libini_config Summary: libnfsidmap plugin using regex based mapping %description The regex plugin parses NFSv4 user and groups names using regex to extract the local user or group. NFSv4 names are created by adding constant strings before and after the local user and group names. %prep rm -rf %{work_name} git clone %{url}.git %{work_name} %build cd %{work_name} sh autogen.sh %configure make %{?_smp_mflags} gzip -9 libnfsidmap-regex.5 %install cd %{work_name} rm -rf %{buildroot} mkdir -p %{buildroot}/lib64/libnfsidmap/ mkdir -p %{buildroot}/usr/share/man/man5/ cp .libs/regex.so %{buildroot}/lib64/libnfsidmap/ cp libnfsidmap-regex.5.gz %{buildroot}/usr/share/man/man5/ %files /lib64/libnfsidmap/regex.so /usr/share/man/man5/libnfsidmap-regex.5.gz %changelog * Tue Feb 27 2018 stefan.walter@inf.ethz.ch - Changed from iniparser to libini_config. - Build RPM directly from git. * Tue Jun 20 2017 stefan.walter@inf.ethz.ch - First initial package for linux. libnfsidmap-regex-1.0/nfsidmap_internal.h000066400000000000000000000056041343476723600206440ustar00rootroot00000000000000/* * nfsidmap_internal.h * * nfs idmapping library, primarily for nfs4 client/server kernel idmapping * and for userland nfs4 idmapping by acl libraries. * * Copyright (c) 2004 The Regents of the University of Michigan. * All rights reserved. * * Andy Adamson * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of the University nor the names of its * contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ struct trans_func { char *name; int (*init)(void); int (*princ_to_ids)(char *secname, char *princ, uid_t *uid, gid_t *gid, extra_mapping_params **ex); int (*name_to_uid)(char *name, uid_t *uid); int (*name_to_gid)(char *name, gid_t *gid); int (*uid_to_name)(uid_t uid, char *domain, char *name, size_t len); int (*gid_to_name)(gid_t gid, char *domain, char *name, size_t len); int (*gss_princ_to_grouplist)(char *secname, char *princ, gid_t *groups, int *ngroups, extra_mapping_params **ex); }; extern int idmap_verbosity; extern nfs4_idmap_log_function_t idmap_log_func; struct trans_func *libnfsidmap_plugin_init(void); /* Level zero always prints, others print depending on verbosity level */ #define IDMAP_LOG(LVL, MSG) \ do { if (LVL <= idmap_verbosity) (*idmap_log_func)MSG; } while (0) #ifndef UNUSED #ifdef __GNUC__ #define UNUSED(foo) UNUSED_ ## foo __attribute__((__unused__)) #else #define UNUSED(foo) UNUSED_ ## foo #endif #endif extern const char *nfsidmap_conf_path; extern const char *nfsidmap_config_get(const char *section, const char *tag); libnfsidmap-regex-1.0/regex.c000066400000000000000000000345461343476723600162630ustar00rootroot00000000000000/* * regex.c * * idmapping functions using regex for gss principals. * * Copyright (c) 2017 Stefan Walter . * Copyright (c) 2008 David Härdeman . * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. * 3. Neither the name of the University nor the names of its * contributors may be used to endorse or promote products derived * from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ #include #include #include #include #include #include #include #include #include #include #include "nfsidmap.h" #include "nfsidmap_internal.h" #define MAX_MATCHES 100 struct ini_cfgfile * dict_file; struct ini_cfgobj * dict; regex_t group_re; regex_t user_re; regex_t gpx_re; int use_gpx; const char * group_prefix; const char * group_name_prefix; const char * group_suffix; const char * user_prefix; const char * user_suffix; const char * group_map_file; const char * group_map_section; char empty = '\0'; size_t group_name_prefix_length; static char * conf_file = "/etc/idmapd.conf"; static char * conf_section = "groups"; struct pwbuf { struct passwd pwbuf; char buf[1]; }; struct grbuf { struct group grbuf; char buf[1]; }; static char *get_default_domain(void) { static char default_domain[NFS4_MAX_DOMAIN_LEN] = ""; if (default_domain[0] == 0) { nfs4_get_default_domain(NULL, default_domain, NFS4_MAX_DOMAIN_LEN); } return default_domain; } /* * Regexp Translation Methods * */ static struct passwd *regex_getpwnam(const char *name, const char *domain, int *err_p) { struct passwd *pw; struct pwbuf *buf; size_t buflen = sysconf(_SC_GETPW_R_SIZE_MAX); char *localname; size_t namelen; int err; int status; int index; regmatch_t matches[MAX_MATCHES]; buf = malloc(sizeof(*buf) + buflen); if (!buf) { err = ENOMEM; goto err; } status = regexec(&user_re, name, MAX_MATCHES, matches, 0); if (status) { IDMAP_LOG(4, ("regexp_getpwnam: user '%s' did not match regex", name)); err = ENOENT; goto err_free_buf; } for (index = 1; index < MAX_MATCHES ; index++) { if (matches[index].rm_so >= 0) break; } if (index == MAX_MATCHES) { IDMAP_LOG(4, ("regexp_getpwnam: user '%s' did not match regex", name)); err = ENOENT; goto err_free_buf; } namelen = matches[index].rm_eo - matches[index].rm_so; localname= malloc(namelen + 1); if (!localname) { err = ENOMEM; goto err_free_buf; } strncpy(localname, name+matches[index].rm_so, namelen); localname[namelen] = '\0'; again: err = getpwnam_r(localname, &buf->pwbuf, buf->buf, buflen, &pw); if (err == EINTR) goto again; if (!pw) { if (err == 0) err = ENOENT; IDMAP_LOG(4, ("regex_getpwnam: local user '%s' for '%s' not found", localname, name)); goto err_free_name; } IDMAP_LOG(4, ("regexp_getpwnam: name '%s' mapped to '%s'", name, localname)); *err_p = 0; return pw; err_free_name: free(localname); err_free_buf: free(buf); err: *err_p = err; return NULL; } static struct group *regex_getgrnam(const char *name, const char *domain, int *err_p) { struct group *gr; struct grbuf *buf; size_t buflen = sysconf(_SC_GETGR_R_SIZE_MAX); char *localgroup; char *staticgroup; char *groupname; size_t namelen; int err = 0; int index; int status; regmatch_t matches[MAX_MATCHES]; struct value_obj * vo; buf = malloc(sizeof(*buf) + buflen); if (!buf) { err = ENOMEM; goto err; } status = regexec(&group_re, name, MAX_MATCHES, matches, 0); if (status) { IDMAP_LOG(4, ("regexp_getgrnam: group '%s' did not match regex", name)); err = ENOENT; goto err_free_buf; } for (index = 1; index < MAX_MATCHES ; index++) { if (matches[index].rm_so >= 0) break; } if (index == MAX_MATCHES) { IDMAP_LOG(4, ("regexp_getgrnam: group '%s' did not match regex", name)); err = ENOENT; goto err_free_buf; } namelen = matches[index].rm_eo - matches[index].rm_so; localgroup = malloc(namelen + 1); if (!localgroup) { err = ENOMEM; goto err_free_buf; } strncpy(localgroup, name+matches[index].rm_so, namelen); localgroup[namelen] = '\0'; IDMAP_LOG(4, ("regexp_getgrnam: group '%s' after match of regex", localgroup)); if (ini_get_config_valueobj(group_map_section, localgroup, dict, INI_GET_FIRST_VALUE, &vo)) goto err_free_buf; staticgroup = ini_get_string_config_value(vo, NULL); if (staticgroup) { IDMAP_LOG(4, ("regexp_getgrnam: group '%s' matched static group '%s'", localgroup, staticgroup)); free(localgroup); groupname = localgroup = staticgroup; } else { groupname = localgroup; if (group_name_prefix_length && ! strncmp(group_name_prefix, localgroup, group_name_prefix_length)) { err = 1; if (use_gpx) err = regexec(&gpx_re, localgroup, 0, NULL, 0); if (err) { IDMAP_LOG(4, ("regexp_getgrnam: removing prefix '%s' (%d long) from group '%s'", group_name_prefix, group_name_prefix_length, localgroup)); groupname += group_name_prefix_length; } else { IDMAP_LOG(4, ("regexp_getgrnam: not removing prefix from group '%s'", localgroup)); } } } IDMAP_LOG(4, ("regexp_getgrnam: will use '%s'", groupname)); again: err = getgrnam_r(groupname, &buf->grbuf, buf->buf, buflen, &gr); if (err == EINTR) goto again; if (!gr) { if (err == 0) err = ENOENT; IDMAP_LOG(4, ("regex_getgrnam: local group '%s' for '%s' not found", groupname, name)); goto err_free_name; } IDMAP_LOG(4, ("regex_getgrnam: group '%s' mapped to '%s'", name, groupname)); free(localgroup); *err_p = 0; return gr; err_free_name: free(localgroup); err_free_buf: free(buf); err: *err_p = err; return NULL; } static int regex_gss_princ_to_ids(char *secname, char *princ, uid_t *uid, uid_t *gid, extra_mapping_params **ex) { struct passwd *pw; int err; /* XXX: Is this necessary? */ if (strcmp(secname, "krb5") != 0 && strcmp(secname, "spkm3") != 0) return -EINVAL; pw = regex_getpwnam(princ, NULL, &err); if (pw) { *uid = pw->pw_uid; *gid = pw->pw_gid; free(pw); } return -err; } static int regex_gss_princ_to_grouplist(char *secname, char *princ, gid_t *groups, int *ngroups, extra_mapping_params **ex) { struct passwd *pw; int err; /* XXX: Is this necessary? */ if (strcmp(secname, "krb5") != 0 && strcmp(secname, "spkm3") != 0) return -EINVAL; pw = regex_getpwnam(princ, NULL, &err); if (pw) { if (getgrouplist(pw->pw_name, pw->pw_gid, groups, ngroups) < 0) err = -ERANGE; free(pw); } return -err; } static int regex_name_to_uid(char *name, uid_t *uid) { struct passwd *pw; int err; pw = regex_getpwnam(name, NULL, &err); if (pw) { *uid = pw->pw_uid; free(pw); } return -err; } static int regex_name_to_gid(char *name, gid_t *gid) { struct group *gr; int err; gr = regex_getgrnam(name, NULL, &err); if (gr) { *gid = gr->gr_gid; free(gr); } return -err; } static int write_name(char *dest, char *localname, const char* name_prefix, const char *prefix, const char *suffix, size_t len) { if (strlen(localname) + strlen(name_prefix) + strlen(prefix) + strlen(suffix) + 1 > len) { return -ENOMEM; /* XXX: Is there an -ETOOLONG? */ } strcpy(dest, prefix); strcat(dest, name_prefix); strcat(dest, localname); strcat(dest, suffix); IDMAP_LOG(4, ("write_name: will use '%s'", dest)); return 0; } static int regex_uid_to_name(uid_t uid, char *domain, char *name, size_t len) { struct passwd *pw = NULL; struct passwd pwbuf; char *buf; size_t buflen = sysconf(_SC_GETPW_R_SIZE_MAX); int err = -ENOMEM; buf = malloc(buflen); if (!buf) goto out; if (domain == NULL) domain = get_default_domain(); err = -getpwuid_r(uid, &pwbuf, buf, buflen, &pw); if (pw == NULL) err = -ENOENT; if (err) goto out_buf; err = write_name(name, pw->pw_name, &empty, user_prefix, user_suffix, len); out_buf: free(buf); out: return err; } static int regex_gid_to_name(gid_t gid, char *domain, char *name, size_t len) { struct group *gr = NULL; struct group grbuf; char *buf; const char *name_prefix; size_t buflen = sysconf(_SC_GETGR_R_SIZE_MAX); int err; int index; int count; char ** keys; char * value; char * groupname = NULL; struct value_obj * vo; do { err = -ENOMEM; buf = malloc(buflen); if (!buf) goto out; err = -getgrgid_r(gid, &grbuf, buf, buflen, &gr); if (gr == NULL && !err) err = -ENOENT; if (err == -ERANGE) { buflen *= 2; free(buf); } } while (err == -ERANGE); if (err) goto out_buf; keys = ini_get_attribute_list(dict, group_map_section, &count, &err); if (err) goto out_buf; for (index = 0; index < count; index++) { if (ini_get_config_valueobj(group_map_section, keys[index], dict, INI_GET_FIRST_VALUE, &vo)) goto out_ini; value = ini_get_string_config_value(vo, NULL); if (value != NULL && ! strcmp(gr->gr_name,value) ) { free(value); groupname = keys[index]; IDMAP_LOG(4, ("regex_gid_to_name: match '%s' -> '%s'", gr->gr_name, groupname)); break; } free(value); } if (groupname) { name_prefix = ∅ } else { groupname = gr->gr_name; name_prefix = group_name_prefix; if (group_name_prefix_length) { if(! strncmp(group_name_prefix, groupname, group_name_prefix_length)) { name_prefix = ∅ } else if (use_gpx) { err = regexec(&gpx_re, groupname, 0, NULL, 0); if (!err) { IDMAP_LOG(4, ("regex_gid_to_name: not adding prefix to group '%s'", groupname)); name_prefix = ∅ } } } } err = write_name(name, groupname, name_prefix, group_prefix, group_suffix, len); out_ini: ini_free_attribute_list(keys); out_buf: free(buf); out: return err; } static int regex_init() { char *string; int status; string = nfsidmap_config_get("Regex", "User-Regex"); if (!string) { warnx("regex_init: regex for user mapping missing"); goto error1; } status = regcomp(&user_re, string, REG_EXTENDED|REG_ICASE); if (status) { warnx("regex_init: compiling regex for user mapping failed with status %u", status); goto error1; } string = nfsidmap_config_get("Regex", "Group-Regex"); if (!string) { warnx("regex_init: regex for group mapping missing"); goto error2; } status = regcomp(&group_re, string, REG_EXTENDED|REG_ICASE); if (status) { warnx("regex_init: compiling regex for group mapping failed with status %u", status); goto error2; } group_name_prefix = nfsidmap_config_get("Regex", "Group-Name-Prefix"); if (!group_name_prefix) { group_name_prefix = ∅ } group_name_prefix_length = strlen(group_name_prefix); user_prefix = nfsidmap_config_get("Regex", "Prepend-Before-User"); if (!user_prefix) { user_prefix = ∅ } user_suffix = nfsidmap_config_get("Regex", "Append-After-User"); if (!user_suffix) { user_suffix = ∅ } group_prefix = nfsidmap_config_get("Regex", "Prepend-Before-Group"); if (!group_prefix) { group_prefix = ∅ } group_suffix = nfsidmap_config_get("Regex", "Append-After-Group"); if (!group_suffix) { group_suffix = ∅ } group_map_file = nfsidmap_config_get("Regex", "Group-Map-File"); if (!group_map_file) { group_map_file = conf_file; } group_map_section = nfsidmap_config_get("Regex", "Group-Map-Section"); if (!group_map_section) { group_map_section = conf_section; } string = nfsidmap_config_get("Regex", "Group-Name-No-Prefix-Regex"); use_gpx = 0; if (string) { status = regcomp(&gpx_re, string, REG_EXTENDED|REG_ICASE); if (status) { warnx("regex_init: compiling regex for group prefix exclusion failed with status %u", status); goto error3; } use_gpx = 1; } if (ini_config_create(&dict)) goto error4; if (ini_config_file_open(group_map_file, 0, &dict_file)) goto error5; if (ini_config_parse(dict_file, INI_STOP_ON_ERROR, INI_MV1S_ALLOW, 0, dict)) goto error6; return 0; error6: ini_config_file_destroy(dict_file); error5: ini_config_destroy(dict); error4: if (use_gpx) regfree(&gpx_re); error3: regfree(&group_re); error2: regfree(&user_re); error1: return -EINVAL; } struct trans_func regex_trans = { .name = "regex", .init = regex_init, .name_to_uid = regex_name_to_uid, .name_to_gid = regex_name_to_gid, .uid_to_name = regex_uid_to_name, .gid_to_name = regex_gid_to_name, .princ_to_ids = regex_gss_princ_to_ids, .gss_princ_to_grouplist = regex_gss_princ_to_grouplist, }; struct trans_func *libnfsidmap_plugin_init() { return (®ex_trans); }