1、main函数
•
函数原型:
•
int
main
(
int
argc
, char *
argv
[]);
2、进程终止
•
正常终止方式
•
1
、从
main
函数返回
•
2
、调用
exit
(额外执行一些清理操作,如关闭打开的文件)
•
3
、调用
_exit
或
_Exit
•
4
、
线程终止(暂不涉及)
•
异常终止方式
•
1
、调用
abort
•
2
、收到一个信号
•
终止处理程序
•
程序退出前自动调用,由
atexit
函数注册
•
int
atexit
(void (*
func
)(void));
#include <stdio.h>
#include <stdlib.h>
void my_exit(void);
int main(void)
{
if( atexit(my_exit) != 0 )
{
perror("atexit");
return 0;
}
if( atexit(my_exit) != 0 )
{
perror("atexit");
return 0;
}
printf("main is done\n");
return(0);
}
void my_exit(void)
{
printf("my_eixt handler\n");
}
3、环境变量列表
•
使用全局变量引用
•
extern char **
environ
;
•
环境变量的操作可以使用
getenv
()
、
putenv
()
•
但是环境变量的遍历只能使用全局变量
environ
4、C程序的内存布局
•
正文段,机器指令(
TEXT
)
•
初始化的数据段(
DATA
)
int maxcount = 99;
•
未初始化的数据段(
BSS
)
long sum[1000];
•
堆栈(
STACK
)
•
堆(
HEAP
)
•
size
命令显示正文段、数据段、
BSS
段的大小
5、共享库
•
共享库使得可执行文件中不再需要包含常用的库函数(库函数的实现可以存储在一个公用内存区中),可执行文件的尺寸将大幅减小
•
共享库的另一个优点是可以用库函数的新版本代替老版本而无需对使用该库的程序重新连接编辑
•
尺寸比较
gcc -static 1.c # 静态方式编译
gcc 1.c # 共享库方式编译
使用size命令查看两种编译方式下生成的执行程序的大小
6、内存分配
•
#include <
stdlib.h
>
•
void *
malloc
(
size_t
size);
•
void *
calloc
(
size_t
nobj
,
size_t
size);
•
void *
realloc
(void *
ptr
,
size_t
newsize
);
•
malloc
分配的内存中的内容是未知的,需要显式初始化
•
calloc
分配的内存初始化为
0
•
realloc
调整之前分配的内存的大小,可以增大
/
缩小,增大时可能会涉及原有内存数据的移动,所以
不要使用指向这块区域的指针
•
void
free
(void *
ptr
); #
释放之前分配的内存
•
alloca
函数 (简单提一下,在堆栈中分配内存,有些系统并不支持)
7、环境变量
•
#include <
stdlib.h
>
•
char *
getenv
(
const
char *name); #
获取环境变量
•
int
putenv
(char *
str
); #
设置或改写环境变量
•
并非所有系统都支持
putenv
8、setjmp()、longjump()
•
#include <
setjmp.h
>
•
int
setjmp
(
jmp_buf
env
);
•
void
longjmp
(
jmp_buf
env
,
int
val
);
•
实现非局部跳转,即函数间跳转,注意与
goto
语句的区别
•
自动变量的潜在问题:
定义自动变量的函数已经返回后,就不能再引用这些自动变量,因为空间已经释放
#include <stdio.h>
#include <stdlib.h>
#include <setjmp.h>
static void f1(void);
static jmp_buf jmpbuffer;
int main(void)
{
switch( setjmp(jmpbuffer) )
{
case 0:
f1(); /* never returns */
break;
case 1:
printf("after longjmp:\n");
break;
}
printf("over\n");
exit(0);
}
static void f1(void)
{
printf("in f1():\n");
longjmp(jmpbuffer, 1);
exit(0); /* never reached */
}
9、getrlimit()、setrlimit ()
•
每个进程都有一组资源限制
•
#include <sys/
resource.h
>
•
int
getrlimit
(
int
resource,
struct
rlimit
*
rlptr
);
•
int
setrlimit
(
int
resource,
const
struct
rlimit
*
rlptr
);
•
调用这两个函数可以实现
shell
命令
ulimit
的功能