前言
本文翻译自红帽 RH442(性能调优) 课程
进程间通信
另一个潜在的内存消耗者是为进程间通信保留的内存机制,RHEL 即支持老的 IPC System V(SysV)也支持新的POSIX IPC 机制。
信号量支持两个或两个以上的进程对共享资源的协调访问。消息队列允许进程通过交换消息协同工作。共享内存允许进程在内存中的相同区域读写操作来交换信息。一个进程想要使用以上三种机制中的一种必须使用合适的系统调用来分配想要的资源,系统管理员可以限制进程可用的 SysV IPC 资源数量。
通过运行以下命令可以获得当前的 SysV IPC 资源限制:
[zyq@databases ~]$ ipcs -l
------ Messages Limits --------
max queues system wide = 32768
max size of message (bytes) = 8192
default max size of queue (bytes) = 16384
------ Shared Memory Limits --------
max number of segments = 4096
max seg size (kbytes) = 262144
max total shared memory (kbytes) = 18014398442373116
min seg size (bytes) = 1
------ Semaphore Limits --------
max number of arrays = 128
max semaphores per array = 250
max semaphores system wide = 32000
max ops per semop call = 32
semaphore max value = 32767
通过以下命令可以获得当前被使用的 SysV IPC 资源
[zyq@databases ~]$ ipcs
------ Message Queues --------
key msqid owner perms used-bytes messages
------ Shared Memory Segments --------
key shmid owner perms bytes nattch status
0x01135ecd 98304 root 600 1000 9
------ Semaphore Arrays --------
key semid owner perms nsems
0x00000000 327680 apache 600 1
0x00000000 360449 apache 600 1
0x00000000 393218 apache 600 1
0x00000000 425987 apache 600 1
0x00000000 458756 apache 600 1
对于重要的应用程序使用/dev/shm临时存储是一种有效的方法来提高服务时长,需要注意如果断电,/dev/shm中的所有数据将会丢失。
ipcrm命令可以强制删除共享内存段,由于进程终止时释放资源的方式,在 Linux 上很少直接使用此命令。
SysV IPC 机制相关的参数可以在/proc/sys/kernel/下调节,也可以直接调节以下内核参数:
- kernel.shmmni 共享内存段最大值(整个系统层面),默认 4096 个。
- kernel.shmall 系统一次可以被使用的总的共享内存的数量,单位 pages ,ipcs -l 展示的是转换成KiB的数值,这个值至少为kernel.shmmax/PAGE_SIZE,PAGE_SIZE可以通过getconf PAGE_SIZE查看。
- kernel.shmmax 单个共享内存段的最大值(单位 bytes),单位 bytes 。
- kernel.msgmnb 单个消息队列的最大值,单位 bytes 。
- kernel.msgmni 消息队列身份标识的最大值。
- kernel.msgmax 进程间可传输的消息最大的大小,注意这个内存不能被交换(swapped)。
- kernel.sem 信号量包含以下设置:
每个信号组的最大信号数量。
系统范围内允许的最大信号数量。
每个信号量系统调用允许的最大操作数。
最大的信号组数量。
注意
大量使用共享内存的软件厂商,会对操作系统关于共享内存的相关设置会有一个推荐设置。
参考
pinfo ipcs 和 ipcs(1),ipcrm(1),和 proc(5) man page
/usr/share/doc/kernel-doc-*/Documentation/sysctl/kernel.txt
练习:管理进程间通信
在这个实验中,测试限制进程间通信可以使用的共享内存大小,在练习结束时,你的机器将配置为禁止共享内存段的分配,但如果真的需要,可以限制为不超过 512 MiB。
开始之前
- 重置你的 serverX 系统。
- 以 student 用户登录图形界面的 serverX。
- 在 serverX 上打开一个 root shell。
- 查看当前被使用的共享内存段,注意 student 用户使用的共享内存段的数量。
[root@server0 ~]# ipcs -m
------ Shared Memory Segments --------
key shmid owner perms bytes nattch status
0x00000000 65536 student 600 4194304 2 dest
0x00000000 163841 student 600 4194304 2 dest
0x00000000 262146 student 600 1048576 2 dest
以上展示了 student 用户使用了三个共享内存段。
5.查看当前被允许分配的共享内存段。
[root@server0 ~]# sysctl kernel.shmmni
kernel.shmmni = 4096
6.临时减少系统可分配的最大共享内存段,将这个值修改为小于 student 用户正在使用的大小。
[root@server0 ~]# sysctl -w kernel.shmmni=0
kernel.shmmni = 0
7. 使用 ipcs -l 验证上一步的修改。
[root@server0 ~]# ipcs -l
------ Messages Limits --------
max queues system wide = 3678
max size of message (bytes) = 8192
default max size of queue (bytes) = 16384
------ Shared Memory Limits --------
max number of segments = 0 #已修改
max seg size (kbytes) = 4194303
max total shared memory (kbytes) = 1073741824
min seg size (bytes) = 1
------ Semaphore Limits --------
max number of arrays = 128
max semaphores per array = 250
max semaphores system wide = 32000
max ops per semop call = 32
semaphore max value = 32767
8. 退出图形界面会话,重新以 student 账户登录图形界面,查看系统当前被使用的共享内存段。
[root@server0 ~]# ipcs -m
------ Shared Memory Segments --------
key shmid owner perms bytes nattch status
可以发现当前没有共享段被使用。
9. 限制系统最高使用512MiB共享内存,并且配置永久生效。
不要直接修改 kernel.shmall 或者 kernel.shmmax 与 kernel.shmmni 。kernel.shmall 使用的单
位是 pages (4 KiB ), kernel.shmmax 使用的单位是 bytes 。
对于 kernle.shmall,将以下内容添加到 /etc/sysctl.conf 文件中,并使之生效,这个值通过以下
计算获得 [512*1024*1024/4096]。
kernel.shmall = 131072
[root@server0 ~]# sysctl -p
kernel.shmall = 131072
对于 kernel.shmmax 和 kernel.shmmni ,将以下内容添加到 /etc/sysctl.conf 文件中,并使之生 效,这个值通过以下计算获得 [512*1024*1024/8]。
kernel.shmmax = 67108864
kernel.shmmni = 8
[root@server0 ~]# sysctl -p
kernel.shmmax = 67108864
kernel.shmmni = 8
注意:kernel.shmmni 的值是随便选的,kernel.shmmax 和 kernel.shmmni 的值可以随便选,只要满足最大不超过512M就可以,例如,kernel.shmmax = 1045876 [1024*1024] , kernel.shmmni = 512 也是一样的。