Tổng quan mục tiêu, giới thiệu và nhiệm vụ của lab Mục tiêu học tập của lab này là để ta có được trải nghiệm trực tiếp về một biến thểthú vị của tấn công tràn bộ đệm; cuộc tấn công này
Trang 1BAN CƠ YẾU CHÍNH PHỦ HỌC VIỆN KỸ THUẬT MẬT MÃ KHOA: AN TOÀN THÔNG TIN
Giảng viên hướng dẫn: PGS.TS Lương Thế Dũng
Sinh viên thực hiện: Trần Quốc Hoàng
Trang 2BAN CƠ YẾU CHÍNH PHỦ HỌC VIỆN KỸ THUẬT MẬT MÃ KHOA: AN TOÀN THÔNG TIN
THỰC TẬP CƠ SỞ CHUYÊN NGÀNH
AN TOÀN PHẦN MỀM
NGHIÊN CỨU THỰC HÀNH CÁCH TẤN CÔNG RETURN-TO-LIBC (RETURN-TO-LIBC ATTACK LAB)
Nhận xét của giáo viên hướng dẫn:
Điểm báo cáo:
Xác nhận của giáo viên hướng dẫn:
2
Trang 3LỜI CẢM ƠN
Chúng em xin chân thành cảm ơn PGS.TS Lương Thế Dũng–giảng viên trựctiếp hướng dẫn, chỉ bảo, tạo mọi điều kiện thuận lợi giúp đỡ chúng em trong quá trìnhthực hiện đề tài
Để có được thành quả như ngày hôm nay, ngoài sự nỗ lực không ngừng nghỉ củacác thành viên trong nhóm thì một phần không nhỏ đóng góp nên thành công này là nhờ
sự quan tâm, chỉ bảo, giúp đỡ của các thầy cô, các anh chị khóa trên và bạn bè xungquanh
Tuy đã có rất nhiều cố gắng và sự nỗ lực của các thành viên để hoàn thiện đề tài,
nhưng chắc chắn đề tài “NGHIÊN CỨU THỰC HÀNH CÁCH TẤN CÔNG RETURN-TO-LIBC (RETURN-TO-LIBC ATTACK LAB)” của chúng em còn nhiều
thiếu sót Chúng em rất mong nhận được sự góp ý từ các thầy giáo để nhóm em có thểhoàn thiện tốt hơn các đề tài nghiên cứu sau
Chúng em xin chân thành cảm ơn!
Trang 4LỜI MỞ ĐẦU
Ngày nay, với xu hướng chuyển đổi số mạnh mẽ của các doanh nghiệp, công ty, tổchức dẫn đến việc tạo ra những phần mềm quản lý, điều hành và làm việc cũng hết sứcthiết yếu Bên cạnh đó, ảnh hưởng của đại dịch COVID-19 cũng đã thúc đẩy nhanh việcchuyển đổi số Để đảm bảo an toàn cho phần mềm khi tạo ra và vận hành tránh bị kẻ xấutấn công gây thiệt hại nghiêm trọng Đó cũng là lý do để chúng em chọn chuyên đềSoftware Security và đặc biệt là nghiên cứu cách tấn công Return-to-Libc
4
Trang 5MỤC LỤC
LỜI CẢM ƠN 3
LỜI MỞ ĐẦU 4
MỤC LỤC 5
CHƯƠNG I: TỔNG QUAN VỀ RETURN-TO-LIBC ATTACK LAB 6
1.1 Tổng quan mục tiêu, giới thiệu và nhiệm vụ của lab 6
1.2 Tổng quan về lý thuyết 6
CHƯƠNG II: CÀI ĐẶT MÔI TRƯỜNG THỰC HIỆN 7
1.1 Chuẩn bị cho bài Lab 7
1.2 Cài đặt môi trường ảo Ubuntu v16.04 của SEED Labs 10
CHƯƠNG III: TIẾN HÀNH THỰC HIỆN VÀ NGHIÊN CỨU CHUYÊN SÂU BÀI LAB THEO THỨ TỰ TỪNG TASK 15
3.1 Cài đặt thiết lập ban đầu để thực hiện bài lab 15
3.1.1 Address Space Randomization (Ngẫu nhiên hóa không gian địa chỉ) 15
3.1.2 Configuring /bin/sh 15
3.1.3 The StackGuard Protection Scheme 15
3.1.4 Non-Executable Stack 16
3.2 Giới thiệu về chương trình chứa lỗ hổng 16
3.3 Task 1: Tìm địa chỉ của hàm libc 18
3.4 Task 2: Đưa chuỗi shell vào bộ nhớ (Putting the shell string in the memory) 20
3.5 Task 3: Khai thác lỗ hổng tràn bộ đệm (Exploiting the Buffer-Overflow Vulnerability) 22
3.6 Task 4: Bật tính năng ngẫu nhiên hóa địa chỉ (Turning on Address Randomization) 27
3.7 Task 5: Vượt qua các biện pháp an toàn của Shell (Defeat Shell’s countermeasure) 31
CHƯƠNG IV: KẾT LUẬN 33
TÀI LIỆU THAM KHẢO 34
Trang 6CHƯƠNG I: TỔNG QUAN VỀ RETURN-TO-LIBC ATTACK
LAB
1.1 Tổng quan mục tiêu, giới thiệu và nhiệm vụ của lab
Mục tiêu học tập của lab này là để ta có được trải nghiệm trực tiếp về một biến thểthú vị của tấn công tràn bộ đệm; cuộc tấn công này có thể bỏ qua một sơ đồ bảo vệ hiệncó hiện được triển khai trong các hệ điều hành Linux chính Một cách phổ biến để khaithác lỗ hổng tràn bộ đệm là làm tràn bộ đệm bằng một mã shellcode độc hại, và sau đókhiến chương trình dễ bị tấn công nhảy đến shellcode được lưu trữ trong ngăn xếp Đểngăn chặn các kiểu tấn công này, một số hệ điều hành cho phép quản trị viên hệ thống tạocác ngăn xếp không thể thực thi được; do đó, việc nhảy đến shellcode sẽ khiến chươngtrình bị lỗi
Thật không may, chương trình bảo vệ ở trên không phải là chống đánh lừa; tồn tạimột biến thể của tấn công tràn bộ đệm được gọi là tấn công return-to-libc, không cầnngăn xếp thực thi; nó thậm chí không sử dụng shell code Thay vào đó, nó làm chochương trình dễ bị tấn công đến một số mã hiện có, chẳng hạn như hàm system () trongthư viện libc, đã được tải vào bộ nhớ
Trong lab này, ta được cung cấp một chương trình có lỗ hổng tràn bộ đệm; nhiệm
vụ của ta là phát triển một cuộc tấn công return-to-libc để khai thác lỗ hổng và cuối cùng
là giành được đặc quyền root Ngoài các cuộc tấn công, ta sẽ được thực hiện một sốphương án bảo vệ đã được triển khai trong Ubuntu để chống lại các cuộc tấn công tràn bộđệm Ta cần đánh giá xem các chương trình có hoạt động hay không và giải thích tại sao
1.2 Tổng quan về lý thuyết
Return to libc là một phương pháp khai thác lỗi tràn bộ đệm trên hệ thống có ngănxếp không thực thi được, nó rất giống với tràn bộ đệm tiêu chuẩn, trong đó địa chỉ trả vềđược thay đổi để trỏ đến một vị trí mới mà chúng ta có thể kiểm soát Tuy nhiên, vìkhông có mã thực thi nào được phép trên ngăn xếp, ta không thể chỉ gắn thẻ trongshellcode
Vì lí do đó ta sử dụng thủ thuật return to libc và sử dụng một hàm được cung cấpbởi thư viện Ta vẫn ghi đè địa chỉ trả về bằng một trong các hàm trong libc, chuyển chonó các đối số chính xác và thực thi nó cho ta Vì các hàm này không nằm trên ngăn xếp,
ta có thể bỏ qua bảo vệ ngăn xếp và thực thi code
6
Trang 8CHƯƠNG II: CÀI ĐẶT MÔI TRƯỜNG THỰC HIỆN
1.1 Chuẩn bị cho bài Lab
Truy cập đường link: https://www.virtualbox.org/wiki/Downloads Để tải và càiđặt
Sau khi tải về thì chạy chương trình để cài đặt vào máy Chọn Next
8
Trang 9Tiếp tục , chọn Next và cuối cùng là chọn Install
Trang 10Chọn Finish để kết thúc quá trình cài đặt Bên dưới là giao diện sau khi cài đặt
hoàn tất
10
Trang 111.2 Cài đặt môi trường ảo Ubuntu v16.04 của SEED Labs
Truy cập vào trang web : https://seedsecuritylabs.org/labsetup.html Chọn version16.04 như hình bên dưới và tải về theo đường dẫn đính kèm
Ở đây em chọn đường dẫn của “Google Drive” Sau khi tải xong chúng ta giải nénfile rar
Quay lại với Oracle VM VirtualBox , Chọn New ,lựa chọn các cài đặt như hình bên dưới và chọn Next
Trang 12Chọn Next cho đến khi đến phần Hark Disk Chọn vào “Use an exitsting virtual hard disk file” và chọn vào icon được khoanh vùng đen.
Chọn Add
12
Trang 13Chọn đến đường dẫn lúc nãy vừa giải nén file Ubuntu v16.04 và chọn vào file bên dưới nhấn Open
Sau khi chọn đường dẫn xong sẽ hiện giống như ảnh màn hình sau và click vào
“SEEDUbuntu-16.04-32bit.vmdk” và chọn Choose
Sau đó ấn Create
Chọn Start để tiến hành cài đặt bên trong
Trang 14Quá trình cài đặt hoàn tắt
14
Trang 15Lưu ý : Khi đóng máy Ubuntu ảo Các bạn nên chọn “Save the machine state”
Để có thể lưu lại những gì mình đang làm
Trang 16CHƯƠNG III: TIẾN HÀNH THỰC HIỆN VÀ NGHIÊN CỨU CHUYÊN SÂU BÀI LAB THEO THỨ TỰ TỪNG TASK
3.1 Cài đặt thiết lập ban đầu để thực hiện bài lab
Ubuntu và các bản phân phối Linux khác đã triển khai một số cơ chế bảo mật đểlàm cho cuộc tấn công tràn bộ đệm trở nên khó khăn Để đơn giản là các cuộc tấn côngcủa ta, trước tiên cần phải vô hiệu hóa các cơ chế bảo mật ấy
3.1.1 Address Space Randomization (Ngẫu nhiên hóa không gian địa chỉ)
Ubuntu và một số hệ thống dựa trên Linux khác sử dụng Address SpaceRandomization để ngẫu nhiên hóa địa chỉ bắt đầu của heap và stack Điều này làm choviệc đoán các địa chỉ chính xác trở nên khó khăn; đoán địa chỉ là một trong những bướcquan trọng của các cuộc tấn công tràn bộ đệm (Buffer Overflow) Trong lab này, ta tiếnhành tắt các tính năng này bằng các lệnh sau
sudo sysctl -w kernel.randomize_va_space=0
3.1.2 Configuring /bin/sh
Thay đổi default shell từ “dash” thành “zsh” để tránh các biện pháp đối phó đượcthực hiện trong “bash” cho các chương trình SET-UID
3.1.3 The StackGuard Protection Scheme
Trình biên dịch GCC thực hiện một cơ chế bảo mật được gọi là Stack Guard đểngăn chặn lỗi tràn bộ đệm Khi có sự bảo vệ này, các cuộc tấn công tràn bộ đệm sẽ khônghoạt động Ta sẽ tắt tính năng bảo vệ này trong quá trình biên dịch bằng cách sử dụng tùychọn -fno-stack-protectionor
16
Trang 173.1.4 Non-Executable Stack
Ở cơ chế này chúng ta sẽ cung cấp tham số “-z execstack” Khi cung cấp tham sốnày, ngăn xếp trở nên thực thi được, sau đó cho phép mã của chúng ta được thực thi khi ởtrong ngăn xếp Theo mặc định, ngăn xếp là không thể thực thi và hệ điều hành biết liệungăn xếp có thực thi được hay không bằng một tập bit nhị phân trong hệ thống Bit nàycó thể được trình biên dịch thao tác và trình biên dịch gcc đặt ngăn xếp là không thể thựcthi (Non-Executable Stack) theo mặc định
3.2 Giới thiệu về chương trình chứa lỗ hổng
Trong bài lab đã cung cấp cho ta một chương trình có chứa lỗ hổng bufferoverflow (lỗi tràn bộ đệm) tên là retlib.c Xuyên suốt lab này sẽ dùng đến chương trình
Trang 18Tiếp theo, ta tiến hành thực hiện các thao tác tắt các cơ chế bảo mật và biện phápđối phó của linux và kiểm tra xem ta có thể tấn công bằng chương trình lỗ hổng trên và
sử dụng thư viện libc để tấn công hay không?
Ta cần đảm bảo rằng ta sử dụng shell / bin / zsh dễ bị tấn công Biện pháp đối phóngẫu nhiên địa chỉ bị tắt Chương trình retlib.c đã cho được tạo là chương trình dễ bị tấncông mà ta sử dụng ở đây và nó có sự cố tràn bộ đệm (buffer overflow) Ta vô hiệu hóatính năng StackGuard protection có sẵn và biên dịch chương trình retlib Sau khi biêndịch, chuyển chương trình được tạo thành chương trình UID thuộc quyền sở hữu của userroot
18
Trang 193.3 Task 1: Tìm địa chỉ của hàm libc
Mục đích của task này là di chuyển đến mã hiện có đã được tải vào bộ nhớ và sửdụng hàm system () và exit () khỏi thư viện libc cho cuộc tấn công
Để tìm địa chỉ của bất kỳ hàm libc nào, ta có thể sử dụng các lệnh gdb sau (a.out làmột chương trình tùy ý):
Ta gỡ lỗi chương trình có lỗ hổng retlib và tạo một điểm ngắt trong hàm main Khichương trình được chạy và đạt đến điểm ngắt, chương trình sẽ được chạy từng dòng một
Từ các lệnh gdb, chúng ta có thể tìm ra rằng địa chỉ cho hàm system () là 0xb7637da0 vàđịa chỉ cho hàm exit () là 0xb762b9d0 Các địa chỉ thực tế trong hệ thống của từng máycó thể khác với số này Đây là những địa chỉ được dùng cho cuộc tấn công
Trang 20Kết luận: Do ta cần sử dụng địa chỉ của hàm system() và exit() trong thư viện libc
cho cuộc tấn công, ta có thể tìm thấy chúng bằng cách sử dụng trình GNU gdb debugger
20
Trang 213.4 Task 2: Đưa chuỗi shell vào bộ nhớ (Putting the shell string in the
memory)
Mục đích của tác vụ này là đưa chuỗi lệnh ‘/bin/sh’ vào bộ nhớ và biết địa chỉ củanó Để đạt được điều này, ta tạo một biến shell mới có tên MYSHELL chứa chuỗi lệnh /bin/sh
Biến MYSHELL có chuỗi shell trong tiến trình con Bây giờ chúng ta tạo chươngtrình envShellString.c đã cho để lấy địa chỉ của biến trong bộ nhớ Chương trình sau đóđược biên dịch và chạy với retlib để lấy địa chỉ của biến
Tiếp theo, chúng ta sử dụng chương trình getenv.c để tìm địa chỉ của biếnMYSHELL Ta tiến hành biên dịch và chạy chương trình này Nó sẽ cho ta output chínhxác địa chỉ và phục vụ cho các tasks tấn công sau
Trang 22Kết luận: Địa chỉ của biến shell được truyền dưới dạng biến môi trường cho tiếntrình con có thể được tìm thấy và được sử dụng cho cuộc tấn công để đưa một số chuỗitùy ý vào bộ nhớ của tiến trình con.
22
Trang 233.5 Task 3: Khai thác lỗ hổng tràn bộ đệm (Exploiting the Buffer-Overflow Vulnerability)
Mục đích của task này là tạo ra nội dụng của badfile bằng cách cung cấp dữ liệunhị phân Qua cách sử dụng objdump trong chương trình retlib, chúng ta có thể tìm ra cácgiá trị của X, Y, Z Các giá trị này được đặt trong chương trình exploit2.c
Dưới đây, ta có thể thấy dòng thứ ba cho biết không gian được cấp cho hàm bof ()
là 0x18 Địa chỉ offset của hàm system () là 24 Địa chỉ exit() của hàm này cao hơn 4 so với hàm system()
Trang 24Chương trình exploit2.c chứa đầy đủ địa chỉ của các hàm system(), exit(), và địachỉ /bin/sh Địa chỉ của các hàm trên được xác định ở các task phía trên.
24
Trang 25Tiếp theo, ta tiếp tục biên dịch và chạy chương trình exploit.c này Ta có thể nhìnthấy root shell có thể được sinh ra.
Khi làm điều này, ta có đặc quyền root Bây giờ, địa chỉ trả về của system (), buf[32] được thay thế bằng 0, tham số của setuid (), không có chỗ cho exit () Đây là lý dotại sao nó trả về lỗi phân đoạn khi chúng ta thoát khỏi trình bao gốc
Kết luận: Bằng cách biết địa chỉ của hàm System (), địa chỉ của hàm exit () và địa
chỉ của biến shell được gửi đến quy trình con dưới dạng biến môi trường và cả các giá trịchỉ mục mảng (X, Y, Z) của chuỗi đệm, ta có thể khai thác chương trình dễ bị tổn thươngcó vấn đề tràn bộ đệm
Trang 27Kết luận: Như chúng ta thấy trong hình trên, địa chỉ hàm exit() đã được đưa ra Ta
có thể nhận thấy rằng địa chỉ của hàm exit() là không cần thiết để thực hiện của tấn côngvào người dùng Root shell được tạo ra mà không cung cấp địa chỉ của exit()
Kết luận: Ta không thể tấn công người dùng Cuộc tấn công không thành công vì
bất cứ khi nào ta đổi tên tệp, địa chỉ của tệp sẽ bị thay đổi và chúng ta phải lặp lại toàn bộtác vụ đã thực hiện trước đó để tìm lại địa chỉ Ở đây ‘retlib’ có một địa chỉ khác và
‘newretlib’ bây giờ có một địa chỉ khác được sử dụng trong task sắp tới
Trang 283.6 Task 4: Bật tính năng ngẫu nhiên hóa địa chỉ (Turning on Address Randomization)
Ta đã biết rằng tất cả các cuộc tấn công được thực hiện đối với người dùng là bằngcách tắt tính năng ngẫu nhiên hóa địa chỉ, biện pháp đối phó và tắt bảo vệ StackGuardtrong khi biên dịch chương trình chứa lỗ hổng Bây giờ ta tiến hành bật lại tính năng ngẫunhiên hóa địa chỉ và kiểm tra xem biện pháp bảo vệ này có hiệu quả chống lại cuộc tấncông Return-to-libc hay không
Sau khi ta bật lại biện pháp đối phó ngẫu nhiên địa chỉ, chương trình ‘exploit2’ và
‘newretlib’ vẫn có thể chạy được
Kết luận: Lần này nó cho ra kết quả Segmentation fault Điều này là do xảy ra tràn
bộ đệm nhưng địa chỉ của system (), exit () và / bin / sh luôn thay đổi Vì vậy, ta khôngthể giữ một địa chỉ chính xác Đây là lý do tại sao cuộc tấn công không thành công Thêmnữa, các giá trị X,Y và Z không thay đổi chỉ có địa chỉ của chúng bị thay đổi
Khi ta bật ngẫu nhiên địa chỉ, ta chạy chương trình biến chuỗi shell mà ta đã tạotrong task 2 để tìm ra địa chỉ của shell Khi ta cho chạy đi chạy lại vài lần, mỗi lần chạy
sẽ cho một kết quả ngẫu nhiên
Ta tiếp ta tiến hành gỡ lỗi ‘newretlib’ bằng trình gỡ lỗi ‘gdb’ để kiểm tra xemngẫu nhiên hóa địa chỉ có còn hiệu quả hay không
28
Trang 29Khi kiểm tra xem ngẫu nhiên hóa địa chỉ có bị vô hiệu hóa hay không và nó chobiết rằng nó đã bị vô hiệu hóa và ngẫu nhiên hóa địa chỉ sẽ tự động tắt sau khi trình gỡ lỗi
‘gdb’ được sử dụng
Trang 30Ta tạo một điểm breakpoint trong hàm chính và chạy chương trình từng dòng sauđó Chúng tôi kiểm tra địa chỉ hàm system () và địa chỉ hàm exit () như dưới đây.
Tính năng ngẫu nhiên hóa địa chỉ được bật lại trong ‘gdb’ hoặc ta có thể nói rằngtính năng ngẫu nhiên hóa vô hiệu hóa đã bị tắt Sau đó, ta tạo một điểm breakpoint tronghàm main () và chạy lại từng dòng chương trình để kiểm tra những gì đã thay đổi trongcác địa chỉ
30
Trang 31Ta thấy địa chỉ hàm system () và địa chỉ hàm exit () đã thay đổi
Kết luận: Ta nhận thấy rằng, ngay cả khi ta đã cố gắng trước đó để bật ngẫu nhiên
địa chỉ thành trong hệ điều hành, ‘gdb’ theo mặc định sẽ vô hiệu hóa ngẫu nhiên địa chỉ
Ta phải tắt đặc biệt tính năng vô hiệu hóa ngẫu nhiên trong ‘gdb’ để duy trì biện pháp đối
phó ngẫu nhiên hóa địa chỉ