《APUE》笔记-第七章-进程环境

1.引言

重要知识:命令行参数、环境变量(环境指针、环境表、环境字符串)、进程终止方式、c程序的启动和终止、c程序的存储空间布局、setjmp、longjmp、进程资源限制

2.main函数

int main(int argc, char *argv[]);//有 argv[argc] = NULL;

执行一个新程序的过程:bash->fork()->子shell->exec()->装入新程序,所以,当执行一个新程序时,调用exec的进程(即子shell)将命令行参数传给新程序;


3.进程终止

8种终止方式,其中5种正常、3种异常。

#include

void exit(int status);

void _Exit(int status);

#include

void _exit(int status);

其中status:终止状态(退出状态)

调用exit和调用_exit、_Exit区别:

调用_exit和_Exit会直接返回内核;调用exit会先执行终止处理程序,再执行fclose清理缓冲区,最后通过调用_exit或_Exit返回内核


调用atexit来登记终止处理程序

int atexit(void (*func)(void));

成功,0;失败,非0

练习atexit、exit:

#include 
#include 
#include 

void atexit_func1(void)
{
        printf("this is atexit_func1\n");
}

void atexit_func2(void)
{
        printf("this is atexit_func2\n");
}

void atexit_func3(void)
{
        printf("this is atexit_func3\n");
}

int main()
{
        printf("this is in main()\n");
        atexit(atexit_func1);
        atexit(atexit_func3);
        atexit(atexit_func2);
        atexit(atexit_func2);
        exit(0);
}
结果:
《APUE》笔记-第七章-进程环境_第1张图片

分析:每登记一次,执行一次;登记顺序与执行顺序相反。exit(0)中0是终止状态


4.c程序的启动和终止、c程序的存储空间布局

看书


5.内存分配函数malloc、calloc、realloc

void *malloc(size_t size);//size为总的分配的内存的大小,分配的内存未初始化

void *calloc(size_t nobj, size_t size);//size为每个对象大小,分配的内存每一bit都初始化为0

void *realloc(void *ptr, size_t newsize);//新增区域内初始值不确定

void *free(void *ptr);

程序练习:

#include 
#include 

int main()
{
        char *p1 = (char *)malloc(sizeof(char) * 10);
        if (p1 == NULL)
        {
                printf("malloc() error\n");
                exit(0);
        }
        printf("memory from malloc() *p1 = %c\n", *p1);

        int *p2 = (int *)calloc(20, sizeof(int));
        if (p2 == NULL)
        {
                printf("calloc() error\n");
                exit(0);
        }
        printf("memory from calloc() *p2 = %d\n", *p2);
        printf("position: 0x%0x\n", p2);

        int *p3 = (int *)realloc(p2, (20 + 100000) * sizeof(int));
        if (p3 == NULL)
        {
                printf("realloc() error\n");
                exit(0);
        }
        printf("memory from calloc() *p3 = %d\n", *p3);
        printf("new position memory from calloc() *p3 = %d\n", *(p3 + 200));
        printf("position: 0x%0x\n", p3);

        free(p1);
        free(p3);

        exit(0);
}

结果:

《APUE》笔记-第七章-进程环境_第2张图片
分析:

malloc分配的内存初始值不确定;calloc分配的内存初始化为0;realloc分配的新内存初始值也为0?(和书上不同),当realloc新分配的内存过大时,会将整个内容移到另一个足够大的区域


6.环境变量

extern char **environ;

#include

char *getenv(const char *name);

int putenv(char *str);

成功,0;出错,非0

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

int unsetenv(const char *name);

成功,0;出错,-1

练习程序:

#include 
#include 

extern char **environ;

int main()
{
        char **env = environ;
        while (*env != NULL)//打印全部环境变量
        {
                printf("%s\n", *env);
                env++;
        }
        char *name = getenv("HOME");//取环境变量
        printf("HOME=%s\n", name);

        if (putenv("MY_HOME=zxin") != 0)//设置环境变量及其值
        {
                printf("putenv() error\n");
        }

        if (setenv("id","000111", 0) != 0)//设置环境变量及其值

        {
                printf("setenv() error\n");
        }
        printf("MY_HOME=%s\n", getenv("MY_HOME"));
        printf("id=%s\n", getenv("id"));
        unsetenv("MY_HOME");//删除环境变量
        unsetenv("id");

        exit(0);
}
结果:

《APUE》笔记-第七章-进程环境_第3张图片
中间还有很大一部分省略,最后为:

《APUE》笔记-第七章-进程环境_第4张图片


7.setjmp和longjmp

#include

jmp_buf;

int setjmp(jmp_buf jmpbuffer);

void longjmp(jmp_buf jmpbuffer, int val);

longjmp的参数val为setjmp的返回值

#include 
#include 

jmp_buf buffer;

void func1(void);
void func2(void);
void func3(void);
void func4(void);

int main()
{
        printf("now in main()\n");
        if (setjmp(buffer) == 5)
        {
                printf("now return to main()\n");
                exit(0);
        }
        func1();
        exit(0);
}

void func1()
{
        printf("now in func1\n");
        func2();
}
void func2()
{
        printf("now in func2\n");
        func3();
}
void func3()
{
        printf("now in func3\n");
        func4();
}
void func4()
{
        printf("now in func4\n");
        longjmp(buffer, 5);
}
结果:

《APUE》笔记-第七章-进程环境_第5张图片

8.getrlimit、setrlimit

#include

int getrlimit(int resource, struct rlimit *r);

int setrlimit(int resource , const struct *rlimit);

成功,0;出错,非0

struct rlimit

{

        rlim_t rlim_cur;//软限制

        rlim_t rlim_max;//硬限制

};

程序如下:

#include 
#include 

int main()
{
        struct rlimit lim;
        if (getrlimit(RLIMIT_NOFILE, &lim) != 0)//每个进程能打开的最多文件数
                exit(-1);
        if (lim.rlim_cur == RLIM_INFINITY)
                printf("infinite\n");
        else
                printf("%d\n", lim.rlim_cur);
        if (lim.rlim_max == RLIM_INFINITY)
                printf("infinite\n");
        else
                printf("%d\n", lim.rlim_max);
        exit(0);
}
结果:

《APUE》笔记-第七章-进程环境_第6张图片


你可能感兴趣的:(linux环境编程)