Linux之线程概念

目录

一、细粒度划分

1、堆区细粒度划分

2、物理内存和可执行程序细粒度划分

3、虚拟地址到物理地址的转化

二、线程的概念

1、基本概念

2、线程的优点

3、线程的缺点

4、线程异常 

5、线程用途

三、Linux下的进程和线程


一、细粒度划分

1、堆区细粒度划分

在语言中,我们知道,用户自己申请的空间是存在于地址空间的堆区上的。可是,堆区是一整块空间,我们每次申请只是申请了其中的一小块,并且我们只是说明了申请空间的大小,拿到的是空间的起始地址。如果,我们多次申请了空间,那么我们怎么知道第一次申请的空间是从堆区哪里到哪里呢,第二次申请的空间是从堆区哪里到哪里呢?

于是os就必须对堆区进行更加精细的管理。在Linux下,每次从堆区申请一块空间,os就会创建结构体 struct vm_area_struct ,该结构体中的数据就是用户申请的每一块空间的相关属性,其中就有空间的起始位置和结束位置。os对于用户申请的空间的管理就成了对结构体链表的管理。os通过这样的精细划分,能够更好地管理用户申请的每一块空间。

当然,链表的整个范围也一定是在堆区的范围之间的。

上图就是os对堆区的细粒度划分的大概内容。

2、物理内存和可执行程序细粒度划分

根据下图,我们来说明。

首先,我们需要知道:1、a.exe这个可执行程序是一个文件。2、a.exe等可执行程序在磁盘上已经按地址空间的方式编译好了。3、并且a.exe等可执行程序已经被分成了若干个4KB大小的小块,我们称之为页帧

当a.exe刚开始运行,一个进程刚开始运行的时候,os首先创建进程的PCB,地址空间,页表,但是还没有通过页表建立虚拟地址到物理地址的联系,而是通过某种硬件方式直接让地址空间找到磁盘上的可执行程序。

在页表中有一列的数据表示是否在内存中(下图,页表绿色的部分)。当执行具体的代码时,进程必定会通过页表访问物理内存。检测页表时,发现数据不在内存中,于是地址空间不再直接与磁盘上的可执行程序建立联系,os将a.exe加载到物理内存中,通过页表与地址空间建立联系。这叫做缺页中断

其实,物理内存也被分成了若干个4KB大小的小空间,我们称之为页框。os将a.exe加载到物理内存中的具体过程就是通过IO,将4KB大小的页帧放进4KB大小的页框中。

当然,对于这些若干个页框,os也必须对其进行管理。每一个页框都有一个struct page结构体,里面都是页框的各种属性,该结构体中有一个成员flag,表示该页框是否被占用。然后将这些结构体存储到一个 struct page men[ ] 数组中,数组的下标就是该页框的编号。 

3、虚拟地址到物理地址的转化

我们结合下图进行说明。

我们早就知道虚拟地址和物理地址之间的联系是通过页表建立的。但是,真正的转化是不止通过一个页表来实现的。

我们平时所说的地址就是虚拟地址,它一共有32个比特位,页表是一种key,value结构的数据结构。我们通过前10个比特位找到一级页表中的key,然后通过value值找到二级页表,然后通过虚拟地址的第二组10个比特位,找到二级页表的key值位置,接着根据value值找到物理内存中某个页的起始地址。最后,根据虚拟地址的最后12个比特位,进行数值计算,最后找到数据在该页的准确位置。

二、线程的概念

1、基本概念

1、在一个程序里的一个执行路线就叫做线程(thread)。更准确的定义是:线程是一个进程内部的控制序列,一切进程至少都有一个执行线程。

2、线程在进程内部运行,本质是在进程地址空间内运行。

3、透过进程虚拟地址空间,可以看到进程的大部分资源,将进程资源合理分配给每个执行流,就形成了线程执行流。

每个进程都有自己独立的地址空间和独立的页表,也就意味着所有进程在运行时本身就具有独立性那么如果我们在创建“进程”时,只创建PCB,并要求新创建出来的PCB与第一次创建的PCB共享地址空间,页表等资源,那么就是下图的情况:

每个线程都是当前进程里的一个执行流,线程在进程内部运行,准确来说线程在进程的地址空间内运行,拥有并使用该进程的一部分资源。 

所以说,进程从内核的角度来说就是承担分配系统资源的基本实体,因为线程都是直接从进程处拿到各种资源的。当然,这与我们之前所理解的进程的概念并不矛盾,我们之前的进程都只有一个PCB,也就是该进程内部只有一个执行流,即单执行流进程。从今天开始,我们就会讲到一个进程有多个执行流,即多执行流进程。

从用户的角度来说,进程就是包括一个或多个PCB(执行流)、地址空间、页表等内核数据结构以及内存中的代码和数据。

线程是CPU调度的基本单位。

前面,我们说,CPU去处理一个进程的时候,最先拿到的是它的PCB,来决定调度谁。那么,现在我们知道了,准确来说,CPU拿到的是一个线程,因为CPU以task_struct为单位进行调度。

我们给CPU的task_struct是小于等于过去所说的task_strcut的,比之前的更轻量化了(Linux下的进程也叫做轻量级进程)。因为每一个task_struct只管理着一个进程的一部分资源。它是进程下的一个执行流。

Linux下的线程是用进程PCB模拟的。

在Linux下,设计者并没有单独为线程设计一个像进程的PCB那样的数据结构, 因为,线程所需要的属性和进程非常相似,所以我们直接复用PCB,用PCB来表示Linux内部的“线程”。但是,如果os真的要专门设计“线程”概念,os那就需要管理线程了:先描述在组织,这样就提高了os的维护成本。

Linux内核中有没有真正意义的线程,Linux是用进程PCB来模拟线程的,这种设计方法是Linux特有的。

2、线程的优点

1、创建一个新线程的代价要比创建一个新进程小得多。
2、与进程之间的切换相比,线程之间的切换需要操作系统做的工作要少很多。
3、线程占用的资源要比进程少很多。
4、能充分利用多处理器的可并行数量。
5、在等待慢速I/O操作结束的同时,程序可执行其他的计算任务。
6、计算密集型应用,为了能在多处理器系统上运行,将计算分解到多个线程中实现。
7、I/O密集型应用,为了提高性能,将I/O操作重叠。线程可以同时等待不同的I/O操作。

3、线程的缺点

1、性能损失
一个很少被外部事件阻塞的计算密集型线程往往无法与共它线程共享同一个处理器。如果计算密集型线程的数量比可用的处理器多,那么可能会有较大的性能损失,这里的性能损失指的是增加了额外的同步和调度开销,而可用的资源不变。
2、健壮性降低
编写多线程需要更全面更深入的考虑,在一个多线程程序里,因时间分配上的细微偏差或者因共享了不该共享的变量而造成不良影响的可能性是很大的,换句话说线程之间是缺乏保护的。
3、缺乏访问控制
进程是访问控制的基本粒度,在一个线程中调用某些OS函数会对整个进程造成影响。
4、编程难度提高
编写与调试一个多线程程序比单线程程序困难得多。

4、线程异常 

单个线程如果出现除零,野指针问题导致线程崩溃,进程也会随着崩溃。线程是进程的执行分支,线程出异常,就类似进程出异常,进而触发信号机制,终止进程,进程终止,该进程内的所有线程也就随即退出 。

#include <iostream>
#include <unistd.h>
#include <string>
#include <pthread.h>using namespace std;void *thread_run(void *argc)
{while(true){sleep(1);int a = 10;a /= 0;}
}int main()
{pthread_t tid;pthread_create(tid, nullptr, thread_run, (void *)"thread1");while (true){cout << "main thread pid: " << getpid() << endl;sleep(3);}return 0;
}

​​​​​​​ 

5、线程用途

合理的使用多线程,能提高CPU密集型程序的执行效率合理的使用多线程,能提高IO密集型程序的用户体验(如生活中我们一边写代码一边下载开发工具,就是多线程运行的一种表现)。

三、Linux下的进程和线程

1、进程是资源分配的基本单位。
2、线程是调度的基本单位。
3、线程共享进程数据,但也拥有自己的一部分数据。

线程共享的进程资源:

1、文件描述符表
2、每种信号的处理方式(SIG_ IGN、SIG_ DFL或者自定义的信号处理函数)
3、当前工作目录
4、用户id和组id

线程需要自己私有的资源:

1、线程ID
2、一组寄存器(线程必须要有自己的上下文)
3、栈(独立的栈结构,能够保存自己的临时变量)

4、errno
5、信号屏蔽字
6、调度优先级

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/726547.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

MySQL 备份方案

优质博文&#xff1a;IT-BLOG-CN 一、为什么要备份 【1】容灾恢复&#xff1a;硬件故障、不经意的 Bug 导致数据损坏&#xff0c;或者服务器及其数据由于某些原因不可获取或无法使用等&#xff08;例如&#xff1a;机房大楼烧毁&#xff0c;恶意的黑客攻击或 Mysql 的 Bug 等&…

8、Linux驱动开发:驱动-读写接口实现(readwrite)

目录 &#x1f345;点击这里查看所有博文 随着自己工作的进行&#xff0c;接触到的技术栈也越来越多。给我一个很直观的感受就是&#xff0c;某一项技术/经验在刚开始接触的时候都记得很清楚。往往过了几个月都会忘记的差不多了&#xff0c;只有经常会用到的东西才有可能真正记…

网络协议学习DAY1

1.网络协议模型: OSI协议模型 应用层 实际发送的数据 表示层 发送的数据是否加密 会话层 是否建立会话连接 传输层 数据传输的方式&#xff08;数据报、流式&#xff09; 网…

Seata 2.x 系列【4】产品简介

有道无术&#xff0c;术尚可求&#xff0c;有术无道&#xff0c;止于术。 本系列Spring Boot 版本 3.1.0 本系列Seata 版本 2.0.0 源码地址&#xff1a;https://gitee.com/pearl-organization/study-seata-demo 文章目录 1. 概述2. 发展历史3. 核心术语3.1 TC3.2 TM3.3 RM 4.…

Unity3D 冯高光与布林冯高光经验模型详解

前言 Unity3D是一款非常流行的游戏开发引擎&#xff0c;它为开发者提供了丰富的功能和工具&#xff0c;使得开发游戏变得更加简单和高效。在Unity3D中&#xff0c;冯高光与布林冯高光经验模型是一种常用的光照模型&#xff0c;用来模拟光线在表面上的反射和折射效果。本文将详…

国创证券|存钱有窍门,掌握这五个窍门利息高出不少?

大部分居民会把手中闲置的资金存入银行&#xff0c;享用安稳的收益&#xff0c;其间存在以下五个诀窍&#xff1a; 1、比照不同银行的利率 储户在去银行存钱时&#xff0c;能够比照不同银行的利率&#xff0c;尽量地挑选利率较高的银行存&#xff0c;来获取较多的收益&#x…

MYSQL筛选字段是否为手机号码

1、需要判断导出的手机号正确性 2、观察到数据中包含“1”、“86”、“86”开头的手机号 3、手机号验证规则&#xff0c;1&#xff08;861&#xff0c;861&#xff09;开头的&#xff0c;第二位从3-9的11位数字&#xff08;除去86&#xff0c;86开头&#xff09; 百度到的正…

URL?后参数有特殊字符问题

前端对于URL的参数不做处理 不处理、用URLDecoder.decode()处理、用URLEncoder.encode()处理、用URLEncoder.encode()处理后再用URLDecoder.decode()处理 结果 前端对于URL的参数用encodeURIComponent(‘XF-OPPZZD-26*316’)处理 结果 前端不处理有&字符时 结果会把后…

BUUCTF---[极客大挑战 2019]BabySQL1

1.这道题和之前做的几道题是相似的&#xff0c;这道题考的知识点更多。难度也比之前的大一些 2.尝试万能密码 or 1#发现过滤了or,使用1和1,发现他对单引号也进行了过滤。于是我尝试进行双写绕过&#xff0c;发现可以通过了。 3.由之前的做题经验可知&#xff0c;这道题会涉及到…

【C#语言入门】10. 操作符详解(下)

【C#语言入门】10. 操作符详解&#xff08;下&#xff09; 四、各类操作符的示例 (T)x 强制类型转换符 //ushort的maxvalue是65535 uint x 65536; ushort y (ushort)x; Console.WriteLine(y);//结果为0类型转换 隐式&#xff08;implicit&#xff09;类型转换 不丢失精度的…

CMake的cmake_dependent_option用法

前言 本篇文章讲解CMake的cmake_dependent_option用法 选项和变量 在讲cmake_dependent_option之前&#xff0c;先讲一下CMake的选项和变量 选项 在CMake中&#xff0c;选项可以用来控制构建过程中的一些开关。我们可以使用option()命令来添加一个选项。option的函数原型如…

ChatGPT的安全警告

ChatGPT作为一种强大的人工智能模型&#xff0c;在提供便利的同时&#xff0c;确实存在一些安全隐患&#xff0c;需要引起我们的关注和重视。 首先&#xff0c;ChatGPT可能会提供不准确或虚假的信息。这主要源于其训练数据的多样性和复杂性&#xff0c;以及模型的自身局限性。…

每日汇评:黄金上破2161美元纪录高位,有可能进一步上涨?

周四早间&#xff0c;金价在2150美元的历史高点附近盘整&#xff0c;并成功上破2160历史高位&#xff1b; 美元在美债收益率的压力下逐步走低&#xff0c;市场期待更多鲍威尔讲话和美国就业数据&#xff1b; 日线图上的RSI指标超买状况继续令黄金买家保持谨慎&#xff1b; 金价…

中外联合培养工商管理博士|社科大新加坡社科大学中文授课DBA

中外联合培养工商管理博士|社科大新加坡社科大学中文授课DBA 全球经济正在经历由科技进步和创新、政治和人口剧烈变化所带来的巨大的不确定性和挑战。面对日趋复杂的外部竞争环境&#xff0c;企业的领导者和管理者需要具备卓越的战略思维和全球洞察力、以科学的精神和严谨务实的…

如何在手机上中恢复已删除的照片

市场上有大量用于恢复手机已删除照片的应用程序。您可以尝试任何合法的应用程序来恢复意外删除的视频。其中一些应用程序包括 奇客数据恢复、Disk Drill等。 恢复已删除的 Android 照片 如果您不小心从 Android 设备中删除了任何重要视频&#xff0c;无需惊慌。您可以按照这些…

2024中国(浙江)环保产业与水科技博览会

汇聚科技智慧力量&#xff0c;助力美丽中国建设 浙江省环境服务业高质量发展大会 2024中国&#xff08;浙江&#xff09;环保产业与水科技博览会 China (Zhejiang) environmental protection industry and Water Technology Expo I 环保产业 I 水利科技 I 智慧水务 I 泵管阀…

Java8 CompletableFuture异步编程-入门篇

&#x1f3f7;️个人主页&#xff1a;牵着猫散步的鼠鼠 &#x1f3f7;️系列专栏&#xff1a;Java全栈-专栏 &#x1f3f7;️个人学习笔记&#xff0c;若有缺误&#xff0c;欢迎评论区指正 目录 前言 1、Future vs CompletableFuture 1.1 准备工作 1.2 Future 的局限性 …

从0开始学习NEON(2)

1、前言 继上一个例子&#xff0c;本次继续来学习NEON&#xff0c;本次学习NEON中向量拼接的操作&#xff0c;主要应用在图像的padding中。 https://blog.csdn.net/weixin_42108183/article/details/136440707 2、案例 2.1 案例1 在某些情况下&#xff0c;需要取在每个向量…

小程序环形进度条爬坑

在做微信小程序的时候&#xff0c;发现用canvas做的环形进度条&#xff0c;在带滚动条的view里面显示有闪动、显示不全的问题&#xff0c;后面改成echart-weixin的pie图实现了&#xff0c;option配置如下 // 表示进度的百分比 var progressValue 70;option {series: [{type: …

双非二本实习前的准备day8

学习目标&#xff1a; 每天2-3到简单sql&#xff08;刷完即止&#xff09;&#xff0c;每天复习代码随想录上的题目2-3道算法&#xff08;时间充足可以继续&#xff09;&#xff0c;背诵的八股的问题也在这里记录了 今日碎碎念&#xff1a; 1&#xff09;今天任务&#xff1…