Smart Contract Audits: What Auditors Check—and What an Audit Does Not Guarantee
Kiểm toán hợp đồng thông minh là hoạt động đánh giá độc lập mã và kiến trúc trong một phạm vi xác định. Mục đích là nhận diện lỗ hổng, lỗi triển khai và điểm không khớp giữa hành vi dự kiến với hành vi thực tế.
Kiểm toán có thể giảm mức độ không chắc chắn nhưng không làm cho hợp đồng trở nên không có rủi ro. Hướng dẫn bảo mật chính thức của Ethereum mô tả kiểm toán là một lớp đánh giá bổ sung, không phải giải pháp vạn năng có thể phát hiện mọi lỗi.
Bài viết này chỉ nhằm mục đích giáo dục. Việc kiểm toán không bảo đảm an toàn, khả năng thu hồi tài sản hay lợi nhuận.
Phạm vi là ưu tiên đầu tiên
Báo cáo hữu ích nêu chính xác những gì đã được đánh giá:
- kho mã nguồn và mã băm commit;
- các tệp và hợp đồng;
- phiên bản trình biên dịch và cài đặt bản dựng;
- các phần phụ thuộc;
- kiến trúc và các vai trò đặc quyền;
- nhánh hoặc bản phát hành;
- các nội dung loại trừ, hạn chế và giả định;
- ngày xem xét.
Điều này quan trọng vì một cuộc kiểm toán hợp lệ có thể chỉ bao quát phiên bản cũ, một lần triển khai khác hoặc chỉ một phần của hệ thống lớn hơn.
Kiểm toán viên thường xem xét những gì
1. Hành vi dự kiến và các điều kiện bất biến
Kiểm toán viên đối chiếu mã với đặc tả:
- ai có thể gọi từng hàm;
- cách tính số tiền và phí;
- khi nào trạng thái thay đổi;
- những thuộc tính nào phải luôn đúng;
- cách xử lý các trường hợp biên và lỗi.
Nếu đặc tả bỏ sót một yêu cầu quan trọng, mã đúng về kỹ thuật vẫn có thể triển khai một thiết kế không an toàn hoặc không mong muốn.
2. Kiểm soát quyền truy cập
Người đánh giá kiểm tra chủ sở hữu, quản trị viên, người vận hành và các vai trò có đặc quyền khác, bao gồm quyền:
- cấp hoặc thu hồi quyền;
- tạm dừng hệ thống;
- thay đổi phí và giới hạn;
- tạo token mới;
- rút tài sản;
- nâng cấp phần triển khai.
Họ cũng xem xét liệu một khóa có thể thực hiện thay đổi quan trọng hay không và liệu các biện pháp kiểm soát như đa chữ ký hoặc khóa thời gian có nằm trong thiết kế hay không.
3. Lệnh gọi bên ngoài và tấn công tái nhập
Trong quá trình thực thi, một hợp đồng có thể chuyển quyền kiểm soát cho hợp đồng khác. Điều này có thể tạo điều kiện cho tấn công tái nhập, khi hợp đồng bên ngoài gọi ngược trở lại trước lúc quá trình chuyển trạng thái ban đầu hoàn tất. Hướng dẫn chính thức của Solidity khuyến nghị sắp xếp cẩn thận các bước kiểm tra, thay đổi trạng thái và tương tác bên ngoài khi phù hợp.
4. Phép tính và đơn vị
Kiểm toán viên tìm kiếm:
- làm tròn và mất độ chính xác;
- số chữ số thập phân của token không khớp;
- thứ tự hoạt động không chính xác;
- các giá trị biên;
- phép chia cho không;
- unsafe
uncheckedarithmetic; - sự chênh lệch giữa đơn vị nội bộ và đơn vị hiển thị.
5. Từ chối dịch vụ và gas
Vòng lặp không giới hạn, mảng tăng dần, lệnh gọi bên ngoài thất bại hoặc hoạt động tốn kém có thể khiến một hàm không còn khả thi để thực thi. Người đánh giá kiểm tra liệu thiết kế có tiếp tục sử dụng được khi dữ liệu tăng lên và khi gặp đầu vào bất thường hay không.
6. Proxy và nâng cấp
Đối với hệ thống có thể nâng cấp, đánh giá cần bao quát:
- hợp đồng proxy và hợp đồng triển khai;
- quyền nâng cấp hoặc quyền quản trị;
- khởi tạo;
- khả năng tương thích của bố cục lưu trữ;
- các đường dẫn nâng cấp trái phép;
- tác động của việc thay đổi logic sau kiểm toán.
Proxy có thể giữ nguyên địa chỉ mà người dùng nhìn thấy trong khi chuyển quyền xử lý sang logic mới. Vì vậy, tuyên bố rằng “hợp đồng không thể thay đổi” phải được kiểm chứng theo kiến trúc thực tế.
7. Tích hợp
Hợp đồng có thể phụ thuộc vào token, oracle giá, cầu nối, DEX, chữ ký hoặc các hợp đồng khác. Kiểm toán viên xem xét các giả định về những phụ thuộc đó, dữ liệu lỗi thời, hành vi token bất thường và các dạng lỗi bên ngoài.
8. Sự kiện và giám sát
Người đánh giá có thể kiểm tra sự kiện có phản ánh chính xác các hành động quan trọng như thay đổi vai trò, nâng cấp, tạm dừng và chuyển tiền hay không. Sự kiện hỗ trợ giám sát nhưng không thay thế việc kiểm tra trạng thái.
Các phương pháp được sử dụng trong kiểm toán
Một cuộc đánh giá thường kết hợp:
- phân tích mã và kiến trúc thủ công;
- kiểm thử đơn vị và kiểm thử tích hợp;
- phân tích tĩnh và động;
- kiểm thử fuzz với đầu vào được tạo tự động;
- kiểm thử dựa trên thuộc tính;
- kiểm tra các nhóm lỗ hổng đã biết;
- xem xét quá trình tạo bản dựng và triển khai;
- đôi khi xác minh hình thức đối với các thuộc tính được chọn.
Không phương pháp đơn lẻ nào bao quát mọi thứ. Xác minh hình thức có thể chứng minh mã đáp ứng đặc tả hình thức; không thể chứng minh một thuộc tính mà đặc tả không nêu.
Người dùng nên đọc báo cáo kiểm toán như thế nào
1. Đối chiếu với phiên bản đã được kiểm toán
Tìm mã băm commit và xác định:
- phần triển khai hiện tại có được tạo từ mã đó hay không;
- có nâng cấp nào diễn ra sau ngày lập báo cáo hay không;
- chuỗi và các địa chỉ đã triển khai có khớp nhau hay không;
- các phần phụ thuộc quan trọng có nằm trong phạm vi xem xét hay không.
Nếu không thể xác lập điều này, báo cáo chỉ cung cấp bằng chứng hạn chế về bản triển khai đang hoạt động.
2. Đọc các phát hiện, không chỉ phần tóm tắt
Đối với từng phát hiện, hãy xem xét:
- mức độ nghiêm trọng và kịch bản;
- mã bị ảnh hưởng;
- khuyến nghị;
- phản hồi của nhà phát triển;
- trạng thái hiện tại;
- đơn vị kiểm toán có kiểm thử lại bản sửa lỗi hay không.
Đã cố định hoặc Đã giải quyết is meaningful only when tied to a specific corrected version.
3. Đọc các giới hạn
Báo cáo có thể loại trừ:
- hệ thống giao diện người dùng và hệ thống phía máy chủ;
- quản lý khóa;
- thiết kế kinh tế;
- hợp đồng của bên thứ ba;
- hạ tầng triển khai;
- cấu hình môi trường vận hành thực tế;
- các vấn đề pháp lý và vận hành.
Người dùng tương tác với toàn bộ hệ thống, không chỉ với các tệp Solidity của hệ thống.
4. Xem xét rủi ro quản trị
Hãy hỏi:
- ai kiểm soát việc nâng cấp;
- các hoạt động có thể bị tạm dừng hay không;
- phí hoặc địa chỉ được liên kết có thể thay đổi hay không;
- có khóa thời gian hay không;
- có sử dụng đa chữ ký hay không;
- cách người dùng biết về các thay đổi.
Đây vẫn là những vấn đề về quản trị và niềm tin, ngay cả khi chưa phát hiện lỗ hổng trong mã.
5. Theo dõi bảo mật sau kiểm toán
Các biện pháp duy trì hữu ích bao gồm:
- kiểm thử mọi bản phát hành;
- xem xét các bản nâng cấp quan trọng;
- chương trình săn lỗi nhận thưởng;
- giám sát vai trò và phần triển khai;
- quy trình ứng phó sự cố;
- giới hạn lượng tài sản chịu rủi ro.
Những gì một cuộc kiểm toán không đảm bảo
Kiểm toán không bảo đảm:
- không tồn tại bất kỳ lỗi nào;
- độ an toàn của mã đã thay đổi sau khi xem xét;
- độ an toàn của trang web, ví, DNS hoặc máy chủ;
- bảo mật của các khóa đặc quyền;
- tính chính xác của token, oracle và cầu nối bên ngoài;
- khả năng chống lại mọi cuộc tấn công kinh tế;
- tính chính trực của một nhóm;
- tuân thủ pháp luật;
- thanh khoản token;
- hoàn trả tài sản;
- lợi nhuận cố định hoặc bất kỳ loại lợi nhuận nào khác.
Những câu hỏi người dùng thận trọng nên đặt ra
Is an auditor’s logo enough?
No. Find the report from the auditor’s own source and check its scope, commit, date, and findings.
If every finding was fixed, is the contract safe?
It means the listed findings were addressed in a stated version. Unknown issues and out-of-scope risks remain.
Are several audits automatically better?
The count alone says little. Coverage, quality, independence, recency, and version matching matter more.
Does an audit still apply after a proxy upgrade?
Only if the new implementation and configuration are covered by the reviewed version.
Danh sách kiểm tra báo cáo
- Báo cáo có thể được lấy từ đơn vị kiểm toán.
- Kho mã và mã băm commit được nêu rõ.
- Các hợp đồng và phần phụ thuộc quan trọng nằm trong phạm vi đánh giá.
- Phiên bản đã đánh giá khớp với bản triển khai đang hoạt động.
- Proxy, phần triển khai và quản trị viên nằm trong phạm vi.
- Việc xác định trạng thái và kiểm tra lại đã được ghi trong tài liệu.
- Đã đọc các giả định và nội dung loại trừ.
- Các rủi ro ngoài mã đã được đánh giá riêng.
Nguồn và tài liệu đọc thêm
- Ethereum.org — Bảo mật hợp đồng thông minh
- Ethereum.org — Kiểm thử hợp đồng thông minh
- Ethereum.org — Xác minh hình thức hợp đồng thông minh
- Solidity Documentation — Các lưu ý về bảo mật
- OpenZeppelin Docs — Mẫu nâng cấp proxy