NeoMutt  2024-04-16-36-g75b6fb
Teaching an old dog new tricks
DOXYGEN
Loading...
Searching...
No Matches
envlist.c
Go to the documentation of this file.
1
30#include "config.h"
31#include <stdbool.h>
32#include <stdio.h>
33#include <string.h>
34#include "envlist.h"
35#include "memory.h"
36#include "string2.h"
37
42void envlist_free(char ***envp)
43{
44 if (!envp || !*envp)
45 return;
46
47 for (char **p = *envp; p && *p; p++)
48 FREE(p);
49
50 FREE(envp);
51}
52
58char **envlist_init(char **envp)
59{
60 if (!envp)
61 return NULL;
62
63 char **src = NULL;
64 char **dst = NULL;
65 int count = 0;
66 for (src = envp; src && *src; src++)
67 count++;
68
69 char **env_copy = mutt_mem_calloc(count + 1, sizeof(char *));
70 for (src = envp, dst = env_copy; src && *src; src++, dst++)
71 *dst = mutt_str_dup(*src);
72
73 return env_copy;
74}
75
88bool envlist_set(char ***envp, const char *name, const char *value, bool overwrite)
89{
90 if (!envp || !*envp || !name || (name[0] == '\0'))
91 return false;
92
93 // Find a matching entry
94 int count = 0;
95 int match = -1;
96 char *str = NULL;
97 for (; (str = (*envp)[count]); count++)
98 {
99 size_t len = mutt_str_startswith(str, name);
100 if ((len != 0) && (str[len] == '='))
101 {
102 if (!overwrite)
103 return false;
104 match = count;
105 break;
106 }
107 }
108
109 // Format var=value string
110 char work[1024] = { 0 };
111 snprintf(work, sizeof(work), "%s=%s", name, NONULL(value));
112
113 if (match >= 0)
114 {
115 // match found, overwrite
116 mutt_str_replace(&(*envp)[match], work);
117 }
118 else
119 {
120 // not found, add a new entry
121 mutt_mem_realloc(envp, (count + 2) * sizeof(char *));
122 (*envp)[count] = mutt_str_dup(work);
123 (*envp)[count + 1] = NULL;
124 }
125
126 return true;
127}
128
136bool envlist_unset(char ***envp, const char *name)
137{
138 if (!envp || !*envp || !name || (name[0] == '\0'))
139 return false;
140
141 int count = 0;
142 for (; (*envp)[count]; count++)
143 ; // do nothing
144
145 char *str = NULL;
146 for (int match = 0; (str = (*envp)[match]); match++)
147 {
148 size_t len = mutt_str_startswith(str, name);
149 if ((len != 0) && (str[len] == '='))
150 {
151 FREE(&(*envp)[match]);
152 // Move down the later entries
153 memmove(&(*envp)[match], &(*envp)[match + 1], (count - match) * sizeof(char *));
154 // Shrink the array
155 mutt_mem_realloc(envp, count * sizeof(char *));
156 return true;
157 }
158 }
159 return false;
160}
void envlist_free(char ***envp)
Free the private copy of the environment.
Definition: envlist.c:42
char ** envlist_init(char **envp)
Create a copy of the environment.
Definition: envlist.c:58
bool envlist_set(char ***envp, const char *name, const char *value, bool overwrite)
Set an environment variable.
Definition: envlist.c:88
bool envlist_unset(char ***envp, const char *name)
Unset an environment variable.
Definition: envlist.c:136
Private copy of the environment variables.
void * mutt_mem_calloc(size_t nmemb, size_t size)
Allocate zeroed memory on the heap.
Definition: memory.c:50
void mutt_mem_realloc(void *ptr, size_t size)
Resize a block of memory on the heap.
Definition: memory.c:114
Memory management wrappers.
#define FREE(x)
Definition: memory.h:45
char * mutt_str_dup(const char *str)
Copy a string, safely.
Definition: string.c:253
size_t mutt_str_startswith(const char *str, const char *prefix)
Check whether a string starts with a prefix.
Definition: string.c:230
char * mutt_str_replace(char **p, const char *s)
Replace one string with another.
Definition: string.c:274
String manipulation functions.
#define NONULL(x)
Definition: string2.h:37