(root)/
coreutils-9.4/
src/
printenv.c
       1  /* printenv -- print all or part of environment
       2     Copyright (C) 1989-2023 Free Software Foundation, Inc.
       3  
       4     This program is free software: you can redistribute it and/or modify
       5     it under the terms of the GNU General Public License as published by
       6     the Free Software Foundation, either version 3 of the License, or
       7     (at your option) any later version.
       8  
       9     This program 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
      12     GNU General Public License for more details.
      13  
      14     You should have received a copy of the GNU General Public License
      15     along with this program.  If not, see <https://www.gnu.org/licenses/>.  */
      16  
      17  /* Usage: printenv [variable...]
      18  
      19     If no arguments are given, print the entire environment.
      20     If one or more variable names are given, print the value of
      21     each one that is set, and nothing for ones that are not set.
      22  
      23     Exit status:
      24     0 if all variables specified were found
      25     1 if not
      26     2 if some other error occurred
      27  
      28     David MacKenzie and Richard Mlynarik */
      29  
      30  #include <config.h>
      31  #include <stdio.h>
      32  #include <sys/types.h>
      33  #include <getopt.h>
      34  
      35  #include "system.h"
      36  
      37  /* Exit status for syntax errors, etc.  */
      38  enum { PRINTENV_FAILURE = 2 };
      39  
      40  /* The official name of this program (e.g., no 'g' prefix).  */
      41  #define PROGRAM_NAME "printenv"
      42  
      43  #define AUTHORS \
      44    proper_name ("David MacKenzie"), \
      45    proper_name ("Richard Mlynarik")
      46  
      47  static struct option const longopts[] =
      48  {
      49    {"null", no_argument, nullptr, '0'},
      50    {GETOPT_HELP_OPTION_DECL},
      51    {GETOPT_VERSION_OPTION_DECL},
      52    {nullptr, 0, nullptr, 0}
      53  };
      54  
      55  void
      56  usage (int status)
      57  {
      58    if (status != EXIT_SUCCESS)
      59      emit_try_help ();
      60    else
      61      {
      62        printf (_("\
      63  Usage: %s [OPTION]... [VARIABLE]...\n\
      64  Print the values of the specified environment VARIABLE(s).\n\
      65  If no VARIABLE is specified, print name and value pairs for them all.\n\
      66  \n\
      67  "),
      68                program_name);
      69        fputs (_("\
      70    -0, --null     end each output line with NUL, not newline\n\
      71  "), stdout);
      72        fputs (HELP_OPTION_DESCRIPTION, stdout);
      73        fputs (VERSION_OPTION_DESCRIPTION, stdout);
      74        printf (USAGE_BUILTIN_WARNING, PROGRAM_NAME);
      75        emit_ancillary_info (PROGRAM_NAME);
      76      }
      77    exit (status);
      78  }
      79  
      80  int
      81  main (int argc, char **argv)
      82  {
      83    char **env;
      84    char *ep, *ap;
      85    int i;
      86    bool ok;
      87    int optc;
      88    bool opt_nul_terminate_output = false;
      89  
      90    initialize_main (&argc, &argv);
      91    set_program_name (argv[0]);
      92    setlocale (LC_ALL, "");
      93    bindtextdomain (PACKAGE, LOCALEDIR);
      94    textdomain (PACKAGE);
      95  
      96    initialize_exit_failure (PRINTENV_FAILURE);
      97    atexit (close_stdout);
      98  
      99    while ((optc = getopt_long (argc, argv, "+iu:0", longopts, nullptr)) != -1)
     100      {
     101        switch (optc)
     102          {
     103          case '0':
     104            opt_nul_terminate_output = true;
     105            break;
     106          case_GETOPT_HELP_CHAR;
     107          case_GETOPT_VERSION_CHAR (PROGRAM_NAME, AUTHORS);
     108          default:
     109            usage (PRINTENV_FAILURE);
     110          }
     111      }
     112  
     113    if (optind >= argc)
     114      {
     115        for (env = environ; *env != nullptr; ++env)
     116          printf ("%s%c", *env, opt_nul_terminate_output ? '\0' : '\n');
     117        ok = true;
     118      }
     119    else
     120      {
     121        int matches = 0;
     122  
     123        for (i = optind; i < argc; ++i)
     124          {
     125            bool matched = false;
     126  
     127            /* 'printenv a=b' is silent, even if 'a=b=c' is in environ.  */
     128            if (strchr (argv[i], '='))
     129              continue;
     130  
     131            for (env = environ; *env; ++env)
     132              {
     133                ep = *env;
     134                ap = argv[i];
     135                while (*ep != '\0' && *ap != '\0' && *ep++ == *ap++)
     136                  {
     137                    if (*ep == '=' && *ap == '\0')
     138                      {
     139                        printf ("%s%c", ep + 1,
     140                                opt_nul_terminate_output ? '\0' : '\n');
     141                        matched = true;
     142                        break;
     143                      }
     144                  }
     145              }
     146  
     147            matches += matched;
     148          }
     149  
     150        ok = (matches == argc - optind);
     151      }
     152  
     153    return ok ? EXIT_SUCCESS : EXIT_FAILURE;
     154  }