线程是操作系统能够进行运算调度的最小单位。它被包含在进程之中,是进程中的实际运作单位。一条线程指的是进程中一个单一顺序的控制流,一个进程中可以并发多个线程,每条线程并行执行不同的任务。
$ sudo apt-get install -y glibc-doc manpages-posix-dev
安装完成后,我们进行代码测试演示
#include
int pthread_create(
pthread_t *restrict tidp, //新创建的线程ID指向的内存单元。
const pthread_attr_t *restrict attr, //线程属性,默认为NULL
void *(*start_rtn)(void *), //新创建的线程从start_rtn函数的地址开始运行
void *restrict arg //默认为NULL。若上述函数需要参数,将参数放入结构中并将地址作为arg传入。
);
首先我们需要makeflie把所有的.c文件编译一下,接下来我们运行程序,输入命令:
$ ./1.pthread_create_exit.out
我们可以看到使用pthread_create创建了五个线程并显示出来,用pthread_exit来终止线程。
函数原型:
void pthread_exit(void*_retval)
函数原型:
int pthread_join(
pthread_t tid, //需要等待的线程,指定的线程必须位于当前的进程中,而且不得是分离线程
void **status //线程tid所执行的函数返回值(返回值地址需要保证有效),其中status可以为NULL
);
$ ./2.pthread_join.out
int pthread_mutex_init(pthread_mutex_t *mutex, const pthread_mutex_attr_t *mutexattr);
mutex表示的是互斥锁的标号; mutexattr表示的互斥锁的属性,一般情况使用NULL,表示缺省属性。 成功返回0 失败返回错误号
int pthread_mutex_lock(pthread_mutex_t *mutex);’
int pthread_mutex_unlock(pthread_mutex_t *mutex);'
运行结果如下
我们可以看到使用互斥锁可以同一时间内只有一个线程访问数据。
所谓死锁就是让两个进程不断争夺运行资源来使程序进入死锁状态。然后我们运行程序,输入命令
$ ./5.pthread_dead_lock_of_mutex.out
$ ./6.pthread_conditional_var.out
狭义定义:进程是正在运行的程序的实例(an instance of a computer program that is being executed)。
广义定义:进程是一个具有一定独立功能的程序关于某个数据集合的一次运行活动。它是操作系统动态执行的基本单元,在传统的操作系统中,进程既是基本的分配单元,也是基本的执行单元。
Linux 的进程有以下6种状态:
D:不可中断的深度睡眠状态,处于这种状态的进程不能响应异步信号;
R:进程处于运行态或就绪状态,只有在该状态的进程才可能在CPU上运行。而同一时刻可能有多个进程处于可执行状态;
S:可中断的睡眠状态,处于这个状态的进程因为等待某种事件的发生而被挂起。;
T:暂停状态或跟踪状态;
X:退出状态,进程即将被销毁;
Z:退出状态,进程成为僵尸进程。
函数以拷贝父进程的方式创建子进程。子进程与父进程有相同的代码空间、文件描述符等资源
创建后,子进程与父进程开始并发执行,执行顺序由内核调度算法来决定
fork()对父子进程各返回一次,
父进程:子进程的PID,
子进程:0;
失败: 小于0;
同样运行.c 文件前我们需要makefile
运行结果
$ ./3-fork-print-pid.out
守护进程是脱离于终端并且在后台运行,周期性的执行某种任务或者等待处理某些发生的事件进程。
使用‘daemon()’创建守护进程
运行结果如下
信号函数用来通知进程发生了异步事件
函数结构
struct sigaction {
void (*sa_handler)(int);
void (*sa_sigaction)(int, siginfo_t *, void *);
sigset_t sa_mask;
int sa_flags;
void (*sa_restorer)(void);
}
示例
运行结果如下图
子进程经过两次等待,父进程将信号传给子进程后,通过exit()退出,并且输出子进程的退出状态
管道,即进程间数据流的通道。通常A进程输出连B进程输入端。符号“|"
1.匿名管道: pipe文件
函数原型:
int pipe(int pipefd[2])
2.命名管道: fifo文件:int mkfifo(const char *pathname, mode_t mode)(ps:参数pathname指定了文件名
参数mode则指定了文件的读写权限)
函数
下载成功后,进入ubuntu-18.04_imx6ul_qemu_system目录,执行install_sdl.sh
必须在Ubunut的桌面环境下启动终端,执行./qemu-imx6ull-gui.sh
我们可以看到下面界面
$ fb-test
$ cd myfb-test
$ ./myfb-test /dev/fb0
$ cd
$ i2cdetect -l #列出所有ic2总线
$ i2cdetect -y 0 #列出总线0上的设备
UU:有设备,有内核驱动
地址:有设备,无驱动
矩阵的最左列是十位,最上面是个位。
安装LED驱动
$ cd
$ cd led_driver_qemu/
$ insmod 100ask_led.ko
控制LED零号灯亮,控制LED一号灯灭
$ ./ledtest /dev/100ask_led0 on
$ ./ledtest /dev/100ask_led1 off
安装驱动
$ cd
$ cd button_driver_qemu/
$ insmod button_drv.ko #扫描你的按键
$ insmod board_100ask_qemu_imx6ull.ko
启动按键控制
$ ./button_led_test
参考:https://blog.csdn.net/Zeilo/article/details/124084107?spm=1001.2014.3001.5502