category
type
status
date
slug
summary
tags
password
Property
Apr 3, 2023 12:23 PM
icon
February 21
- 计算机网络
- Golang net/http包相关特性
March 3
- I/O多路复用:select/poll/epoll
文件描述符
:socket实际上是一个文件,也就会对应一个文件描述符。在Linux下,单个进程打开的文件描述的数量是有限制的,没有经过修改的值一般是1024,可以通过ulimit增大文件描述符的数目。
- Linux高性能网络模式Reactor和Proactor
March 4
- 零拷贝技术(
适用于小文件传输
): 真正的零拷贝技术
:两次上下文切换和两次数据拷贝- 没有SG-DMA的文件传输技术(两次上下文切换和三次数据拷贝):
- DMA拷贝技术:用户进程调用read系统调用后,CPU发出IO请求到DMA中,DMA再发生IO请求到磁盘中,磁盘将数据读取读取到磁盘缓冲区中,读取完毕后通知DMA控制器,DMA控制器将数据从磁盘缓冲区读取到内核缓冲区,读取完毕后通知CPU将内核缓冲区中的数据拷贝到用户缓冲区中。最后read系统调用返回:
- 传统的文件传输存在四次用户态和内核态之间的上下文交换(因为发生了reade和write两次系统调用)以及四次数据拷贝:
- 采用mmap+write优化后: 由于mmap系统调用会直接把内核缓冲区的数据映射到用户空间,以避免操作系统内核和用户空间之间的数据拷贝。但是仍然存在4次上下文切换,但是数据拷贝次数变为3次
- 内核缓冲区主要是指:PageCache,其主要优点是缓存最近被访问的数据和预读功能。
- 在传输大文件时使用PageCache会存在以下问题:
- PageCahe由于长时间被大文件占据,其他【热点】小文件就无法充分使用到PageCache于是导致磁盘的读写性能下降
- PageCache中的大文件数据,由于没有享受到缓存带来的好处,白白浪费了DMA多拷贝到PageCache一次。
- 在高并发场景下,针对大文件的传输,应该采用
异步I/O+直接I/O
来代替零拷贝技术: - 实用例子:
note:





大文件传输:

在 nginx 中,我们可以用如下配置,来根据文件的大小来使用不同的方式:
当文件大小大于
directio
值后,使用「异步 I/O + 直接 I/O」,否则使用「零拷贝技术」- Redis大Key对持久化的影响
- 在
AOF写回策略
中配置Always
策略,马上调用fsync()
函数将数据写入磁盘,如果此时是大key则写入时间会比较长,从而造成redis主线程的阻塞。 而Everysec
策略是会创建一个异步的任务来执行fsync()
函数,所以大key持久化过程不会影响redis主线程。 而No
策略永不会执行fsync()函数,由操作系统确定写入磁盘时机,所以大key的持久化也不会影响redis主线程。 在RDB策略下
,随着越来越多的大key存在,redis占用的内存会越来越大,对应的页表就会越大。在通过fork()创建子进程时复制页表就会很耗时,从而影响redis的主线程
。 修改大key时,会触发写时复制,会把对应物理内存复制一份
,由于大key占用的物理内存比较大,所以在复制物理内存这一过程中会很耗时,从而影响redis的主线程。- Linux开启内存大页是会影响redis性能的,内存大页支持2M大小的内存页分配,而常规的内存页分配是按照4KB的粒度来进行的。 如果开启内存大页,在RDB过程中如果客户端只请求修改100B的数据,在发生写时复制后,redis也要拷贝2M的大页,每次写时复制引起的复制内存单位放大了512倍,拖慢了写操作的执行时间,使redis的性能大打折扣。 关闭内存大页的方法:
note:

- C++中的
std::move
函数
备注:基础不够未看完,补C++基础ing……
- 理解 C/C++ 中的左值和右值
March 7
March 27
April 2
- Golang 编译时使用
-ldflags
实现版本信息注入
- dart
箭头函数
??=
和??
运算符