Adversarial Robustness
Bền vững trước tấn công — AI không dễ bị lừa
Bạn thêm nhiễu CỰC NHỎ (mắt người không thấy) vào ảnh con mèo. AI nhận dạng sẽ thế nào?
Dưới đây là lưới pixel 16×16 mô phỏng ảnh con mèo. Kéo thanh trượt để tăng epsilon (biên độ nhiễu). Ba ô: ảnh gốc, nhiễu đối kháng (hồng = dấu dương, xanh = dấu âm), và ảnh cuối cùng mà mô hình nhìn thấy.
Hình minh họa
Công thức:
Nhiễu đối kháng được cộng vào ảnh gốc. Khi ε ≈ 0.01, mắt người hoàn toàn không phân biệt được x và x′, nhưng mô hình không có adversarial training thường đã bắt đầu lật nhãn từ ε ≈ 0.035.
Giữ adversarial training TẮT, tăng ε dần. Ghi nhận ε nhỏ nhất làm mô hình lật nhãn.
BẬT adversarial training, lặp lại. So sánh ngưỡng lật nhãn — mô hình đã bền vững hơn bao nhiêu lần?
Fast Gradient Sign Method (Goodfellow et al., 2014) là attack đơn giản nhất nhưng vẫn rất hiệu quả:
- Gradient được tính theo input (không phải theo weights) — cùng engine autograd đã có trong PyTorch.
sign()chỉ giữ dấu — mỗi pixel thay đổi đúng ±ε, tối ưu hoá tăng loss dưới ràng buộc L∞.- Chi phí: 1 forward + 1 backward — rẻ hơn 1 epoch training vài triệu lần.
Xe tự lái dùng camera nhận dạng biển báo giao thông. Kẻ xấu dán sticker nhỏ lên biển 'DỪNG LẠI' khiến AI đọc thành 'Tốc độ 120 km/h'. Hậu quả nguy hiểm nhất là gì?
Giải thích
Adversarial Robustness là khả năng AI duy trì dự đoán chính xác khi đầu vào bị thao túng có chủ đích. Khái niệm liên quan chặt chẽ tới red-teaming (tìm lỗ hổng chủ động) và guardrails (hàng rào bảo vệ đầu ra), và là một mảnh ghép trung tâm của alignment.
1. FGSM — Fast Gradient Sign Method: 1 bước ±ε theo sign của gradient. Nhanh nhất, làm baseline.
2. PGD — Projected Gradient Descent: K bước nhỏ + chiếu về epsilon-ball sau mỗi bước. Mạnh hơn FGSM nhiều, được coi là "strongest first-order attack".
3. CW — Carlini & Wagner: optimization-based, min hoá nhiễu sao cho dự đoán đổi. Tạo nhiễu nhỏ hơn nữa nhưng tốn nhiều bước optimizer (khó phát hiện nhất).
Phương trình PGD nhìn như FGSM lặp lại:
là phép chiếu về epsilon-ball quanh x; là step size (thường ε/10); sau K bước, nhiễu không vượt quá ε.
1. Adversarial Training (AT): Tạo adversarial examples mỗi batch, train trên cả dữ liệu gốc + adversarial. Hiệu quả nhất nhưng tốn 3-10x thời gian training. Madry et al. (2018) là tham chiếu chuẩn.
2. Certified Defense: Chứng minh toán học rằng dự đoán không đổi trong phạm vi epsilon. Ví dụ: Randomized Smoothing (Cohen et al., 2019), Interval Bound Propagation.
3. Input Preprocessing: Lọc / biến đổi input trước khi đến mô hình: JPEG compression, spatial smoothing, feature squeezing. Rẻ nhưng dễ bị bypass bằng adaptive attack.
Min-max formulation của adversarial training
Adversarial training giải bài toán hai cấp:
Vòng trong (max) là attack — tìm nhiễu tồi tệ nhất. Vòng ngoài (min) là training — cập nhật trọng số để robust với nhiễu đó. Xấp xỉ vòng trong bằng PGD K-bước → được gọi là PGD adversarial training.
"""Adversarial attacks & training — PyTorch + CleverHans.
CleverHans (https://github.com/cleverhans-lab/cleverhans) là thư viện
chuẩn cho adversarial ML. Ở đây ta kết hợp CleverHans cho attack +
PyTorch training loop cho defense.
"""
import torch
import torch.nn as nn
import torch.nn.functional as F
from torch.utils.data import DataLoader
from cleverhans.torch.attacks.fast_gradient_method import fast_gradient_method
from cleverhans.torch.attacks.projected_gradient_descent import projected_gradient_descent
# ---------------------------------------------------------------------
# 1. Attacks
# ---------------------------------------------------------------------
def fgsm_attack(model: nn.Module, x: torch.Tensor, y: torch.Tensor, eps: float = 0.03):
"""1 bước FGSM — rẻ, hữu ích làm baseline."""
model.eval()
# CleverHans API: fast_gradient_method(model, x, eps, norm, ...)
x_adv = fast_gradient_method(
model_fn=model,
x=x,
eps=eps,
norm=float("inf"),
y=y,
targeted=False,
)
return x_adv.detach()
def pgd_attack(model: nn.Module, x: torch.Tensor, y: torch.Tensor,
eps: float = 0.03, alpha: float = 0.007, steps: int = 10):
"""PGD-K — attack chuẩn để đo robustness."""
model.eval()
x_adv = projected_gradient_descent(
model_fn=model,
x=x,
eps=eps,
eps_iter=alpha,
nb_iter=steps,
norm=float("inf"),
y=y,
targeted=False,
rand_init=True, # khởi tạo ngẫu nhiên trong ball → mạnh hơn
sanitize=True,
)
return x_adv.detach()
# ---------------------------------------------------------------------
# 2. Adversarial training loop (Madry-style)
# ---------------------------------------------------------------------
def train_robust(
model: nn.Module,
loader: DataLoader,
optimizer: torch.optim.Optimizer,
device: torch.device,
eps: float = 0.03,
steps: int = 7,
clean_weight: float = 0.5,
):
model.train()
for x, y in loader:
x, y = x.to(device), y.to(device)
# (a) Sinh adversarial batch — mỗi step train đều có attack mới
x_adv = pgd_attack(model, x, y, eps=eps, alpha=eps/4, steps=steps)
model.train() # pgd_attack gọi model.eval()
# (b) Loss kết hợp clean + adversarial
logits_clean = model(x)
logits_adv = model(x_adv)
loss = (
clean_weight * F.cross_entropy(logits_clean, y)
+ (1 - clean_weight) * F.cross_entropy(logits_adv, y)
)
optimizer.zero_grad()
loss.backward()
optimizer.step()
# ---------------------------------------------------------------------
# 3. Đánh giá robustness
# ---------------------------------------------------------------------
@torch.no_grad()
def clean_accuracy(model, loader, device):
model.eval()
correct, total = 0, 0
for x, y in loader:
x, y = x.to(device), y.to(device)
correct += (model(x).argmax(1) == y).sum().item()
total += y.size(0)
return correct / total
def pgd_accuracy(model, loader, device, eps=0.03, steps=20):
"""Robust accuracy — dùng PGD mạnh (nhiều bước) để đánh giá."""
model.eval()
correct, total = 0, 0
for x, y in loader:
x, y = x.to(device), y.to(device)
x_adv = pgd_attack(model, x, y, eps=eps, alpha=eps/10, steps=steps)
with torch.no_grad():
correct += (model(x_adv).argmax(1) == y).sum().item()
total += y.size(0)
return correct / total
# Thông thường: clean_acc giảm 1-3%, robust_acc tăng từ ~0% → 45-60%.
Camera giao thông AI (Hà Nội, TP.HCM) có thể bị lừa bằng hoạ tiết dán trên biển số xe.
AI nhận dạng khuôn mặt tại sân bay có thể bị đánh bại bằng kính hoa văn đặc biệt (Sharif et al., 2016).
Chatbot tiếng Việt có thể bị ép sai qua homoglyph (thay chữ Latin bằng chữ Cyrillic trông giống) — adversarial attack cho NLP.
Cần kết hợp adversarial training, ensemble, và kiểm định bên ngoài cho mọi AI safety-critical.
Demo tấn công với CleverHans — chạy được ngay
Đoạn code dưới đây là demo tối thiểu: tải một mô hình CNN đã train, tấn công bằng FGSM + PGD từ CleverHans, và đo accuracy trước/sau.
"""Demo: Tấn công một mô hình CIFAR-10 đã train bằng CleverHans.
Chạy: python demo_cleverhans_attack.py
Kết quả mong đợi: clean_acc ≈ 0.92, fgsm_acc ≈ 0.15, pgd_acc ≈ 0.02
(nếu mô hình KHÔNG được adversarial training)
"""
import torch
import torchvision as tv
from cleverhans.torch.attacks.fast_gradient_method import fast_gradient_method
from cleverhans.torch.attacks.projected_gradient_descent import projected_gradient_descent
device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
# 1. Tải CIFAR-10 test set
mean = torch.tensor([0.4914, 0.4822, 0.4465])
std = torch.tensor([0.2470, 0.2435, 0.2616])
transform = tv.transforms.Compose([
tv.transforms.ToTensor(),
tv.transforms.Normalize(mean, std),
])
testset = tv.datasets.CIFAR10(root="./data", train=False, download=True, transform=transform)
loader = torch.utils.data.DataLoader(testset, batch_size=128, shuffle=False)
# 2. Tải mô hình — ví dụ ResNet-18 từ torchvision hub
model = torch.hub.load("chenyaofo/pytorch-cifar-models",
"cifar10_resnet20", pretrained=True).to(device)
model.eval()
# 3. Hàm đánh giá
def eval_attack(attack_fn, name: str):
correct, total = 0, 0
for x, y in loader:
x, y = x.to(device), y.to(device)
x_adv = attack_fn(x, y) if attack_fn is not None else x
with torch.no_grad():
pred = model(x_adv).argmax(1)
correct += (pred == y).sum().item()
total += y.size(0)
acc = correct / total
print(f"{name:>10s} accuracy = {acc:.4f}")
return acc
# 4. Clean
eval_attack(None, "clean")
# 5. FGSM — 1 bước
eval_attack(
lambda x, y: fast_gradient_method(model, x, 8/255, float("inf"), y=y),
"FGSM",
)
# 6. PGD-20 — chuẩn công bố
eval_attack(
lambda x, y: projected_gradient_descent(
model, x,
eps=8/255, eps_iter=2/255, nb_iter=20,
norm=float("inf"), y=y, rand_init=True,
),
"PGD-20",
)
# 7. AutoAttack (nếu cài autoattack pip package)
# from autoattack import AutoAttack
# aa = AutoAttack(model, norm="Linf", eps=8/255, version="standard")
# x_adv = aa.run_standard_evaluation(x, y)
White-box, Black-box, Gray-box — ba mô hình mối đe doạ
Khi đánh giá robustness, ta phân loại theo mức quyền truy cập của kẻ tấn công:
- White-box: kẻ tấn công biết toàn bộ kiến trúc, trọng số, và gradient. FGSM / PGD / CW đều là white-box. Kịch bản tệ nhất — dùng để đánh giá upper bound.
- Black-box: chỉ truy vấn qua API, không biết nội tại mô hình. Dùng Square Attack, NES, transfer attack. Thực tế hơn nhưng vẫn hiệu quả đáng sợ.
- Gray-box: biết kiến trúc nhưng không biết trọng số, hoặc có query limit. Tấn công qua transferability: train surrogate model, attack surrogate, transfer lên target.
Transferability là hiện tượng đáng lo ngại: adversarial examples tạo cho mô hình A thường lừa được cả mô hình B có kiến trúc khác. Đây là lý do ensemble đơn thuần không đủ — cần ensemble đa dạng (khác kiến trúc, khác data augmentation, khác training objective).
Adversarial training cải thiện robust accuracy (từ ~0% lên 40-60% dưới PGD) nhưng thường giảm clean accuracy 1-3%. Trade-off đáng chấp nhận cho ứng dụng safety-critical (xe tự lái, y tế, an ninh), có thể không cần cho ứng dụng rủi ro thấp (gợi ý sản phẩm, nhận dạng ảnh giải trí).
Tsipras et al. (2019) chứng minh trade-off này là nội tại — không chỉ do thuật toán kém, mà vì feature robust và feature chính xác có thể xung đột nhau.
Không có biện pháp đơn lẻ nào đủ. Kiến trúc bền vững đi theo nguyên tắc Defense in Depth:
- Input level: preprocessing (JPEG, total variation denoising), anomaly detector.
- Model level: adversarial training, ensemble nhiều mô hình có kiến trúc khác nhau.
- Output level: confidence threshold, uncertainty estimation (dropout-at-inference).
- System level: fallback sang cảm biến khác (LiDAR, GPS), human in the loop khi confidence thấp.
Một startup Việt Nam triển khai AI nhận dạng chữ ký cho ngân hàng. Họ đo clean accuracy 99%. Bạn là security reviewer — đâu là yêu cầu BẮT BUỘC?
- Không chỉ báo cáo accuracy dưới FGSM default — dễ cho kết quả ảo.
- Dùng PGD-50 + AutoAttack (ensemble APGD-CE, APGD-DLR, FAB, Square) làm chuẩn.
- Báo cáo cả L∞, L2, và L0 (nếu tấn công sparse quan trọng).
- Thử adaptive attack biết rõ defense của bạn — đây mới là bài kiểm tra thật.
- Với LLM / NLP: đo robustness với paraphrase, homoglyph, unicode confusable, prompt injection.
- Công khai weights + attack script — không có robustness nào tồn tại dưới "security through obscurity".
Chuẩn CIFAR-10 / ImageNet. Nhiễu ≈ 3% mỗi pixel — mắt người không thấy.
50 bước gradient + 10 khởi tạo ngẫu nhiên. Số liệu tối thiểu để công bố.
Mô hình không phòng thủ thường ≈ 0%. SOTA robust ≈ 70% nhưng tốn nhiều tài nguyên.
- Adversarial attack = nhiễu CỰC NHỎ nhưng thiết kế theo gradient, đủ để lừa AI hoàn toàn.
- FGSM: 1 bước, nhanh. PGD: nhiều bước + projection, mạnh hơn. CW: optimization-based, khó phát hiện nhất.
- Physical attacks (sticker biển báo, kính, áo hoạ tiết) nguy hiểm hơn digital — hoạt động trong thế giới thực.
- Adversarial training (min-max) hiệu quả nhất nhưng tốn 3-10x thời gian và giảm clean accuracy 1-3%.
- Defense in depth: preprocessing + adversarial training + ensemble + fallback — không biện pháp đơn lẻ nào đủ.
- BẮT BUỘC đánh giá bằng PGD-50 + AutoAttack + adaptive attack trước khi claim robustness cho production.
- Goodfellow, Shlens, Szegedy (2014) — Explaining and Harnessing Adversarial Examples (FGSM gốc).
- Madry et al. (2018) — Towards Deep Learning Models Resistant to Adversarial Attacks (PGD adversarial training).
- Croce & Hein (2020) — Reliable evaluation of adversarial robustness with AutoAttack.
- RobustBench (robustbench.github.io) — leaderboard chuẩn cho robust accuracy trên CIFAR / ImageNet.
Kiểm tra hiểu biết
FGSM (Fast Gradient Sign Method) tạo nhiễu đối kháng bằng cách nào?