opuntiaOS - an operating system targeting x86 and ARMv7
at master 2.7 kB view raw
1#include <stdbool.h> 2#include <stdlib.h> 3#include <string.h> 4 5static void free_var(const char* string) 6{ 7 // TODO: Implement me! 8} 9 10char* getenv(const char* name) 11{ 12 size_t len = strlen(name); 13 for (int i = 0; environ[i]; i++) { 14 const char* envv = environ[i]; 15 char* eqpos = strchr(envv, '='); 16 if (!eqpos) { 17 continue; 18 } 19 size_t curlen = (size_t)(eqpos - envv); 20 if (curlen == len && strncmp(name, envv, len) == 0) { 21 return (char*)&envv[len + 1]; 22 } 23 } 24 25 return NULL; 26} 27 28int setenv(const char* name, const char* value, int overwrite) 29{ 30 if (!overwrite && getenv(name)) { 31 return 0; 32 } 33 34 int name_len = strlen(name); 35 int value_len = strlen(value); 36 int len = name_len + 1 + value_len; 37 char* string = (char*)malloc(len + 1); 38 strncpy(string, name, name_len); 39 string[name_len] = '='; 40 strncpy(&string[name_len + 1], value, value_len); 41 string[len] = '\0'; 42 return putenv(string); 43} 44 45int putenv(char* string) 46{ 47 char* pos = strchr(string, '='); 48 if (!pos) { 49 return unsetenv(string); 50 } 51 52 size_t len = (size_t)(pos - string); 53 int env_i = 0; 54 for (; environ[env_i]; env_i++) { 55 const char* envv = environ[env_i]; 56 char* eqpos = strchr(envv, '='); 57 if (!eqpos) { 58 continue; 59 } 60 size_t curlen = (size_t)(eqpos - envv); 61 if (len != curlen) { 62 continue; 63 } 64 65 if (strncmp(string, envv, len) == 0) { 66 free_var(envv); 67 environ[env_i] = string; 68 return 0; 69 } 70 } 71 72 char** new_environ = (char**)malloc(sizeof(char*) * (env_i + 2)); 73 for (int i = 0; i < env_i; i++) { 74 new_environ[i] = environ[i]; 75 } 76 new_environ[env_i] = string; 77 new_environ[env_i + 1] = NULL; 78 79 extern int __environ_malloced; 80 if (__environ_malloced) { 81 free(environ); 82 } 83 environ = new_environ; 84 __environ_malloced = 1; 85 return 0; 86} 87 88int unsetenv(const char* name) 89{ 90 size_t len = strlen(name); 91 int env_i = 0; 92 int remove_pos = 0; 93 const char* remove_env = NULL; 94 for (; environ[env_i]; env_i++) { 95 const char* envv = environ[env_i]; 96 char* eqpos = strchr(envv, '='); 97 if (!eqpos) { 98 continue; 99 } 100 size_t curlen = (size_t)(eqpos - envv); 101 if (len != curlen) { 102 continue; 103 } 104 105 if (strncmp(name, envv, len) == 0) { 106 remove_pos = env_i; 107 remove_env = envv; 108 } 109 } 110 111 size_t move_len = ((env_i - 1) - remove_pos) * sizeof(char*); 112 memmove(&environ[remove_pos], &environ[remove_pos + 1], move_len); 113 free_var(remove_env); 114 return 0; 115}