1 /* 2 * Set up arguments for main() and prepare environment variables 3 * 4 * This code is free software; you can redistribute it and/or modify it 5 * under the terms of the GNU Library General Public License version 2. 6 */ 7 8 #include "libcflat.h" 9 #include "argv.h" 10 #include "auxinfo.h" 11 12 int __argc; 13 const char *__args; 14 char *__argv[100]; 15 char *__environ[200]; 16 17 char **environ = __environ; 18 19 static char args_copy[1000]; 20 static char *copy_ptr = args_copy; 21 22 #define isblank(c) ((c) == ' ' || (c) == '\t') 23 #define isalpha(c) (((c) >= 'A' && (c) <= 'Z') || ((c) >= 'a' && (c) <= 'z') || (c) == '_') 24 #define isalnum(c) (isalpha(c) || ((c) >= '0' && (c) <= '9')) 25 26 static const char *skip_blanks(const char *p) 27 { 28 while (isblank(*p)) 29 ++p; 30 return p; 31 } 32 33 void __setup_args(void) 34 { 35 const char *args = __args; 36 char **argv = __argv + __argc; 37 38 while (*(args = skip_blanks(args)) != '\0') { 39 *argv++ = copy_ptr; 40 while (*args != '\0' && !isblank(*args)) 41 *copy_ptr++ = *args++; 42 *copy_ptr++ = '\0'; 43 } 44 __argc = argv - __argv; 45 } 46 47 static void setup_args(const char *args) 48 { 49 if (!args) 50 return; 51 52 __args = args; 53 __setup_args(); 54 } 55 56 void setup_args_progname(const char *args) 57 { 58 __argv[0] = copy_ptr; 59 strcpy(__argv[0], auxinfo.progname); 60 copy_ptr += strlen(auxinfo.progname) + 1; 61 ++__argc; 62 setup_args(args); 63 } 64 65 static char *env_eol(char *env) 66 { 67 while (*env && *env != '\n') 68 ++env; 69 return env; 70 } 71 72 static char *env_invalid_eol(char *env) 73 { 74 char *eol = env_eol(env); 75 char eol_old = *eol; 76 77 *eol = '\0'; 78 printf("Invalid environment variable: %s\n", env); 79 *eol = eol_old; 80 return eol; 81 } 82 83 static char *env_next(char *env) 84 { 85 char *p; 86 87 if (!*env) 88 return env; 89 90 if (isalpha(*env)) { 91 bool invalid = false; 92 93 p = env + 1; 94 while (*p && *p != '=' && *p != '\n') { 95 if (!isalnum(*p)) 96 invalid = true; 97 ++p; 98 } 99 100 if (*p != '=') 101 invalid = true; 102 103 if (invalid) { 104 env = env_invalid_eol(env); 105 return *env ? env_next(env + 1) : env; 106 } 107 return env; 108 } 109 110 p = env; 111 while (isblank(*p)) 112 ++p; 113 114 if (*p == '\n') 115 return env_next(p + 1); 116 117 if (*p == '#') 118 env = env_eol(env); 119 else 120 env = env_invalid_eol(env); 121 122 return *env ? env_next(env + 1) : env; 123 } 124 125 void setup_env(char *env, int size) 126 { 127 char *eof = env + size, *p = env; 128 bool newline = false; 129 int i = 0; 130 131 while (*p) 132 ++p; 133 if (p == eof) 134 newline = true; 135 136 while (env < eof) { 137 if (newline) 138 env = env_next(env); 139 if (!*env || env >= eof) 140 break; 141 __environ[i++] = env; 142 while (env < eof && *env && !(newline && *env == '\n')) 143 ++env; 144 *env++ = '\0'; 145 } 146 } 147