(root)/
glibc-2.38/
nis/
nis_defaults.c
       1  /* Copyright (c) 1997-2023 Free Software Foundation, Inc.
       2     This file is part of the GNU C Library.
       3  
       4     The GNU C Library is free software; you can redistribute it and/or
       5     modify it under the terms of the GNU Lesser General Public
       6     License as published by the Free Software Foundation; either
       7     version 2.1 of the License, or (at your option) any later version.
       8  
       9     The GNU C Library is distributed in the hope that it will be useful,
      10     but WITHOUT ANY WARRANTY; without even the implied warranty of
      11     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      12     Lesser General Public License for more details.
      13  
      14     You should have received a copy of the GNU Lesser General Public
      15     License along with the GNU C Library; if not, see
      16     <https://www.gnu.org/licenses/>.  */
      17  
      18  #include <assert.h>
      19  #include <stdio.h>
      20  #include <stdlib.h>
      21  #include <string.h>
      22  #include <stdint.h>
      23  #include <sys/types.h>
      24  #include <rpc/rpc.h>
      25  #include <rpcsvc/nis.h>
      26  #include <shlib-compat.h>
      27  
      28  #define DEFAULT_TTL 43200
      29  
      30  /*
      31  ** Some functions for parsing the -D param and NIS_DEFAULTS Environ
      32  */
      33  static nis_name
      34  searchXYX (char *str, const char *what)
      35  {
      36    assert (strlen (what) == 6);
      37    assert (strncmp (str, what, 6) == 0);
      38    str += 6;			/* Points to the begin of the parameters.  */
      39  
      40    int i = 0;
      41    while (str[i] != '\0' && str[i] != ':')
      42      ++i;
      43    if (i == 0)			/* only "<WHAT>=" ? */
      44      return strdup ("");
      45  
      46    return strndup (str, i);
      47  }
      48  
      49  
      50  static nis_name
      51  searchgroup (char *str)
      52  {
      53    return searchXYX (str, "group=");
      54  }
      55  
      56  
      57  static nis_name
      58  searchowner (char *str)
      59  {
      60    return searchXYX (str, "owner=");
      61  }
      62  
      63  
      64  static uint32_t
      65  searchttl (char *str)
      66  {
      67    char buf[strlen (str) + 1];
      68    char *cptr, *dptr;
      69    uint32_t time;
      70    int i;
      71  
      72    dptr = strstr (str, "ttl=");
      73    if (dptr == NULL)		/* should (could) not happen */
      74      return DEFAULT_TTL;;
      75  
      76    dptr += 4;			/* points to the begin of the new ttl */
      77    i = 0;
      78    while (dptr[i] != '\0' && dptr[i] != ':')
      79      i++;
      80    if (i == 0)			/* only "ttl=" ? */
      81      return DEFAULT_TTL;
      82  
      83    strncpy (buf, dptr, i);
      84    buf[i] = '\0';
      85    time = 0;
      86  
      87    dptr = buf;
      88    cptr = strchr (dptr, 'd');
      89    if (cptr != NULL)
      90      {
      91        *cptr = '\0';
      92        cptr++;
      93        time += atoi (dptr) * 60 * 60 * 24;
      94        dptr = cptr;
      95      }
      96  
      97    cptr = strchr (dptr, 'h');
      98    if (cptr != NULL)
      99      {
     100        *cptr = '\0';
     101        cptr++;
     102        time += atoi (dptr) * 60 * 60;
     103        dptr = cptr;
     104      }
     105  
     106    cptr = strchr (dptr, 'm');
     107    if (cptr != NULL)
     108      {
     109        *cptr = '\0';
     110        cptr++;
     111        time += atoi (dptr) * 60;
     112        dptr = cptr;
     113      }
     114  
     115    cptr = strchr (dptr, 's');
     116    if (cptr != NULL)
     117      *cptr = '\0';
     118  
     119    time += atoi (dptr);
     120  
     121    return time;
     122  }
     123  
     124  static unsigned int
     125  searchaccess (char *str, unsigned int access)
     126  {
     127    char buf[strlen (str) + 1];
     128    char *cptr;
     129    unsigned int result = access;
     130    int i;
     131    int n, o, g, w;
     132  
     133    cptr = strstr (str, "access=");
     134    if (cptr == NULL)
     135      return 0;
     136  
     137    cptr += 7;			/* points to the begin of the access string */
     138    i = 0;
     139    while (cptr[i] != '\0' && cptr[i] != ':')
     140      i++;
     141    if (i == 0)			/* only "access=" ? */
     142      return 0;
     143  
     144    strncpy (buf, cptr, i);
     145    buf[i] = '\0';
     146  
     147    n = o = g = w = 0;
     148    cptr = buf;
     149    if (*cptr == ',') /* Fix for stupid Solaris scripts */
     150      ++cptr;
     151    while (*cptr != '\0')
     152      {
     153        switch (*cptr)
     154  	{
     155  	case 'n':
     156  	  n = 1;
     157  	  break;
     158  	case 'o':
     159  	  o = 1;
     160  	  break;
     161  	case 'g':
     162  	  g = 1;
     163  	  break;
     164  	case 'w':
     165  	  w = 1;
     166  	  break;
     167  	case 'a':
     168  	  o = g = w = 1;
     169  	  break;
     170  	case '-':
     171  	  cptr++;		/* Remove "-" from beginning */
     172  	  while (*cptr != '\0' && *cptr != ',')
     173  	    {
     174  	      switch (*cptr)
     175  		{
     176  		case 'r':
     177  		  if (n)
     178  		    result = result & ~(NIS_READ_ACC << 24);
     179  		  if (o)
     180  		    result = result & ~(NIS_READ_ACC << 16);
     181  		  if (g)
     182  		    result = result & ~(NIS_READ_ACC << 8);
     183  		  if (w)
     184  		    result = result & ~(NIS_READ_ACC);
     185  		  break;
     186  		case 'm':
     187  		  if (n)
     188  		    result = result & ~(NIS_MODIFY_ACC << 24);
     189  		  if (o)
     190  		    result = result & ~(NIS_MODIFY_ACC << 16);
     191  		  if (g)
     192  		    result = result & ~(NIS_MODIFY_ACC << 8);
     193  		  if (w)
     194  		    result = result & ~(NIS_MODIFY_ACC);
     195  		  break;
     196  		case 'c':
     197  		  if (n)
     198  		    result = result & ~(NIS_CREATE_ACC << 24);
     199  		  if (o)
     200  		    result = result & ~(NIS_CREATE_ACC << 16);
     201  		  if (g)
     202  		    result = result & ~(NIS_CREATE_ACC << 8);
     203  		  if (w)
     204  		    result = result & ~(NIS_CREATE_ACC);
     205  		  break;
     206  		case 'd':
     207  		  if (n)
     208  		    result = result & ~(NIS_DESTROY_ACC << 24);
     209  		  if (o)
     210  		    result = result & ~(NIS_DESTROY_ACC << 16);
     211  		  if (g)
     212  		    result = result & ~(NIS_DESTROY_ACC << 8);
     213  		  if (w)
     214  		    result = result & ~(NIS_DESTROY_ACC);
     215  		  break;
     216  		default:
     217  		  return (~0U);
     218  		}
     219  	      cptr++;
     220  	    }
     221  	  n = o = g = w = 0;
     222  	  break;
     223  	case '+':
     224  	  cptr++;		/* Remove "+" from beginning */
     225  	  while (*cptr != '\0' && *cptr != ',')
     226  	    {
     227  	      switch (*cptr)
     228  		{
     229  		case 'r':
     230  		  if (n)
     231  		    result = result | (NIS_READ_ACC << 24);
     232  		  if (o)
     233  		    result = result | (NIS_READ_ACC << 16);
     234  		  if (g)
     235  		    result = result | (NIS_READ_ACC << 8);
     236  		  if (w)
     237  		    result = result | (NIS_READ_ACC);
     238  		  break;
     239  		case 'm':
     240  		  if (n)
     241  		    result = result | (NIS_MODIFY_ACC << 24);
     242  		  if (o)
     243  		    result = result | (NIS_MODIFY_ACC << 16);
     244  		  if (g)
     245  		    result = result | (NIS_MODIFY_ACC << 8);
     246  		  if (w)
     247  		    result = result | (NIS_MODIFY_ACC);
     248  		  break;
     249  		case 'c':
     250  		  if (n)
     251  		    result = result | (NIS_CREATE_ACC << 24);
     252  		  if (o)
     253  		    result = result | (NIS_CREATE_ACC << 16);
     254  		  if (g)
     255  		    result = result | (NIS_CREATE_ACC << 8);
     256  		  if (w)
     257  		    result = result | (NIS_CREATE_ACC);
     258  		  break;
     259  		case 'd':
     260  		  if (n)
     261  		    result = result | (NIS_DESTROY_ACC << 24);
     262  		  if (o)
     263  		    result = result | (NIS_DESTROY_ACC << 16);
     264  		  if (g)
     265  		    result = result | (NIS_DESTROY_ACC << 8);
     266  		  if (w)
     267  		    result = result | (NIS_DESTROY_ACC);
     268  		  break;
     269  		default:
     270  		  return (~0U);
     271  		}
     272  	      cptr++;
     273  	    }
     274  	  n = o = g = w = 0;
     275  	  break;
     276  	case '=':
     277  	  cptr++;		/* Remove "=" from beginning */
     278  	  /* Clear */
     279  	  if (n)
     280  	    result = result & ~((NIS_READ_ACC + NIS_MODIFY_ACC
     281  				 + NIS_CREATE_ACC + NIS_DESTROY_ACC) << 24);
     282  
     283  	  if (o)
     284  	    result = result & ~((NIS_READ_ACC + NIS_MODIFY_ACC
     285  				 + NIS_CREATE_ACC + NIS_DESTROY_ACC) << 16);
     286  	  if (g)
     287  	    result = result & ~((NIS_READ_ACC + NIS_MODIFY_ACC
     288  				 + NIS_CREATE_ACC + NIS_DESTROY_ACC) << 8);
     289  	  if (w)
     290  	    result = result & ~(NIS_READ_ACC + NIS_MODIFY_ACC
     291  				+ NIS_CREATE_ACC + NIS_DESTROY_ACC);
     292  	  while (*cptr != '\0' && *cptr != ',')
     293  	    {
     294  	      switch (*cptr)
     295  		{
     296  		case 'r':
     297  		  if (n)
     298  		    result = result | (NIS_READ_ACC << 24);
     299  		  if (o)
     300  		    result = result | (NIS_READ_ACC << 16);
     301  		  if (g)
     302  		    result = result | (NIS_READ_ACC << 8);
     303  		  if (w)
     304  		    result = result | (NIS_READ_ACC);
     305  		  break;
     306  		case 'm':
     307  		  if (n)
     308  		    result = result | (NIS_MODIFY_ACC << 24);
     309  		  if (o)
     310  		    result = result | (NIS_MODIFY_ACC << 16);
     311  		  if (g)
     312  		    result = result | (NIS_MODIFY_ACC << 8);
     313  		  if (w)
     314  		    result = result | (NIS_MODIFY_ACC);
     315  		  break;
     316  		case 'c':
     317  		  if (n)
     318  		    result = result | (NIS_CREATE_ACC << 24);
     319  		  if (o)
     320  		    result = result | (NIS_CREATE_ACC << 16);
     321  		  if (g)
     322  		    result = result | (NIS_CREATE_ACC << 8);
     323  		  if (w)
     324  		    result = result | (NIS_CREATE_ACC);
     325  		  break;
     326  		case 'd':
     327  		  if (n)
     328  		    result = result | (NIS_DESTROY_ACC << 24);
     329  		  if (o)
     330  		    result = result | (NIS_DESTROY_ACC << 16);
     331  		  if (g)
     332  		    result = result | (NIS_DESTROY_ACC << 8);
     333  		  if (w)
     334  		    result = result | (NIS_DESTROY_ACC);
     335  		  break;
     336  		default:
     337  		  return result = (~0U);
     338  		}
     339  	      cptr++;
     340  	    }
     341  	  n = o = g = w = 0;
     342  	  break;
     343  	default:
     344  	  return result = (~0U);
     345  	}
     346        if (*cptr != '\0')
     347  	cptr++;
     348      }
     349  
     350    return result;
     351  }
     352  
     353  
     354  nis_name
     355  __nis_default_owner (char *defaults)
     356  {
     357    char *default_owner = NULL;
     358  
     359    char *cptr = defaults;
     360    if (cptr == NULL)
     361      cptr = getenv ("NIS_DEFAULTS");
     362  
     363    if (cptr != NULL)
     364      {
     365        char *dptr = strstr (cptr, "owner=");
     366        if (dptr != NULL)
     367  	{
     368  	  char *p = searchowner (dptr);
     369  	  if (p == NULL)
     370  	    return NULL;
     371  	  default_owner = strdupa (p);
     372  	  free (p);
     373  	}
     374      }
     375  
     376    return strdup (default_owner ?: nis_local_principal ());
     377  }
     378  libnsl_hidden_nolink_def (__nis_default_owner, GLIBC_2_1)
     379  
     380  
     381  nis_name
     382  __nis_default_group (char *defaults)
     383  {
     384    char *default_group = NULL;
     385  
     386    char *cptr = defaults;
     387    if (cptr == NULL)
     388      cptr = getenv ("NIS_DEFAULTS");
     389  
     390    if (cptr != NULL)
     391      {
     392        char *dptr = strstr (cptr, "group=");
     393        if (dptr != NULL)
     394  	{
     395  	  char *p = searchgroup (dptr);
     396  	  if (p == NULL)
     397  	    return NULL;
     398  	  default_group = strdupa (p);
     399  	  free (p);
     400  	}
     401      }
     402  
     403    return strdup (default_group ?: nis_local_group ());
     404  }
     405  libnsl_hidden_nolink_def (__nis_default_group, GLIBC_2_1)
     406  
     407  
     408  uint32_t
     409  __nis_default_ttl (char *defaults)
     410  {
     411    char *cptr, *dptr;
     412  
     413    if (defaults != NULL)
     414      {
     415        dptr = strstr (defaults, "ttl=");
     416        if (dptr != NULL)
     417  	return searchttl (defaults);
     418      }
     419  
     420    cptr = getenv ("NIS_DEFAULTS");
     421    if (cptr == NULL)
     422      return DEFAULT_TTL;
     423  
     424    dptr = strstr (cptr, "ttl=");
     425    if (dptr == NULL)
     426      return DEFAULT_TTL;
     427  
     428    return searchttl (cptr);
     429  }
     430  libnsl_hidden_nolink_def (__nis_default_ttl, GLIBC_2_1)
     431  
     432  /* Default access rights are ----rmcdr---r---, but we could change
     433     this with the NIS_DEFAULTS variable. */
     434  unsigned int
     435  __nis_default_access (char *param, unsigned int defaults)
     436  {
     437    unsigned int result;
     438    char *cptr;
     439  
     440    if (defaults == 0)
     441      result = 0 | OWNER_DEFAULT | GROUP_DEFAULT | WORLD_DEFAULT;
     442    else
     443      result = defaults;
     444  
     445    if (param != NULL && strstr (param, "access=") != NULL)
     446      result = searchaccess (param, result);
     447    else
     448      {
     449        cptr = getenv ("NIS_DEFAULTS");
     450        if (cptr != NULL && strstr (cptr, "access=") != NULL)
     451  	result = searchaccess (cptr, result);
     452      }
     453  
     454    return result;
     455  }
     456  libnsl_hidden_nolink_def (__nis_default_access, GLIBC_2_1)