What's interesting is that setenv itself is protected by a lock so multiple parallel calls to setenv ought to work (I didn't actually check). getenv doesn't use a lock.
Is there ever a reason to call setenv? execve and posix_spawn both let you pass an environment.
Edit: hmm I guess variables like LD_PRELOAD and PATH that get used by the standard lib you might want to set. Or if any other libraries modify their runtime behavior based on env vars.
I sometimes call setenv very early in a program's execution to affect what certain libraries do. For example, I have some projects which do `if (!getenv("GST_DEBUG") { setenv("GST_DEBUG", "4"); }` at the beginning of main (before `gst_init()`), in order to print warning and error messages to the terminal when using the gstreamer library. I think I've done similar to set ASAN_OPTIONS as well.
There's also the use-case of wrapper programs; programs which do a thing and then call exec. If the wrapper wants to set environment variables for the exec'd program, you could use execvpe, but setenv + execvp is simpler.
https://sourceware.org/git/?p=glibc.git;a=blob;f=stdlib/sete...