Variable char **environ is defined in Unistd.h, to represent all current environment variables, generally access to specific environment variables can be getenv, but to traverse all environment variables is to use Environ.
That is, the extern char **environ is declared globally within the program, but it is also possible to set the 3rd parameter of the main function, but it is not recommended because the main function of ISO C does not have a third argument.
Environ maintains a char* array, each of which is a pointer to the environment variable at the top of the function stack frame, and the end of the array is null.
So the correct traversal posture is the following
for (int i = 0; Environ[i]! = NULL; i++) puts (environ[i]);
And then I tried the wrong pose.
for (char *ptr = environ[0]; ptr; ptr++) puts (PTR);
The result is a program dump, which examines the next discovery error out on ptr++, because the PTR type is char*, and after executing + + The pointer moves forward only 1 byte.
And so it became.
for (char *ptr = environ[0]; ptr; ptr + = (strlen (PTR) + 1) puts (environ[i]);
The code is ugly, and there are more unnecessary calculations, the strlen function, but the program is still dump.
That's how I debug.
for (char *ptr = environ[0]; ptr; ptr + = (strlen (PTR) + 1)) { static int i = 0; if (strcmp (PTR, environ[i])! = 0) { printf ("Error:%d\n", i); break; } Puts (PTR); i++; }
Errors are as follows
Program received signal SIGSEGV, segmentation fault.__strcmp_sse2_unaligned () at: /sysdeps/x86_64/multiarch/strcmp-sse2-unaligned. S:204204 . /sysdeps/x86_64/multiarch/strcmp-sse2-unaligned. S:no such file or directory.
Yes, environ. The last element of the array is null, but strcmp must receive a non-null pointer as a parameter (because the strcmp parameter S1, S2 must be accessible with *S1, *S2, and Null is address 0, which is an address that the user cannot access. A SIGSEGV signal is generated when a user accesses an unreachable address.
So I positioned myself to strcmp.
the if environ[i]==0
(GDB) p ptr$ 1 0x7fffffffefe3 " /home/xyz/tlpi/a.out " (GDB) p environ[i]$ 2 0x0
The reason is clear. In the C program storage space high address is the command line parameters and environment variables in sequence, such as
N1 is the number of environment variables, and N2 is the number of command-line arguments. So when PTR points to the last environment variable, ptr+= (strlen[ptr]+1) points to argv[0].
The character pointer array environ holds n1+1 elements, and an extra element is null. ptr+= (strlen[ptr]+1) is a direct access to the program's storage space, and does not have a terminator.
The SIGSEGV signal is raised when PTR reaches the address of the function stack frame below the inaccessible area in memory (that is, argv[n2-1].
Accessing the process environment variable environ a pit