2016-08-19 42 views
0

我试图从C++程序访问环境变量。所以我做了一个测试程序,它工作正常:无法从C/C++程序访问环境变量

#include <stdio.h> 
#include <stdlib.h> 

int main() 
{ 
    printf("MANIFOLD : %s\n", getenv("MANIFOLD_DIRECTORY")); 
    return(0); 
} 

输出:MANIFOLD : /home/n1603031f/Desktop/manifold-0.12.1/kitfox_configuration/input.config

注:getenv的签名是:

char *getenv(const char *name); 

但是当我用这个作为的一部分更大的程序与许多文件链接:

energy_introspector->configure (getenv("MANIFOLD_DIRECTORY")); 

以上不起作用。

char *a = new char [1000]; 
a = getenv("MANIFOLD_DIRECTORY"); 
energy_introspector->configure (a); 

上面也不起作用。

注:

void configure(const char *ConfigFile); 

错误消息:配置功能的签名

Number of LPs = 1 
[Ubuntu10:18455] *** Process received signal *** 
[Ubuntu10:18455] Signal: Segmentation fault (11) 
[Ubuntu10:18455] Signal code: Address not mapped (1) 
[Ubuntu10:18455] Failing at address: (nil) 
[Ubuntu10:18455] [ 0] /lib/x86_64-linux-gnu/libpthread.so.0(+0x10330) [0x7f9a38149330] 
[Ubuntu10:18455] [ 1] /lib/x86_64-linux-gnu/libc.so.6(strlen+0x2a) [0x7f9a37dfc9da] 
[Ubuntu10:18455] [ 2] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x5bf8c4] 
[Ubuntu10:18455] [ 3] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x5a4ac6] 
[Ubuntu10:18455] [ 4] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x5a4df8] 
[Ubuntu10:18455] [ 5] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x4283b6] 
[Ubuntu10:18455] [ 6] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x41e197] 
[Ubuntu10:18455] [ 7] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x41de7a] 
[Ubuntu10:18455] [ 8] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x41d906] 
[Ubuntu10:18455] [ 9] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x41710b] 
[Ubuntu10:18455] [10] /lib/x86_64-linux-gnu/libc.so.6(__libc_start_main+0xf5) [0x7f9a37d95f45] 
[Ubuntu10:18455] [11] /home/n1603031f/Desktop/manifold-0.12.1/simulator/smp/QsimLib/smp_llp() [0x41697f] 
[Ubuntu10:18455] *** End of error message *** 
-------------------------------------------------------------------------- 
mpirun noticed that process rank 0 with PID 18455 on node Ubuntu10 exited on signal 11 (Segmentation fault). 
-------------------------------------------------------------------------- 

但这个工程:

energy_introspector->configure ("/home/n1603031f/Desktop/manifold-0.12.1/kitfox_configuration/input.config"); 
+0

是否可以在'configure'里面调用'getenv'?每次调用'getenv'时,都可能导致上次调用的结果无效。 –

+0

@TheDark号从'configure'没有调用'getenv()'。# – PRP

+0

在C++中几乎没有'new char [1000]'的理由。无论是'std :: string','std :: vector '还是'std :: array '都是更好的选择。在这种情况下:'std :: string a = getenv();' – MSalters

回答

3

getenv返回一个指向库分配内存的指针,该内存不属于您的程序所拥有的。你的

a = new char [1000] 

行显示你没有认识到这一点,似乎认为你需要提供内存。这是不正确的,尤其是你可能永远不会释放由getenv返回的内存。

(即使这将是正确的,简单的指针赋值

a = getenv... 

仍然是错误的,因为你只是换一个指针,而不是复制的记忆。这行是内存泄漏,你松动指针分配的1000个字符)

如果你想让你的程序拥有该内存,所以你可以稍后free它,你需要将它复制到我们的私人内存空间。

a = new char [1000]; 
e = getenv (<whatever>); 
strcpy (a, e); 

不幸的是,我不能看到你与指针后来在你的其他例子,特别是如果你试图freedelete它。两者都会导致错误。

+0

你的解决方案是什么?有没有 ? – PRP

+0

btw ....'a = new char [1000]; e = getenv(​​); strcpy(a,e);'不起作用 – PRP

+1

@PRP *究竟是什么*“不起作用”? – tofro

1

您的代码中的第一个显式错误是char数组分配,然后指定getenv的结果。这导致内存泄漏。在你的情况下使用:

std::string a = getenv("MANIFOLD_DIRECTORY"); 

这将结果保存在变量a,使你的代码不受解封环境变量。

如果getenv返回NULL,则具有指定名称的变量不在传递给应用程序的环境中。尝试用下面的代码列出所有可用的环境变量。

extern char** environ; 

for (int i = 0; environ[i] != NULL; ++i) { 
    std::cout << environ[i] << std::endl; 
} 

如果你的变量没有被列出,那么很可能是你打电话给你的应用程序的问题。另一种选择是您的环境未被设置。