本站消息

  出租广告位,需要合作请联系站长

  今日名言-想象你自己对困难作出的反应,不是逃避或绕开它们,而是面对它们,同它们打交道,以一种进取的和明智的方式同它们奋斗 。——马克斯威尔·马尔兹

  今日名言-用谅解、宽恕的目光和心理看人、待人。人就会觉得葱笼的世界里,春意盎然,到处充满温暖。——蔡文甫


+关注
已关注

分类  

暂无分类

标签  

暂无标签

日期归档  

暂无数据

程序员基础知识

发布于2021-07-24 21:07     阅读(577)     评论(0)     点赞(26)     收藏(3)


硬件基础知识

关于底层的细节:适度打开

cpu制作:一堆沙子+一堆铜+一堆胶水+特定金属添加+特殊工艺

cpu原理:怎么代表数字(晶体管(二极管,逻辑开关),电代表数字)

cpu组成:PC(program counter)程序计数器 Registers 寄存器(暂时存储cpu需要的数据)ALU计算逻辑单元CU控制单元MMU内存管理单元,四核八线程(一个运算单元对应两个寄存器和pc)

三级缓存 缓存锁实现之一:MESI(每个公司的cpu缓存一致性协议名字不一样,英特尔缓存行64字节) cache 缓存一致性协议

有些无法缓存的数据或者跨越多个缓存行的数据依然必须使用总线锁

JDK7采用long padding提高效率 JDK8加入@contended注解

CPU乱序执行

DCL单例中必须加volatile,禁止指令重排序,以免线程使用了半初始化状态的对象

乱序条件:as if serial 单线程执行出来的结果一样的

NUMA 分配内存会优先分配该线程所在CPU的最近内存 ZGC可以做到

内核:操作系统管理硬件,庞大,在一起(如PC、手机) 微内核:5G IoT芯片,应用程序的调度,弹性部署 外核:定制化科研实验室中

用户态与内核态 linux内核跑在ring 0级,用户程序跑在ring 3,对于系统的关键访问,需要经过内核同意,保证系统的健壮性

内核执行的操作(200多个系统调用)sendfile read write pthread fork

JVM->站在OS老大面前,只是个程序

纤程:用户级别的线程,需要的资源很小

进程 线程 纤程 中断

面试高频:进程和线程有什么区别?

进程(进程描述符PCB)是程序运行起来的状态,线程是进程中的不同执行路径,进程是OS分配资源(独立的内存的空间)的基本单位,线程(共享进程的内存空间,没有独立的内存空间)是执行调度的基本单位 linux中线程就是普通的进程,只是共享内存,windows是LWP 轻量级进程

纤程是在用户态的,是线程中的线程,切换和调度不需要经过OS 优势:1.占用资源少:线程:1M Fiber:4k 2.切换简单 3.启动很多个10w+

目前2020年 支持纤程:Kotlin Scala Go Python(lib)Java(目前还没内置 loom)

纤程的应用场景

纤程vs线程池:很短的计算任务,不需要和内核打交道(不用去文件读什么东西的时候)并发量高!

内核线程是内核自己的线程 进程创建和启用 系统函数fork()(父子进程) exec()

僵尸线程:父进程产生子进程后,会维护PCB结构,子进程退出,父进程还没释放这个结构(挂个名)

孤儿线程:子进程结束之前,父进程就已经退出了,给一个指定进程去维护

进程调度

非抢占式 抢占式(进程调度器开始或暂停)

linux调度:2.5版本的 时间片轮询,偏向服务器,对交互不友好 2.6版本 CFS完全公平调度算法(不再采用绝对时间片,按优先级分配时间片的比例,记录每一个进程的执行时间,如果有一个进程时间不到分配的比例优先执行)实时进程绝对优先于普通进程

中断

硬件和内核的打交道,如键盘敲下来了的通信机制,硬件传给cpu,cpu找到固定程序,固定程序找到操作系统再给处理程序

软中断==系统调用:一个特殊的中断符号,16进制的80 中断只是个信号(软件产生的中断)

ax填入调用号,其他寄存器传入参数,再通过ax返回

一个程序的执行过程,要么处于用户态,要么处于内核态

阻塞和非阻塞:用户态中执行需要中断去内核态中执行,用户态还能不能继续执行

内存空间

多个进程装入内存:1.内存不够用 2.相互打扰

为了解决这两个问题,诞生了现在的内存管理系统:虚拟地址 分页装入 软硬件结合寻址

1.分页(内存不够用),内存中分成固定大小的页框(4k),把程序(硬件上)分成4k大小的块,用到哪块加载哪块,加载的过程中,如果内存满了,会把最不常用的块放到swap分区,这就是著名的LRU算法(所有涉及到缓存的算法) LeetCode146题 least Recently Used 最不常用(哈希表查找O(1)+双向链表排序新增O(1))

2.虚拟内存(相互打扰用),让进程工作在虚拟空间,不再是直接的物理地址。虚拟空间多大呢? 寻址空间64位系统2^64位,比物理内存大很多 站在虚拟空间角度,进程是独享整个系统+cpu 内存映射:线性地址=偏移量+基地址 线性地址通过OS+MMU映射到物理地址

3.缺页中断:页面内存中没有,产生缺页异常,由内核处理并加载

ZGC

ColoredPointer,GC信息记录在指针上,不是记录在头部 (好处:内存立即重用,不用改头部信息)

42位指针 寻址空间4T 目前最大支持16T 原因:CPU如何区分一个立即数和一条指令 总线内部分为:数据总线 地址总线 控制总线 地址总线:48位 4颜色指针 颜色指针本质上包含了地址映射的概念

系统IO原理

一切皆文件:-:普通文件(可执行、图片、文本)REG d:目录 l:链接 b:块设备 c:字符设备 s:socket p:pipeline

任何程序都有 文件描述符 0:标准输入 1:标准输出 2:报错输出 I/O重定向 pipelin e是起子进程

操作系统的page cache 是为了优化IO性能 缺点是丢失数据

普通IO一次一次写 BufferIO一次写8字节

NewIO filechannel 通过mapped:是mmap调用一个进程和内核共享的内存区域且这个内存区域是pangecache到文件的映射, put()不会产生系统调用,但也受pagecache影响,更快一些 netty(on heap, off heap). Kafka log:mmap

OS没有绝对数据可靠性,为什么设计pagecache,减少 硬件 IO调用,提速,优先使用内存

即使你想要可靠性,调成最慢的方式 但是单点问题会让你的性能损耗,一毛钱收益都没有

解决办法 主从复制 主备HA kafka/es 副本(socket io)(同步/异步)

lsof -p 查询文件描述符 netstat -natp 查询网络状况 tcpdump监听包

NIO

SocketIO

tcp:面向连接的,可靠的传输协议 三次握手 内核级开辟资源

socket 四元组 CIP CPORT+SIP SPORT (唯一性 内核级的 即使你不调用accept)

TCP拥塞:当客户端窗口满了,回服务端满了,服务端就会阻塞不发

socket的参数:backlog 有多少等待着 buffersize 缓冲区大小,有优化的时候包攒着发,没优化的时候直接就发

keepalive(tcp层面的)双方建立了连接很久不说话,tcp会自动发数据确认是否还存活

strace -ff -o out cmd 追踪系统调用,io实现

同步异步:调用,在得到结果之前返不返回(关注消息通信机制) 阻塞非阻塞:得到结果之前线程是否被挂起等待(关注的是程序等待结果的状态)

只关注IO:不关注从IO读写完之后的事情

同步:app自己R/W 异步:kernel完成R/W 仿佛程序只访问了buffer没有访问IO win:io cp

阻塞:调了方法一直等到返回值 非阻塞:调了返回是否读到,不等待继续往下运行后面再多次询问

linux以及成熟的框架netty 常用同步阻塞和同步非阻塞

BIO时代:阻塞,速度慢

socket = fd3 bind(fd3,8090)listen(fd3)接受监听阻塞,克隆线程去接收消息阻塞-> netstat -natp 0.0.0.0:8090 0.0.0.0:* LISTEN

NIO:newio可以设置非阻塞configureblocking(false) 不用抛出线程

优势:可以通过一个或多个线程,来解决N个IO连接处理

问题:C10K 每循环一次:O(n)复杂度rev 很多调用是无用的,浪费的 调用是系统调用

解决办法:多路复用器,多条路(IO)通过一个系统调用,获得其中的IO状态,然后由程序自己对有状态的IO进行R/W

多路复用器:SELECT POSIX/POLL/EPOLL(同步模型下非阻塞的多路复用)

其实无论NIO,多路复用器都是要遍历所有的IO,询问状态只不过

NIO遍历过程成本在用户态内核态切换

多路复用器SELECT POSIX/POLL遍历的过程触发了一次系统调用,用户态内核态切换过程中把fds传递给内核,内核重新根据用户这次调用传来的fds遍历查询状态

SELECT POSIX/POLL问题:1.每次都要重新传递fds 2.每次内核被调之后,针对这次调用,触发一个遍历fds全量的复杂度

EPOLL:内核中,程序在红黑树中放过一些fd,那么伴随内核基于中断处理完fd的buffer,状态之后,继续把有状态的fd拷贝到链表中(不用每次都遍历fd,程序只要调用wait,能及时取走有状态的fd结果集) io threads 业务交给其他线程处理

为什么ulimit -n 1024还是超过了1024?root用户权限形同虚设,但是生产环境肯定是非root用户

原文链接:https://blog.csdn.net/qq_35818890/article/details/118863422



所属网站分类: 程序员的那点事

作者:每个人身上都有毛毛

链接:http://www.pythonpdf.com/blog/article/285/43fcb0b66d1576db1ff7/

来源:编程知识网

任何形式的转载都请注明出处,如有侵权 一经发现 必将追究其法律责任

26 0
收藏该文
已收藏

评论内容:(最多支持255个字符)