Phát Hiện và Xóa Bỏ Malware Đào Tiền Mã Hóa trên Máy Chủ Linux

Security tutorial - IT technology blog
Security tutorial - IT technology blog

Dashboard giám sát của bạn hiển thị CPU ở mức 98% — nhưng ứng dụng đang nhàn rỗi và traffic hoàn toàn bình thường. Sự kết hợp đó — CPU bị ghim cứng, không có gì giải thích — có nghĩa là có thứ gì đó trên máy chủ đang ngốn tài nguyên không phải của bạn để tiêu.

Một khách hàng của tôi đã học được bài học này theo cách đau đớn. Một miner XMRig đã lặng lẽ đào Monero trên VPS của họ suốt ba tuần trước khi hóa đơn cloud bất thường cao kích hoạt cảnh báo. Đến khi tôi được gọi vào, chúng tôi đã trải qua cả cuối tuần truy vết nguồn lây nhiễm, dọn sạch các cơ chế duy trì và xây dựng lại hệ thống bảo mật từ đầu. Máy chủ của chính tôi đã bị tấn công brute-force SSH lúc 2 giờ sáng nhiều năm trước — từ đó, bảo mật là thứ đầu tiên tôi cấu hình trên bất kỳ máy mới nào.

Vấn Đề Thực Tế: Chiếm Dụng CPU Âm Thầm

Cryptominer chiếm một vị trí kỳ lạ trong thế giới malware. Chúng không phá hủy dữ liệu, không đòi tiền chuộc, và cố gắng hết sức để ẩn mình. Mô hình kinh doanh là đánh cắp tài nguyên tính toán thuần túy: chu kỳ CPU của bạn, hóa đơn điện của bạn, ví Monero của họ. Mỗi giờ chúng không bị phát hiện là lợi nhuận cho kẻ tấn công — và một khoản phí không giải thích được cho bạn.

Các triệu chứng xuất hiện dần dần:

  • Đột biến CPU không giải thích được (thường 70–100% trên tất cả các core)
  • Thời gian phản hồi của máy chủ giảm mặc dù traffic bình thường
  • Hóa đơn điện toán đám mây cao hơn dự kiến
  • Kết nối mạng ra ngoài bất thường đến các IP không rõ
  • Các cron job hoặc dịch vụ systemd mới mà bạn không tạo

Đến khi hầu hết admin nhận ra, miner đã chạy được vài ngày hoặc vài tuần.

Phân Tích Nguyên Nhân Gốc Rễ: Nó Đã Xâm Nhập Như Thế Nào?

Trước khi đụng vào bất kỳ tiến trình nào, hãy tìm ra điểm xâm nhập. Dọn sạch miner mà không đóng cửa đó lại, và nó sẽ quay trở lại trong vài giờ. Cryptominer khai thác cùng một điểm xâm nhập nhiều lần — biết các mẫu đó, và dấu vết điều tra sẽ trở nên dễ theo dõi hơn nhiều.

SSH Brute Force / Credential Stuffing

SSH với xác thực mật khẩu đang bị lộ là vector #1. Một VPS mới triển khai có thể nhận hơn 1.000 lần thử đăng nhập trong giờ đầu tiên. Các bot tự động quét toàn bộ dải /8 suốt ngày đêm. Mật khẩu yếu hoặc tái sử dụng trên tài khoản root và sudo bị crack nhanh — đôi khi dưới năm phút trên hệ thống mục tiêu. Khi vào được, kẻ tấn công tải và chạy payload đào tiền ngay lập tức.

Khai Thác Ứng Dụng Web

WordPress, ứng dụng PHP, hoặc framework chưa vá với các lỗ hổng RCE đã biết cung cấp cho kẻ tấn công khả năng thực thi lệnh trực tiếp. Log4Shell (CVE-2021-44228), được công bố vào tháng 12 năm 2021, trở thành phương tiện phát tán cryptominer trong vòng 48 giờ sau khi công bố. Lỗ hổng PHP deserialization và SSTI theo cùng một mẫu. Miner được cài đặt qua web shell hoặc command injection trực tiếp — thường trong vài giây sau khi khai thác.

Docker và Kubernetes API Bị Lộ

Cổng 2375 không có xác thực TLS về cơ bản là quyền truy cập root không được xác thực vào host của bạn. Kẻ tấn công kết nối trực tiếp đến Docker API, khởi động container có đặc quyền với quyền truy cập filesystem của host, và thoát ra để cài đặt payload. Dashboard Kubernetes cấu hình sai cho kết quả tương tự theo một con đường khác.

Gói Phần Mềm Bị Xâm Phạm và CI/CD Pipeline

Các gói npm hoặc PyPI độc hại — và build pipeline bị xâm phạm — tiêm code đào tiền âm thầm vào quá trình triển khai của bạn. Đây là loại khó phát hiện nhất. Cơ chế phân phối trông hoàn toàn hợp lệ, nên các biện pháp bảo vệ vành đai tiêu chuẩn không gắn cờ nó.

Phát Hiện: Lập Bản Đồ Toàn Bộ Nhiễm Trước Khi Đụng Vào Bất Cứ Thứ Gì

Tắt tiến trình trước khi bạn hiểu toàn bộ phạm vi hầu như luôn phản tác dụng. Miner tự trồng lại từ các cơ chế duy trì mà bạn chưa tìm thấy. Đây là cách tiếp cận có hệ thống thực sự hiệu quả.

Bước 1: Xác Định Các Tiến Trình Đáng Ngờ

# Kiểm tra các tiến trình ngốn CPU nhiều nhất
top -b -n 1 | head -20

# Xem chi tiết hơn với đường dẫn lệnh đầy đủ
ps aux --sort=-%cpu | head -20

# Kiểm tra các tiến trình chạy từ binary đã bị xóa (kỹ thuật ẩn mình kinh điển)
ls -la /proc/*/exe 2>/dev/null | grep deleted

Miner thường giả mạo các tiến trình hệ thống: kworker, kthreadd, sshd, hoặc các chuỗi trông ngẫu nhiên. Chú ý đặc biệt đến kiểm tra binary đã xóa — nếu /proc/<PID>/exe trỏ đến đường dẫn (deleted), đó gần như luôn là độc hại. Kẻ tấn công thực thi binary, sau đó xóa ngay khỏi đĩa, chỉ để lại tiến trình đang chạy.

Bước 2: Theo Dõi Các Kết Nối Mạng Ra Ngoài

# Liệt kê tất cả kết nối với tiến trình chịu trách nhiệm
ss -tulpn

# XMRig thường kết nối đến các mining pool trên cổng 3333, 4444, 5555, 14444
ss -tnp | grep -E ':3333|:4444|:5555|:14444'

# Phân giải IP của các kết nối đáng ngờ
for ip in $(ss -tn | grep ESTAB | awk '{print $5}' | cut -d: -f1 | sort -u); do
    host "$ip" 2>/dev/null | head -1
done

Bước 3: Kiểm Tra Mọi Cơ Chế Duy Trì

Tính bền vững là nơi miner thể hiện kỹ thuật của chúng. Chúng tự cài vào nhiều vị trí để tắt tiến trình chỉ kích hoạt khởi động lại từ nơi khác.

# Kiểm tra tất cả crontab, kể cả theo từng user
crontab -l 2>/dev/null
cat /etc/crontab
ls -la /etc/cron.d/ /etc/cron.daily/ /etc/cron.hourly/
for user in $(cut -d: -f1 /etc/passwd); do
    crontab -u "$user" -l 2>/dev/null && echo "--- $user ---"
done

# Kiểm tra các dịch vụ systemd với tên không quen thuộc
systemctl list-units --type=service --state=running
ls -la /etc/systemd/system/

# Kiểm tra các file khởi động shell có chứa downloader được chèn vào
find /root /home -name '.bashrc' -o -name '.profile' -o -name '.bash_profile' \
    | xargs grep -l 'curl\|wget\|chmod' 2>/dev/null

Bước 4: Tìm Các File Miner

# Tìm kiếm ở các vị trí có thể ghi mà miner ưa thích
ls -la /tmp/ /dev/shm/ /var/tmp/
find /tmp /dev/shm /var/tmp -type f -newer /etc/passwd 2>/dev/null

# Tìm kiếm file cấu hình XMRig
find / -name 'config.json' -newer /etc/passwd 2>/dev/null \
    | xargs grep -l 'pool\|wallet' 2>/dev/null

# Kiểm tra PHP web shell trong web root
find /var/www -name '*.php' -newer /etc/passwd 2>/dev/null \
    | xargs grep -l 'base64_decode\|eval\|system(' 2>/dev/null

So Sánh Các Giải Pháp: Ba Cách Xử Lý Máy Chủ Bị Xâm Phạm

Khi đã lập bản đồ nhiễm, bạn đối mặt với một ngã rẽ thực sự. Mỗi lựa chọn mang hồ sơ rủi ro khác nhau — chọn sai và bạn hoặc lãng phí một ngày hoặc để lại cho kẻ tấn công một con đường quay lại.

Phương Án A: Dọn Dẹp Trực Tiếp (Nhanh, Rủi Ro Cao Hơn)

Tắt tiến trình, xóa file, và xóa sạch cơ chế duy trì tại chỗ. Hiệu quả khi nhiễm đơn giản và bạn có thể xác định từng phần của nó. Rủi ro thực sự: bỏ sót một cơ chế duy trì và nó sẽ trở lại vào sáng hôm sau, như thể không có gì xảy ra.

Phương Án B: Xây Dựng Lại Máy Chủ Hoàn Toàn (Toàn Diện, Chậm Hơn)

Cấp phát máy chủ mới, khôi phục từ bản sao lưu đã biết là tốt, hoặc triển khai lại stack ứng dụng từ đầu. Đây là con đường duy nhất đảm bảo trạng thái sạch. Nếu máy chủ chứa dữ liệu nhạy cảm hoặc vector tấn công chưa hoàn toàn rõ ràng, đây là lựa chọn đúng — dứt khoát.

Phương Án C: Khôi Phục Snapshot

Trên các nhà cung cấp cloud (AWS, GCP, DigitalOcean), khôi phục về snapshot trước khi nhiễm. Nhanh và sạch — nhưng bạn cần bật snapshot, và cần biết chính xác khi nào nhiễm bắt đầu. Dấu thời gian đó hiếm khi rõ ràng.

Đề xuất của tôi: đối với máy chủ production nơi vector tấn công chưa rõ, hãy xây dựng lại (Phương Án B). Đối với môi trường dev hoặc staging nơi bạn có thể truy vết chính xác cách miner xâm nhập, dọn dẹp trực tiếp có thể chấp nhận được — nhưng xác minh kỹ trước khi tiếp tục.

Cách Tiếp Cận Tốt Nhất: Dọn Dẹp Có Hệ Thống và Tăng Cường Bảo Mật

Giai Đoạn 1: Khoanh Vùng — Cắt Đứt Kết Nối Miner Ngay Lập Tức

# Chặn kết nối ra ngoài đến các cổng mining pool phổ biến
iptables -A OUTPUT -p tcp --dport 3333 -j DROP
iptables -A OUTPUT -p tcp --dport 4444 -j DROP
iptables -A OUTPUT -p tcp --dport 5555 -j DROP
iptables -A OUTPUT -p tcp --dport 14444 -j DROP

# Chặn các domain mining pool đã biết ở cấp DNS
cat >> /etc/hosts << 'EOF'
0.0.0.0 pool.minexmr.com
0.0.0.0 xmr.pool.minergate.com
0.0.0.0 xmrpool.eu
0.0.0.0 monerohash.com
EOF

Giai Đoạn 2: Tiêu Diệt — Xóa Bỏ Mọi Thứ

# Tắt tiến trình miner
kill -9 <PID>

# Xóa cơ chế duy trì dựa trên systemd
systemctl stop <malicious-service>
systemctl disable <malicious-service>
rm /etc/systemd/system/<malicious-service>.service
systemctl daemon-reload

# Dọn sạch các vị trí thả file phổ biến của miner
rm -rf /tmp/xmrig /dev/shm/.x /var/tmp/.update*

# Xóa các mục crontab độc hại (chỉnh sửa và xóa các dòng đáng ngờ)
crontab -e

Giai Đoạn 3: Xác Minh Đã Sạch

# Xác nhận CPU đã trở về bình thường
top -b -n 3 | grep '%Cpu'

# Xác minh không còn kết nối ra ngoài đáng ngờ
watch -n 2 'ss -tnp | grep -v "127.0.0\|::1"'

# Chạy kiểm tra rootkit
apt install -y chkrootkit rkhunter
chkrootkit
rkhunter --check --sk

Giai Đoạn 4: Tăng Cường Bảo Mật Chống Tái Nhiễm

# Tắt xác thực mật khẩu SSH
# Regex này xử lý cả dòng PasswordAuthentication có và không có dấu # ở đầu
sed -i 's/^#*PasswordAuthentication.*/PasswordAuthentication no/' /etc/ssh/sshd_config
systemctl restart sshd

# Thay thế tất cả SSH authorized keys — thu hồi bất kỳ key nào bạn không nhận ra
cat ~/.ssh/authorized_keys  # Kiểm tra file này cẩn thận

# Cài đặt và cấu hình fail2ban cho SSH
apt install -y fail2ban
cat > /etc/fail2ban/jail.local << 'EOF'
[sshd]
enabled = true
maxretry = 3
bantime = 3600
findtime = 600
EOF
systemctl enable --now fail2ban

# Bật cập nhật bảo mật tự động
apt install -y unattended-upgrades
dpkg-reconfigure --priority=low unattended-upgrades

# Hạn chế thực thi từ các thư mục có thể ghi bởi tất cả
# remount là tạm thời — thêm vào /etc/fstab để giữ sau khi reboot
mount -o remount,noexec /tmp
mount -o remount,noexec /dev/shm
# Thêm vào /etc/fstab để cố định:
# tmpfs /tmp     tmpfs defaults,noexec,nosuid,nodev 0 0
# tmpfs /dev/shm tmpfs defaults,noexec,nosuid,nodev 0 0

Giai Đoạn 5: Thiết Lập Cảnh Báo Bất Thường CPU

# Cảnh báo khi CPU vượt 80% — vmstat cho đầu ra đáng tin cậy trên mọi distro
cat > /usr/local/bin/cpu-monitor.sh << 'EOF'
#!/bin/bash
THRESHOLD=80
# cột 15 của vmstat là idle%; trừ từ 100 để lấy tổng % đang bận
CPU=$(vmstat 1 2 | tail -1 | awk '{print 100 - $15}' | cut -d'.' -f1)
if [ "$CPU" -gt "$THRESHOLD" ]; then
    echo "CẢNH BÁO CPU CAO: ${CPU}% trên $(hostname) lúc $(date)" \
        | mail -s "Cảnh báo CPU" [email protected]
fi
EOF
chmod +x /usr/local/bin/cpu-monitor.sh
echo "*/5 * * * * root /usr/local/bin/cpu-monitor.sh" > /etc/cron.d/cpu-monitor

# Thiết lập auditd để bắt thực thi từ /tmp
apt install -y auditd
auditctl -w /tmp -p x -k tmp-execution
auditctl -w /etc/cron.d/ -p wa -k crontab-changes

# Xem xét audit log
ausearch -k tmp-execution
ausearch -k crontab-changes

Một mẫu lặp lại trong mọi trường hợp tái nhiễm tôi đã xử lý: admin dọn sạch miner nhưng không bao giờ xác định điểm xâm nhập ban đầu. Vá lỗ hổng trước tiên. Nếu bạn không thể xác định kẻ tấn công đã vào như thế nào, con đường duy nhất phía trước là xây dựng lại hoàn toàn — coi máy cũ là đã bị xâm phạm hoàn toàn và đừng khôi phục nó.

Tốc độ phát hiện là yếu tố phân biệt một sự cố nhỏ với một sự cố nghiêm trọng. Miner bị bắt trong giờ đầu gần như không tốn gì. Ba tuần đào tiền không bị phát hiện có nghĩa là mất tiền thật, khả năng lộ dữ liệu, và đúng vậy — một cuối tuần rất dài.

Share: