7.9 环境变量

7.9

如同前述,境字符串的形式是:

name = value

UNIX核并不种字符串的意,它的解完全取于各个应用程序。例如, shell使用了大量的量。其中某一些在登录时动设置(如HOMEUSER等),有些由用户设置。我通常在一shell文件中量以控制shell作。例如,若置了M A I L PAT H它告Bourne shellK o r n Shell到哪里去查看件。

ANSI C了一getenv,可以用其取量值,但是该标准又称环境的容是由实现的。

#include <stdlib.h>

char *getenv(const char *name) ;

//返回:指向与name关联的value的指针,若未找到则为NULL

注意,此函返回一,它指向name = value字符串中的value。我们应当使用getenv从环中取一个环量的值,而不是直接存取environ

POSIX . 1X P G 3了某些量。表7 – 1列出了由这两个标准定并受到SVR44 . 3 + BSD支持的量。SVR44 . 3 + BSD使用了很多依实现量。FIPS 151-1要求登shell要定义环HOMELOGNAME

7-1

                       

HOME                起始目

L A N G                     本地名

L C _ A L L                 本地名

L C _ C O L L A T E      本地排序名

L C _ C T Y P E            本地字符分

L C _ M O N E T A R Y  本地货币编辑

L C _ N U M E R I C  本地编辑

L C _ T I M E         本地日期/时间格式名

LOGNAME         

N L S P A T H           消息模板序列

P A T H                     搜索可行文件的路

T E R M                   

T Z                 时区

除了取量值,有也需要量,或者是改变现量的值,或者是增加新量。(在下一章将会了解到,我能影的是程及其后生成的子程的境,但不能影程的境,通常是一shell程。管如此,修改境表的能力仍然是很有用的。)不幸的是,并不是所有系都支持种能力。

修改环境表三的原型是:

#include <stdlib.h>

int putenv(const char *str) ;

int setenv(const char *name, const char *value, int rewrite) ;

//两个函数返回:若成功则为0,若出错则为非0

void unsetenv(const char *name) ;

的操作是:

• putenv取形式name = value的字符串,其放到境表中。如果name存在,除其原的定

• setenvnamevalue。如果在境中name存在,那么( a )rewrite0首先除其存的定( b )rewrite0除其存定name新的value,而且也不出)。

• unsetenvname的定。即使不存在种定也不算出

些函在修改境表是如何行操作的呢?回一下7 – 3,其中,境表(指向实际name = value字符串的指针数组)和境字符串典型地存放在程存部(之上)。除一字符串很简单——只要先找到,然后所有后都向下移一位置。但是增加一字符串或修改一个现存的字符串就比以上的空程存

部,所以充,即法向上充,也法向充。

l  如果修改一个现存的name:

n  如果新value度少于或等于value度,只要在原字符串所用空

入新字符串。

n  如果新value度大于原度,须调malloc新字符串分配空,然后字符中,然后使境表中针对name的指指向新分配

l  如果要增加一新的name操作就更加复。首先,mallocname = value分配空,然后将该符串入此空

n  如果是第一次增加一name须调malloc新的指表分配空境表复制到新分配,并指向新name = value的指存在表的表尾,然后又空指存在其后。最后使environ指向新指表。再看一下7 – 3,如果原境表位于栈顶之上(是一种常),那么必须将此表移至堆中。但是,此表中的大多仍指向栈顶之上的各name = value字符串。

n  如果不是第一次增加一name可知以前已malloc在堆中为环境表分配了空,所以只要realloc,以分配比原空多存放一的空。然后将该指向新name = value字符串的指存放在表表尾,后面跟空指