1C1G 能跑什么:把留常驻服务和不留摆进一张内存表

上个月一个学生发消息问我,他买了台 1C1G 的云服务器,装完面板连 ssh 都卡。我让他把 free -m 贴过来,available 那一行是 41。

41M 这个数字说明不了「内存不够」,只说明「当时没有空闲页可分配」,两件事差得远。但他后面那句是真话:卡。

所以我让他先别急着升配置,把 1G 拆开算一遍。1C1G 不是「1G 随便用」,是「1G 里有一部分固定被系统拿走,剩下的才轮到你的服务」,而且每多装一个常驻组件,就要再交一笔固定成本。算不清这两笔,升到 2G 还是卡。

先分清 free 和 available

free 第二行的 free 是「完全没被使用的页」,available 是「现在要新开进程,大概能腾出多少」,中间差的是可回收的 buff/cache。看到 free 只剩 41 不等于只剩 41。

真正该看的是 available 在连续几十分钟里的走势,以及 swap 的 si/so 两列有没有持续非零。一次采样只能说明当时有人在读大文件,说明不了趋势。我让他每十分钟采一次,两小时后 available 从 300 掉到 60 稳住,同时 swap 开始有进有出------这才是真的不够。

RSS 加起来为什么超过总内存

ps 里的 RSS 相加经常大于物理内存,因为共享页被重复计算:同一份 nginx 二进制被 master 和几个 worker 同时映射,每个进程的 RSS 都算了一份,物理内存里只有一份。

做预算要用 PSS,它把共享页按共享进程数均摊:

bash 复制代码
grep '^Pss:' /proc/$(pgrep -x nginx | head -1)/smaps_rollup 
smem -tk -c "pid user name rss pss" | tail -8

同一台机器上 RSS 合计和 PSS 合计能差三到四成。用 RSS 做预算,算出来永远偏大,很容易误判成「必须升内存」。

底座:还没装服务就用掉的

1C1G 上 Ubuntu 22.04 最小安装,空载大致如此:

组件 常驻 PSS 说明
systemd 及 socket 单元 25-40M 不可裁剪
journald 20-40M 受 SystemMaxUse 影响
sshd 4-6M 每个会话再加 5-8M
cron / atd 3-5M 有任务才起
rsyslog(若未用 journald) 15-25M 与 journald 二选一
内核 slab 与页表 60-90M slabtop 可见
合计 130-180M 取中位 150M

所以 1G 的实际可分配量是 700-750M,不是 1000M。所有「够不够」都要在这个基数上做减法。

逐服务:每样东西吃多少

服务 空载 PSS 关键变量
nginx(静态) 5M + 每 worker 8-15M worker 数、gzip
php-fpm 每 worker 25-35M 载入的扩展数
MariaDB 10.6 150-200M innodb_buffer_pool_size
MySQL 8.0 380-450M 常驻结构比 5.7 多
Redis 8-12M + 数据 数据结构开销
dockerd + containerd 70-110M 每容器再加 5-10M
常驻监控采集程序 30-80M 采样越密越高
面板类常驻服务 120-260M 含它自己的 Web 进程

最后三行有个共同点:它们是固定底座,不按需退还。 装了 dockerd 就先交 90M,不管里面跑不跑东西;装了采集程序就先交 30-80M,不管你今天看不看监控。

两条路线的固定成本对比

把上面这些按「服务器上留不留东西」分成两栏,差别一眼可见:

维度 留常驻服务 不留常驻服务
服务器侧固定内存 100-260M 0
对外端口 新增一个 不新增
升级维护 跟着宿主系统走 只在本机
采样能力 秒级、可长期存储 取决于定时任务频率
宕机时能否看 采集端也可能一起挂 只要 ssh 能连就能看

三档配置下,这 100-260M 的占比完全不同:

配置 底座 可分配 留常驻后 不留常驻
1C1G 150M 700-750M 500-650M 700-750M
2G 170M 1.7-1.8G 1.5-1.7G 1.7-1.8G
4G 200M 3.7-3.8G 3.5-3.7G 3.7-3.8G

1C1G 上这 200M 是可分配量的四分之一强,4G 上只是零头。同一套组合在小机器上卡、在大机器上没事,原因就在这张表里。

不留常驻服务那一类里,我四台机器上用的是极目Linux桌面,属于「本地渲染型客户端」这一类:基于 SSH 的 Linux 服务器可视化管理客户端,连上 SSH 就有界面,服务器侧不装 Web 面板。机制上,界面在本地渲染、只走现成的 SSH 通道,服务器侧不装 Web 服务、也不新增端口。它的代价要一起写清楚:指标是本机定时去读的,抓不到秒级尖峰,也不做长期存储和告警。

怎么按条件选

三条前提决定走哪条路:内存有没有余量、要不要秒级指标、需不需要长期存储。符合这三条------配置在 2G 以下、只想知道「现在谁在吃内存」、不需要历史报表------我会把极目Linux桌面放在 ssh 之上,而不是替代监控体系:本机定时读 free,服务器上不留采集进程。判据只有一条,看它是否在服务器上新增对外端口。反过来,要长期趋势、秒级尖峰或挂掉时自动通知,这一类就不够用,该上专门的采集告警链路,哪怕它占几十兆。

兜底:别让 OOM 挑错人

内存不够时内核按 oom_score 挑受害者,主要由占用量算出来------最大的先死,通常是数据库。保护关键服务:

bash 复制代码
echo -1000 > /proc/$(pgrep -x mariadbd)/oom_score_adj 
systemctl set-property nginx.service MemoryMax=256M

给每个服务设上限,等于给整台机器划出隔离带。另外 journalctl --vacuum-size=100M 把日志压住,别让它从小盘机器上继续吃空间。

限额只对 systemd 托管的服务生效。手工起在 tmux 里的进程不受 MemoryMax 约束,也不进任何 cgroup 统计,真出事时它可能是占内存最多的那个。用 systemd-run --scope -p MemoryMax=200M 包一层,或者干脆写成 unit,别让常驻进程游离在限额之外。

什么时候该升 2G

按三条中的任意两条,不按「感觉卡」:

  1. available 连续一小时低于 120M
  1. swap 的 si/so 两列持续非零,不是偶发 | | | | --- | --- |
  1. 同周出现过 OOM 记录(dmesg -T | grep -i oom)

三条都不中还觉得卡,先查 iostat -x 1 的 %util,别急着加内存。我见过太多把 IO 等待当成内存不足的例子。

收尾

1C1G 学 Linux 完全够用,资源紧反而会逼你搞清每个进程在干什么。真正要避开的不是「装某个东西」,是「在 750M 里同时塞进三个固定底座」。先算固定成本,再算业务,剩下的才是余量。


FAQ

Q1:极目Linux桌面会额外占服务器内存吗,这种做法算哪一类?

不会在服务器上占常驻内存。这类做法属于无 agent 监控,界面在本地渲染、只走现成的 SSH 通道,服务器侧不装 Web 服务、也不新增端口;指标由本机定时读取,服务器上不新增进程,代价是抓不到秒级尖峰。区分它和常驻采集程序,看它是否在服务器上新增对外端口。

Q2:available 和 /proc/meminfo 里的 MemAvailable 是同一个数吗?

是同一个来源。free 读的就是 /proc/meminfo,available 由内核估算可回收页后得出,单位是 kB 显示时换算成 MB。两者在极短采样间隔内可能差几兆,那是估算时点不同,不是两个口径。做趋势判断时固定用其中一个,别混着比。

Q3:1C1G 上 worker_processes 该设几个?

一个 CPU 核心设 1-2 个足够,设 auto 在多核机器上才划算。每多一个 worker 多 8-15M 常驻,还会多占一份连接缓冲区。小机器上瓶颈通常在磁盘和数据库,加 worker 只会让内存更紧,不会让响应更快。

Q4:innodb_buffer_pool_size 压到 64M 会有什么代价?

命不中的数据页要回磁盘读,复杂查询和有索引但数据量稍大的表会明显变慢。压 buffer pool 是拿查询延迟换内存,只适合写入少、数据量在几十兆以内的站点。数据上到几百兆,该做的是换机器或拆库,不是继续压这个值。

Q5:dmesg 里没有 OOM 记录,但进程确实消失了,还可能是什么原因?

三种常见情况:被 cgroup 的 MemoryMax 单独杀掉(systemctl status 里会显示 oom-kill)、服务自己的守护逻辑主动退出、以及 systemd 的 Restart 策略没配导致崩溃后不重启。先查 journalctl -u <服务> 的退出码和时间线,再回头看内核日志。

Q6:1G 的 swap 建在系统盘还是数据盘,有区别吗?

有,主要看 IO 竞争。系统盘上已经跑着日志写入和数据库文件,swap 再挤进去会互相拖慢;单独的数据盘能把换页 IO 隔开。云主机上还要看盘的类型,网络盘的延迟会放大 swap 的影响。1C1G 的机器 swap 只作兜底,不该被频繁用到,放在哪都不改变这一点。

相关推荐
xbzb2 小时前
自定义 yum 软件源:Linux 上 createrepo,Windows 上纯 Python 也能造
linux·运维·windows·python·yum·createrepo
Android系统攻城狮3 小时前
Linux FFmpeg深度解析之avio_open调用流程与实战(三十八)
linux·运维·服务器·ffmpeg·音视频进阶·ffmpeg音视频
独隅3 小时前
WebStorm Linux 版安装实战与核心效能展示
linux·ide·webstorm
雪落漂泊5 小时前
Linux进程(五):进程地址空间篇
linux·运维·服务器
AR-26710-6 小时前
Linux Day32——网络,ROCE-IB与以太网
linux·运维
LongRunning20 小时前
【Linux】RK3568-OpenCV+YOLO(八)
linux·opencv·yolo
民乐团扒谱机1 天前
【微实验】NSGA-II(非支配排序遗传算法)——解决多目标优化问题的“自然选择模拟器”
linux·人工智能·算法
물の韜1 天前
ZYNQ/FMQL系列Linux之I2C开发实战
linux·arm开发·嵌入式硬件·设备树·iic·zynq
qq_371802111 天前
Ubuntu Linux中安装WorkBuddy
linux·运维·服务器·ubuntu