《嵌入式系统原理与应用》第十章 Linux应用编程与实例 培训教学课件

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

ROM
程序2
程序n
RAM
进程1
其他进程
进程2
程序1

CPU
R0-Ri
10.1.2 进程和线程
每个进程都拥有自己的数据段、代码段和堆栈段,以进程为单位进行调度时,需要有比较复杂的上下文切换等动作,系统开销大。 为了降低任务切换时的系统开销,将进程分解成几个小模块——线程,这些线程共享进程的数据空间,以这些线程作为单位进行调度,减少系统调度开销。 线程是进程的子集,进程是资源管理的最小单位,线程是程序执行的最小单位。
获取线程的栈保护区大小
8
pthread_attr_setguardsize()
设置线程的栈保护区大小
9
pthread_attr_getscope()
获取线程的作用域
10
pthread_attr_setscope()
设置线程的作用域
11
pthread_attr_getstack()
获取线程的堆栈信息(栈地址和栈大小)
程序到进程转换的过程,整个转换过程主要包含以下3个步骤: 查找到对应程序代码存放的位置。 使用fork()函数为启动一个新进程。 在新进程中调用exec族函数(请参考第五章内核部分)装载程序档,并执行程序档中的main()函数。
10.1.1 程序与进程的关系
程序与进程有以下的关系: 1. 程序只是一系列指令序列与数据的集合,只是一个静态的实体。进程则不同,它是程序在某个数据集上的执行过程,它是一个动态运行的实体,有自己的生命周期 2. 进程和程序并不是一一对应的,一个程序执行在不同的数据集上运行就会成为不同的进程。 3. 进程具有并发性,而程序没有。 4. 进程是竞争计算机资源的基本单位,而程序不是。
获取线程间的CPU亲缘性
4
pthread_attr_setaffinity_np()
设置线程的CPU亲缘性
5
pthread_attr_getdetachstate()
获取线程分离状态属性
6
pthread_attr_setdetachstate()
修改线程分离状态属性
7
pthread_attr_getguardsize()
10.2.1 线程创建
2. 线程创建 pthread_create()函数是用于创建一个线程的,创建线程实际上就是确定调用该线程函数的入口点。 函数原型: int pthread_create(pthread_t *thread, const pthread_attr_t *attr, void *(*start_routine) (void *), void *arg); 参数说明: 1) pthread_t *thread:pthread_t是一种用于表示线程的数据类型,每一个pthread_t类型的变量都可以表示一个线程。 2) const pthread_attr_t *attr:用于手动设置新建线程的属性,例如线程的调用策略、线程所能使用的栈内存的大小等。 3) void *(*start_routine) (void *):以函数指针的方式指明新建线程需要执行的函数。 4)void *arg:指定传递给start_routine()函数的实参,当不需要传递任何数据时,将arg赋值为NULL即可。
线程1

SCHED_RR
线程1
进程2

进程i
时间片1
I如下: int pthread_attr_setinheritsched(pthread_attr_t *attr, int inheritsched); int pthread_attr_getinheritsched(const pthread_attr_t *attr, int *inheritsched); int pthread_attr_setschedpolicy(pthread_attr_t *attr, int policy); int pthread_attr_getschedpolicy(const pthread_attr_t *attr, int *policy); attr:指向一个线程属性的指针。 inheritsched:线程是否继承调度属性,可选值分别为 PTHREAD_INHERIT_SCHED:调度属性将继承于创建的线程,attr中设置的调度属性将被忽略。 PTHREAD_EXPLICIT_SCHED:调度属性将被设置为attr中指定的属性值。 policy:可选值为线程的三种调度策略,SCHED_OTHER、SCHED_FIFO、SCHED_RR。
设置线程是否继承调度属性
(1)初始化一个线程对象的属性 函数原型: int pthread_attr_init(pthread_attr_t *attr); 若函数调用成功返回0,否则返回对应的错误代码。 attr:指向一个线程属性的指针 (2)销毁一个线程属性对象 pthread_attr_destroy()函数销毁。 函数原型: int pthread_attr_destroy(pthread_attr_t *attr); 若函数调用成功返回0,否则返回对应的错误代码。 attr:指向一个线程属性的指针
程序并不能单独执行,只有将程序加载到存储器中,系统为他分配资源后才能够执行,这种执行的程序称之为进程,也就是说进程是系统进行资源分配和调度的一个独立单位。操作系统会为每个进程分配单独的地址空间。 同样的一个程序,可以实例化为多个进程 程序只是个静态的可执行文档,而进程是一个动态的实体
10.1.1 程序与进程的关系
10.1.2 进程和线程
线程本质是一个进程内部的一个控制序列,类似于队列,一个进程可以拥有一个线程或者多个线程。 当进程执行fork()函数创建一个新进程时,将创建出该进程的一份新副本。新进程拥有自己的变量和PID,执行几乎完全独立于父进程,进程开销大;在进程中创建一个新线程时,新的执行线程将拥有自己的栈空间,但与它的创建者共享全局变量、文件描述符、信号处理函数和当前目录状态,不是产生当前进程的副本。 Linux系统每个进程都有独立的地址空间,一个进程崩溃后,在系统的保护模式下并不会对系统中其他进程产生影响;而线程只是一个进程内部的一个控制序列,当线程崩溃后,进程也随之崩溃。
10.2.2 线程管理
3. 线程栈设置 线程共享使用的是进程的存储器空间,那么一个进程有n个线程,默认的线程栈大小是1M,那么就有可能导致进程的存储器空间是不够的。可以根据具体需要调小和调大线程栈空间。 获取、设置线程栈大小可以使用以下函数: int pthread_attr_setstacksize(pthread_attr_t *attr, size_t stacksize); int pthread_attr_getstacksize(const pthread_attr_t *attr, size_t *stacksize); 参数: attr:指向一个线程属性的指针。 stacksize:线程栈的大小。
设置线程的调度策略
17
pthread_attr_getschedparam()
获取线程的调度优先级
18
pthread_attr_setschedparam()
设置线程的调度优先级
19
pthread_attr_getinheritsched()
获取线程是否继承调度属性
20
pthread_attr_setinheritsched()
10.2.1 线程创建
线程的属性非常多,而且其属性值不能直接设置,须使用相关函数进行操作
10.2.1 线程创建
序号
API
描述
1
pthread_attr_init()
初始化一个线程对象的属性
2
pthread_attr_destroy()
销毁一个线程属性对象
3
pthread_attr_getaffinity_np()
嵌入式系统及应用 第10章 Linux应用编程与实例
本章目录
1
2
程序、进程与线程
线程管理
3
C-V2X OBU应用编程实例
10.1.1 程序与进程的关系
10.1 程序、进程与线程
程序:程序是源代码编译后生成的可执行程序文档,是为了完成特定任务而准备好的指令序列与数据的集合。 进程(process)则是程序执行的具体实例,包含该程序在执行时候的所有状态与所使用的资源。在程序执行的过程中,它享有系统的资源,至少包括进程的运行环境、CPU、外设、存储器、进程ID等资源与信息。
10.2 线程管理
1. 线程属性 Linux中线程属性结构如下: typedef struct { int etachstate; //线程的分离状态 int schedpolicy; //线程调度策略 struct sched_param schedparam; //线程的调度参数 int inheritsched; //线程的继承性 int scope; //线程的作用域 size_t guardsize; //线程栈末尾的警戒缓冲区大小 int stackaddr_set; //线程的栈设置 void* stackaddr; //线程栈的位置 size_t stacksize; //线程栈的大小 }pthread_attr_t;
本章目录
1
2
程序、进程与线程
线程管理
3
C-V2X OBU应用编程实例
在Linux系统下的多线程遵循POSIX标准,而其中的一套常用的线程库是pthread,它是一套通用的线程库。 使用时必须包含以下头文件: #include <pthread.h> 除此之外在链接时需要使用库libpthread.a。因为pthread的库不是Linux系统的文件,所以在编译时要加上-lpthread(或-pthread)选项。
10.2.1 线程创建
1. 线程的调度策略选择 POSIX标准指定了三种调度策略: 分时调度策略 (SCHED_OTHER)。 实时调度策略,先进先出方式调度(SCHED_FIFO)。 实时调度策略 ,时间片轮转方式调度(SCHED_RR)。
10.2.2 线程管理
SCHED_FIFO
线程2
线程n
12
pthread_attr_setstack()
设置线程堆栈区
13
pthread_attr_getstacksize()
获取线程堆栈大小
14
pthread_attr_setstacksize()
设置线程堆栈大小
15
pthread_attr_getschedpolicy()
获取线程的调度策略
16
pthread_attr_setschedpolicy()
10.2.2 线程管理
2. 线程的优先级设置 在Linux系统中,优先级数值越小,线程优先级越高. 获取、设置线程静态优先级可以使用以下函数: int pthread_attr_setschedparam(pthread_attr_t *attr, const struct sched_param *param); int pthread_attr_getschedparam(const pthread_attr_t *attr, struct sched_param *param); 参数: attr:指向一个线程属性的指针。 param:静态优先级数值。 仅当调度策略为实时(即SCHED_RR或SCHED_FIFO)时,可以在运行时通过pthread_setschedparam()函数来改变优先级,默认为0。
10.2.2 线程管理
4. 线程退出 在该函数运行完之后,该线程也就隐式退出了,这与进程的退出差不多。而另一种退出线程的方法是使用pthread_exit()函数。 不能随意使用exit()退出函数来进行出错处理,将会导致整个进程退出,线程退出只能使用pthread_exit()函数。 函数原型: void pthread_exit(void *retval); 参数: retval:如果retval不为空,则会将线程的退出值保存到retval中,如果不关心线程的退出值,形参为NULL即可。 如果某个线程想要等待另一个线程退出,并且获取它的退出值,可以使用pthread_join()函数以阻塞的方式等待thread指定的线程结束。
相关文档
最新文档