跳转至

UNIX C API

1 fork 和 vfork 异同

  • 执行顺序
  • fork:父进程和子进程执行先后顺序不确定,取决于内核调度算法。
  • vfork:子进程先执行 exec 函数簇或 exit,子进程退出再执行父进程。
  • 内存空间:
  • fork:子进程复制父进程的数据空间、堆、栈,共享代码段,子进程改变数据不会响父进程。
  • vfork:子进程并不完全复制父进程地址空间,子进程与父进程共享数据空间,子进程改变数据会影响父进程。
  • vfork 目的是创建一个新进程,再让新进程通过 exec 函数簇去执行一个新程序。
title: 写时复制技术(copy on write)
由于在fork之后,往往子进程直接使用exec函数簇去执行另一段代码,不需要使用到父进程的数据段、堆栈,复制这些不使用的区域会导致不必要的开销,写时复制技术可以解决此类问题。
当任意一个进程修改了这些数据时,则内核才为这块数据分配一个地址,制作一个副本。

1.1 wait 和 waitpid 异同

  • wait 使其调用者阻塞,waitpid 由参数控制是否阻塞。

2 解析命令行参数

2.1 getopt 获取命令行参数

  • 功能:解析命令行参数
  • 语法:int getopt(int argc, char * const argv[],const char *optstring);
  • argc:main 函数的 argc
  • argv:main 函数的 argv
  • optstring: 解析的选项字母,且最后需尾随冒号 :(选项以 - 加字母的短选项组合,后再接一个长选项,如 ./test -n 1 -t 2,optstring 则设置成 nt:
  • 返回值:解析到参数返回短选项,解析到不存在的选项返回冒号 :,解析完返回 -1
  • 示例
#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>

int main(int argc, char *argv[])
{
    int flags, opt;
    int nsecs, tfnd;

    nsecs = 0;
    tfnd = 0;
    flags = 0;
    while ((opt = getopt(argc, argv, "nt:")) != -1)
    {
        switch (opt)
        {
        case 'n':
            flags = 1;
            break;
        case 't':
            nsecs = atoi(optarg);
            tfnd = 1;
            break;
        default: /* '?' */
            fprintf(stderr, "Usage: %s [-t nsecs] [-n] name\n",
                    argv[0]);
            exit(EXIT_FAILURE);
        }
    }

    printf("flags=%d; tfnd=%d; optind=%d\n", flags, tfnd, optind);

    if (optind >= argc)
    {
        fprintf(stderr, "Expected argument after options\n");
        exit(EXIT_FAILURE);
    }

    printf("name argument = %s\n", argv[optind]);

    /* Other code omitted */

    exit(EXIT_SUCCESS);
}
  • 输出结果
$ ./test_getopt -t 123 -n 567
flags=1; tfnd=1; optind=4
name argument = 567

2.2 getopt_long

3 flock,lockf,fcntl

https://www.cnblogs.com/starrysky77/p/9974130.html

  • flock 对应 fuse flock
  • lockf 对应 fuse lock

4 fallocate

  • 使用场景:需要生成大文件时, 使用 fallocate 可以替代 dd 功能。

4.1 fallocate 和 truncate 有所区别

  • fallocate :为文件预分配物理空间,不是生成空洞文件,而且 fallocate 分配的空间在磁盘的扇区上是连续的,能减少后续写入和读取文件时的磁盘寻道的资源开销
  • truncate :生成的是空洞文件,并不占用实际的磁盘空间, 只是文件看上去逻辑大小比较大,但实际占用的空间是 0。

4.2 什么是空洞文件

UNIX 的文件操作,允许操作的偏移位置超过当前的文件长度,这样中间留出的空间的字节会被设置为 0,这部分空间被称为空洞 (hole),linux 系统上空洞不占用实际的硬盘空间。