為省錢 m6i 換 m6a,在 Web 場景下真的划算嗎?

更新 發佈閱讀 28 分鐘

結論直接看

整體而言,m6i.large(Intel Xeon)在 context switch 與高併發效能上顯著優於 m6a.large(AMD EPYC)

m6i 更適合用於需要頻繁切換的工作負載,例如 Web API、短命週期容器、Gateway、或高併發微服務。
m6a 則雖在整體效能上略遜,但對長期運算型任務仍具價格優勢。

若系統對互動延遲敏感、或經常出現「偶爾卡一下」的體感問題,m6i 會是更穩定的選擇。

Wei 啥的結論

6 Instance Family 的 Intel 家族還是很可靠的,不用為了那一點點錢犧牲性能。
得不償失。

其實 7 Instance Family 我也測了一下。結論也是一樣,只是差距不像 6 Instance Family 這麼明顯。所以我收回 閉著眼睛選 m7a?m7i 在雲端容器時代怎麼輸的 中的評論,如果是 Web 或是 多工的場景,還是使用 Intel 系列吧。

起因

剛好遇到朋友問說,他任職公司最近正在打算節省 AWS 上面的費用,打算把所有的 6i 機型都換成 6a。(儘管 7a 的單核效能屌打 7i,但是 7a 比較貴。)

問我到底該不該這麼做。
而我剛好正在燒 Credit,也剛做完 m6i 與 m6a 的 CPU 性能評比。
首先先搞清楚需求,他們最常用來跑 Restful API,對於大流量上的需求非常明確。

那單純的跑分就沒什麼意義了,反而是在 CS 的比對下比較重要。
因為每次的 Request 都可以看成是多執行緒併發。

什麼是 Context Switch

Context Switch,中文稱作上下文切換或環境切換,是電腦術語,指CPU從執行一個行程(process)切換到另一個行程時,必須儲存前者當前的執行狀態(上下文),再載入後者的狀態,以便讓多個行程能共享單一CPU資源。 這個切換過程需要時間,稱為Context Switch的「成本」,也是實現多工(multitasking)的關鍵機制。 

實驗

假設

那這樣設計實驗就很簡單了。
直接用 ab 狂打 nginx server 就可以了。

- 若 m6a 相比 m6i:

perf bench sched pipe 的平均尾端延遲更長
ab 場景下 cycles_per_switch 顯著更高(例如:1.3倍 到 2倍)
hackbench elapsed 更久
同時 p95/p99 延遲較差

則可合理歸因:切換排程每次成本較高,在高切換 I/O 場景體感「狀態卡頓」。

測試腳本

用 Linux 來跑,環境可以用在 Amazon Linux 2023 或是 ubuntu 22.04 上。

整體流程

  1. 建立輸出資料夾:依照時間建立 runs/YYYYMMDD_HHMMSS/
  2. 偵測系統套件管理工具dnf, yum, 或 apt-get)。
  3. 安裝測試所需套件:如 gcc, perf, sysstat, nginx, ab 等。
  4. 蒐集系統資訊:CPU、記憶體、kernel 參數等。
  5. 建構測試程式
    hackbench:自製的簡化 hackbench 負載測試。
  6. 準備 nginx:啟動 web server 給壓測工具用。
  7. 執行測試
    lat_ctx:測量 thread context switch 延遲。
    perf bench sched pipe:內建的 pipe-based context switch 基準。hackbench:模擬多進程通訊的切換壓力。
    ab(ApacheBench)+ perf stat:在實際 web 請求時測 cycles、context-switch、page-fault 等。
    perf stat(syscall mix):觀察系統呼叫分佈。
  8. 生成 SUMMARY.txt:整合所有結果(latency、每秒請求、每次切換週期等)。
#!/usr/bin/env bash
set -euo pipefail

# =========================
# Context Switch Repro Pack (v2)
# - Adds: --allowerasing for dnf
# - Adds: cycles_per_switch from perf stat during ab
# - Adds: perf bench sched pipe micro-benchmark
# - Makes lmbench/lat_ctx optional (build may fail on some distros)
# Tested on: Amazon Linux 2023 / AL2 / Ubuntu 22.04+
# =========================

TS="$(date +%Y%m%d_%H%M%S)"
OUT="runs/${TS}"
mkdir -p "${OUT}/logs" "${OUT}/bin" "${OUT}/src"

log() { echo "[$(date +%H:%M:%S)] $*"; }

detect_os() {
if command -v dnf >/dev/null 2>&1; then PM=dnf
elif command -v yum >/dev/null 2>&1; then PM=yum
elif command -v apt-get >/dev/null 2>&1; then PM=apt
else
echo "Unsupported OS: need dnf/yum/apt-get"; exit 1
fi
echo "${PM}" > "${OUT}/PM.txt"
}

install_deps() {
local pm="$1"
log "Installing dependencies via ${pm} ..."
case "${pm}" in
dnf)
sudo dnf -y update || true
sudo dnf -y install gcc gcc-c++ make git curl tar unzip \
sysstat perf nginx httpd-tools \
elfutils-libelf-devel zlib-devel --allowerasing
;;
yum)
sudo yum -y update || true
sudo yum -y install gcc gcc-c++ make git curl tar unzip \
sysstat perf nginx httpd-tools \
elfutils-libelf-devel zlib-devel
;;
apt)
sudo apt-get update -y || true
# linux-tools-$(uname -r) 可能抓不到,退而求其次安裝 linux-tools-common / generic
sudo apt-get install -y build-essential git curl tar unzip \
sysstat nginx apache2-utils linux-tools-common || true
sudo apt-get install -y "linux-tools-$(uname -r)" || true
sudo apt-get install -y linux-tools-generic || true
;;
esac

# enable sysstat (pidstat)
if command -v systemctl >/dev/null 2>&1; then
sudo systemctl enable --now sysstat >/dev/null 2>&1 || true
fi
}

build_lat_ctx() {
log "Building lmbench (lat_ctx optional) ..."
pushd "${OUT}/src" >/dev/null
if [ ! -d "lmbench" ]; then
git clone --depth=1 https://github.com/intel/lmbench.git || \
git clone --depth=1 https://github.com/ckolivas/lmbench.git lmbench || true
fi
if [ -d "lmbench/src" ]; then
cd lmbench/src
make results || true
make lat_ctx || true
if [ -f "lat_ctx" ]; then
cp -f lat_ctx "${PWD}/../../bin/"
else
echo "WARN: lat_ctx build failed; will skip lat_ctx test" | tee -a "${OUT}/SUMMARY.txt"
fi
else
echo "WARN: lmbench source not available; skip lat_ctx" | tee -a "${OUT}/SUMMARY.txt"
fi
popd >/dev/null || true
}

build_hackbench() {
log "Building hackbench-like ..."
pushd "${OUT}/src" >/dev/null
cat > hackbench.c <<'EOF'
#include <pthread.h>
#include <sched.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/time.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#define MSG "hello"
int main(int argc, char **argv) {
int groups = 10, loops = 10000;
if (argc > 1) groups = atoi(argv[1]);
if (argc > 2) loops = atoi(argv[2]);
for (int g=0; g<groups; g++) {
int fds[2]; if (pipe(fds) != 0) { perror("pipe"); exit(1); }
pid_t p = fork();
if (p < 0) { perror("fork"); exit(1); }
if (p == 0) {
for (int i=0; i<loops; i++) if (write(fds[1], MSG, sizeof(MSG)) < 0) perror("write");
close(fds[0]); close(fds[1]); _exit(0);
} else {
char buf[64];
for (int i=0; i<loops; i++) if (read(fds[0], buf, sizeof(MSG)) < 0) perror("read");
close(fds[0]); close(fds[1]); waitpid(p, NULL, 0);
}
}
printf("hackbench-like: groups=%d loops=%d done.\n", groups, loops);
return 0;
}
EOF
gcc -O2 -pthread -o hackbench hackbench.c
cp -f hackbench "${PWD}/../bin/"
popd >/dev/null
}

prep_nginx() {
log "Preparing nginx ..."
if command -v systemctl >/dev/null 2>&1; then
sudo systemctl enable --now nginx
else
sudo nginx || true
fi
echo "hello $(hostname) @ $(date)" | sudo tee /usr/share/nginx/html/index.html >/dev/null
}

run_lat_ctx() {
if [ ! -x "${OUT}/bin/lat_ctx" ]; then
log "lat_ctx not available; skipping"
return
fi
log "Running lat_ctx ..."
for s in 64 128 256 512; do
"${OUT}/bin/lat_ctx" -s "${s}" 2 4 8 16 | tee -a "${OUT}/logs/lat_ctx_${s}.log"
done
}

run_hackbench() {
log "Running hackbench-like ..."
for G in 10 50; do
/usr/bin/time -f "elapsed_sec=%E cs_switched=%w" \
"${OUT}/bin/hackbench" "${G}" 20000 \
2>&1 | tee -a "${OUT}/logs/hackbench_g${G}.log"
done
}

run_perf_pipe() {
log "Running perf bench sched pipe ..."
perf bench sched pipe -l 100000 > "${OUT}/logs/perf_pipe.txt" 2>&1 || true
}

run_web_ab() {
log "Running nginx + ab with perf stat (cycles,cs) ..."
sleep 1
pgrep nginx || sudo nginx || true
local NGINX_PIDS
NGINX_PIDS="$(pgrep -d, nginx || true)"
echo "NGINX_PIDS=${NGINX_PIDS}" > "${OUT}/logs/nginx_pids.txt"

( pidstat -w -t 1 -p ALL > "${OUT}/logs/pidstat_web.txt" ) &
PIDSTAT_BG=$!

# warm-up
ab -n 20000 -c 200 http://127.0.0.1/index.html >/dev/null 2>&1 || true

# main run + perf (system-wide)
perf stat -a -e cycles,instructions,context-switches,cpu-migrations,task-clock,page-faults \
ab -n 200000 -c 500 http://127.0.0.1/index.html \
> "${OUT}/logs/ab_stdout.txt" 2> "${OUT}/logs/perf_ab.txt" || true

sleep 1
kill ${PIDSTAT_BG} >/dev/null 2>&1 || true
}

run_perf_syscall_mix() {
log "Measuring syscalls during hackbench ..."
if perf list 2>/dev/null | grep -q syscalls:sys_enter; then
perf stat -a -e context-switches,syscalls:sys_enter_read,syscalls:sys_enter_write,syscalls:sys_enter_futex \
"${OUT}/bin/hackbench" 30 30000 \
> "${OUT}/logs/perf_syscalls_out.txt" 2> "${OUT}/logs/perf_syscalls_stat.txt" || true
else
perf stat -a -e context-switches \
"${OUT}/bin/hackbench" 30 30000 \
> "${OUT}/logs/perf_syscalls_out.txt" 2> "${OUT}/logs/perf_syscalls_stat.txt" || true
fi
}

collect_system_info() {
log "Collecting system info ..."
{
echo "===== uname -a ====="; uname -a
echo; echo "===== CPU ====="; lscpu || cat /proc/cpuinfo
echo; echo "===== Memory ====="; free -h || true
echo; echo "===== Kernel cmdline ====="; cat /proc/cmdline || true
echo; echo "===== Sched tunables ====="
for f in /proc/sys/kernel/sched_*; do echo "$f=$(cat $f)"; done 2>/dev/null || true
echo; echo "===== Instance type (IMDS) ====="
curl -s --max-time 2 -H "Metadata-Flavor: Amazon" \
http://169.254.169.254/latest/meta-data/instance-type || true
echo
} > "${OUT}/SYSTEM.txt"
}

summarize() {
log "Summarizing ..."
{
echo "# Context Switch Repro Summary"
echo "Timestamp: ${TS}"
echo
echo "## Platform"
echo "Package Manager: $(cat ${OUT}/PM.txt)"
echo
echo "## Microbench"
if [ -f "${OUT}/logs/lat_ctx_64.log" ]; then
echo "- lat_ctx samples:"
grep -H "size=" -n ${OUT}/logs/lat_ctx_*.log || true
else
echo "- lat_ctx: not available (build failed or skipped)"
fi
echo
echo "- hackbench-like (elapsed/cs_switched if available):"
grep -H "elapsed_sec" -n ${OUT}/logs/hackbench_*.log || true
echo
echo "- perf bench sched pipe (pure cs latency):"
grep -E "avg|Percentiles" -n "${OUT}/logs/perf_pipe.txt" || true
echo
echo "## Web workload"
echo "- ab result:"
grep -E "Requests per second|Time per request|50%|90%|95%|99%" -n ${OUT}/logs/ab_stdout.txt || true
echo
echo "- perf (system-wide during ab):"
grep -E "cycles|instructions|context-switches|cpu-migrations|task-clock|page-faults" -n ${OUT}/logs/perf_ab.txt || true
echo
echo "- perf cycles/context-switches (during ab):"
awk '
/[0-9]+\s+cycles/ {c=$1}
/[0-9]+\s+context-switches/ {cs=$1}
END { if (c>0 && cs>0) printf(" cycles_per_switch ~= %.1f\n", c/cs); else print " (insufficient data)"; }
' "${OUT}/logs/perf_ab.txt" || true
echo
echo "## Syscall mix (hackbench)"
grep -E "context-switches|syscalls:sys_enter_" -n ${OUT}/logs/perf_syscalls_stat.txt || true
echo
echo "## Interpretation Tips"
} > "${OUT}/SUMMARY.txt"

log "Done. Results in: ${OUT}"
echo "Open ${OUT}/SUMMARY.txt"
}

main() {
detect_os
install_deps "$(cat ${OUT}/PM.txt)"
collect_system_info
build_lat_ctx || true
build_hackbench
prep_nginx
run_lat_ctx
run_perf_pipe
run_hackbench
run_web_ab
run_perf_syscall_mix
summarize
}

main "$@"

結果

m6a 為 AMD EPYC 9R14,m6i 為 Intel Xeon 8375C

Hackbench

在 hackbench 測試中,m6i 明顯更快:

  • g10 測試:m6a 約 0.18 秒,m6i 只需 0.07 秒。
  • g50 測試:m6a 約 0.91 秒,m6i 只需 0.36 秒。

整體來看,m6i 約快 2.5 倍。這代表它在多群組 Processes 間通訊與 context switch 場景中反應更快。

Nginx + ab 壓力測試

以 Nginx 伺服器配合 ApacheBench 進行壓測(20 萬次請求、500 併發)。

  • m6i 平均每秒可處理 22,201 requests/sec
    而 m6a 只有 11,862 requests/sec,效能幾乎高出 87%
  • 每次請求平均耗時:m6a 為 42.1 毫秒,m6i 下降至 22.5 毫秒。
  • 延遲分位數部分:
    • p50:41ms → 22ms
    • p90:47ms → 25ms
    • p95:48ms → 25ms
    • p99:50ms → 26ms

整體分佈顯示,m6i 不僅平均速度更快,尾端延遲也更穩定。

perf 系統層觀察

perf stat 的結果來看:

  • m6i 的 context-switches 約為 296k 次(16.2K/sec),比 m6a 的 285k 次(8.4K/sec)多,代表它能處理更多切換而不造成卡頓。
  • m6i 的 task-clock 為 18.3 秒,而 m6a 為 33.9 秒,執行效率顯著更高。
  • page fault 與 cpu migration 數據相近,但 m6i 的遷移次數稍高,顯示核心調度更積極。

Syscall Mix

hackbench 測試中,m6a 約有 376 次 context-switch,m6i 為 304 次。
雖切換次數略少,但整體耗時更短,顯示 m6i 的切換開銷更低。

結論

整體而言,m6i.large(Intel Xeon 8375C)在 context switch 與高併發效能上顯著優於 m6a.large(AMD EPYC 9R14)

m6i 更適合用於需要頻繁切換的工作負載,例如 Web API、短命週期容器、Gateway、或高併發微服務。
m6a 則雖在整體效能上略遜,但對長期運算型任務仍具價格優勢。

若系統對互動延遲敏感、或經常出現「偶爾卡一下」的體感問題,m6i 會是更穩定的選擇。


留言
avatar-img
留言分享你的想法!
avatar-img
Wei 的工程師聊什麼
4會員
12內容數
2025/09/29
AWS EC2 m7i.large對比m7a.large,測試顯示 m7a 在科學計算、影音編碼、壓縮、AI、編譯等多數負載快 20%~70%,部分翻倍。雖 m7a.large 價格高 15%,效能卻遠超差額。建議 Web 與容器選 m7a,大型資料庫或 HPC 再考慮 m7i。
Thumbnail
2025/09/29
AWS EC2 m7i.large對比m7a.large,測試顯示 m7a 在科學計算、影音編碼、壓縮、AI、編譯等多數負載快 20%~70%,部分翻倍。雖 m7a.large 價格高 15%,效能卻遠超差額。建議 Web 與容器選 m7a,大型資料庫或 HPC 再考慮 m7i。
Thumbnail
2025/09/28
本文透過 Phoronix Test Suite 進行詳細的效能評測,比較 AWS EC2 m8i.large 和 m7i.large 的差異,分析其在不同工作負載下的表現。並深入探討隨需(On-Demand)、和Savings Plans(SP)的成本效益,為您提供最適合的升級建議。
Thumbnail
2025/09/28
本文透過 Phoronix Test Suite 進行詳細的效能評測,比較 AWS EC2 m8i.large 和 m7i.large 的差異,分析其在不同工作負載下的表現。並深入探討隨需(On-Demand)、和Savings Plans(SP)的成本效益,為您提供最適合的升級建議。
Thumbnail
2025/09/28
本文針對 AWS m8i.large 和 m8i-flex.large 執行詳細效能評測,比較兩者在科學計算、影音編碼、編譯渲染等多方面的表現。結論顯示,m8i 在需要持續高效能的多執行緒任務上表現更佳,而 m8i-flex 則適合一般及間歇性工作負載,並提供更好的性價比。
Thumbnail
2025/09/28
本文針對 AWS m8i.large 和 m8i-flex.large 執行詳細效能評測,比較兩者在科學計算、影音編碼、編譯渲染等多方面的表現。結論顯示,m8i 在需要持續高效能的多執行緒任務上表現更佳,而 m8i-flex 則適合一般及間歇性工作負載,並提供更好的性價比。
Thumbnail
看更多
你可能也想看
Thumbnail
AMD財報與上調財測,以AI、PC與伺服器晶片帶動收入表現落後補漲、財測維持增速,微軟整體部門包括雲端與AI業務保持正增長,與Google表現差距不大,整體AI題材已失去先行者優勢,競爭者後來居上,三星受益於AI對記憶體需求激勵財報表現。昨日市場維持相對強勢、產業分歧,關注財報後是否出現產業輪動。
Thumbnail
AMD財報與上調財測,以AI、PC與伺服器晶片帶動收入表現落後補漲、財測維持增速,微軟整體部門包括雲端與AI業務保持正增長,與Google表現差距不大,整體AI題材已失去先行者優勢,競爭者後來居上,三星受益於AI對記憶體需求激勵財報表現。昨日市場維持相對強勢、產業分歧,關注財報後是否出現產業輪動。
Thumbnail
在半導體科技頂端的台積電和ASML都發布了財報,面臨回檔壓力的AI半導體還有戲嗎?
Thumbnail
在半導體科技頂端的台積電和ASML都發布了財報,面臨回檔壓力的AI半導體還有戲嗎?
Thumbnail
MRVL FY1Q25 營收報 11.61 億美元,略低於 Sell Side 預期的 11.62 億美元 ,但略高於我 model 預期的 11.5 億美元,主要是受惠於資料中心營收維持強勁的雙位數 QoQ 成長。
Thumbnail
MRVL FY1Q25 營收報 11.61 億美元,略低於 Sell Side 預期的 11.62 億美元 ,但略高於我 model 預期的 11.5 億美元,主要是受惠於資料中心營收維持強勁的雙位數 QoQ 成長。
Thumbnail
AI PC 硬體 + AI OS + AI PC 摘要
Thumbnail
AI PC 硬體 + AI OS + AI PC 摘要
Thumbnail
AMD 從一個小公司逆風翻盤,經歷了多次起起伏伏,最終在蘇姿豐的帶領下重新崛起,成為與英特爾分庭抗禮的晶片巨頭。AMD 通過推出高性能 Zen 架構的 CPU 產品,以及在數據中心和 AI 領域的戰略佈局,成功擴大了市場份額,並實現了股價的百倍增長。
Thumbnail
AMD 從一個小公司逆風翻盤,經歷了多次起起伏伏,最終在蘇姿豐的帶領下重新崛起,成為與英特爾分庭抗禮的晶片巨頭。AMD 通過推出高性能 Zen 架構的 CPU 產品,以及在數據中心和 AI 領域的戰略佈局,成功擴大了市場份額,並實現了股價的百倍增長。
Thumbnail
儘管 5G 技術還在發展和部署階段,但科技公司和無線通訊產業已著手開始發展更先進的 6G 數據技術,取代 5G,來滿足未來更快速、更可靠、更智能的無線通訊需求。下一代 6G 技術可能比 5G 快 100 倍,在速度方面顯著提升。同時 6G 允許設備、消費者和周圍環境之間進行更深層次的整合與即時通訊。
Thumbnail
儘管 5G 技術還在發展和部署階段,但科技公司和無線通訊產業已著手開始發展更先進的 6G 數據技術,取代 5G,來滿足未來更快速、更可靠、更智能的無線通訊需求。下一代 6G 技術可能比 5G 快 100 倍,在速度方面顯著提升。同時 6G 允許設備、消費者和周圍環境之間進行更深層次的整合與即時通訊。
Thumbnail
#華景電 120周看法這邊拉長更新 這邊已經有兩次的慣性155~160 第一階段下來一點185~195兩個階段都要有停利規劃,有過程才不會痛苦 AMC微汙染防治設備,競爭對手只有一間美國供應商,市占比60:40 客戶就是半導體 記憶體 封測廠中間過程的空頭是跟著科技股一起波動 目前未
Thumbnail
#華景電 120周看法這邊拉長更新 這邊已經有兩次的慣性155~160 第一階段下來一點185~195兩個階段都要有停利規劃,有過程才不會痛苦 AMC微汙染防治設備,競爭對手只有一間美國供應商,市占比60:40 客戶就是半導體 記憶體 封測廠中間過程的空頭是跟著科技股一起波動 目前未
追蹤感興趣的內容從 Google News 追蹤更多 vocus 的最新精選內容追蹤 Google News