- MacThrottle là ứng dụng dựa trên SwiftUI hiển thị trực quan trên thanh menu khi Mac giới hạn hiệu năng do quá nhiệt - mã nguồn mở
- So sánh API
ProcessInfo.thermalState của macOS với lệnh powermetrics, đồng thời tìm cách phát hiện chính xác trạng thái nhiệt thực tế của hệ thống
- Cuối cùng triển khai phương thức tận dụng thông báo mà
thermald đăng lên hệ thống notifyd của Darwin để đọc trạng thái nhiệt mà không cần quyền root
- Ứng dụng bao gồm đồ thị nhiệt độ và tốc độ quạt, biểu tượng màu theo từng trạng thái, tính năng thông báo macOS, đồng thời hỗ trợ tự chạy khi đăng nhập
- Là công cụ giúp nắm bắt trạng thái quản lý nhiệt của Apple Silicon Mac theo thời gian thực, mang lại phương tiện chẩn đoán hữu ích cho lập trình viên và người dùng nâng cao
Nhận diện vấn đề thermal throttling trên Mac
- Khi dùng màn hình ngoài 4K 120Hz với M2 MacBook Air, đã xảy ra suy giảm hiệu năng và độ trễ phản hồi
- Không có quạt nên không thể nhận biết qua tiếng ồn, nhưng mức tiêu thụ điện lại giảm trong khi CPU đang ở 100% tải
- Dùng iStat Menus và MX Power Gadget để xác nhận xung nhịp CPU và mức điện năng bị sụt giảm, từ đó chẩn đoán thermal throttling
- Hiện tượng tương tự cũng xuất hiện trên M4 Max MacBook Pro, được nhắc đến như vấn đề do giới hạn thiết kế nhiệt của bản 14 inch
- Dù hiệu quả điện năng của Apple Silicon vẫn rất cao, tác giả vẫn muốn tìm cách phát hiện trực tiếp trạng thái nhiệt
Kiểm tra trạng thái nhiệt trên macOS bằng lập trình
- macOS có nhiều cách để lộ trạng thái nhiệt, nhưng thiếu tính nhất quán
- Cách Apple khuyến nghị là dùng
ProcessInfo.thermalState trong Foundation
- Ví dụ đầu ra:
nominal, fair, serious, critical
- Lệnh
powermetrics -s thermal yêu cầu quyền root cũng cung cấp thông tin tương tự, nhưng
mức phân chia trạng thái của hai cách là khác nhau
- Ví dụ:
fair bao trùm cả hai trạng thái moderate và heavy trong powermetrics
- Thời điểm throttling thực sự xuất hiện được hiển thị là
heavy trong powermetrics, nhưng ProcessInfo không thể phân biệt được
Tận dụng thermald và hệ thống thông báo Darwin
- Dữ liệu của
powermetrics đến từ daemon thermald, và
thermald đăng trạng thái áp lực nhiệt hiện tại dưới dạng sự kiện hệ thống notifyd
- Có thể kiểm tra trạng thái bằng lệnh
notifyutil -g com.apple.system.thermalpressurelevel
- Các mức áp lực nhiệt được định nghĩa trong header
OSThermalNotification.h:
nominal, moderate, heavy, trapping, sleeping
- Bằng cách gọi
notify_register_check và notify_get_state trong mã Swift, đã triển khai được chức năng đọc trạng thái nhiệt theo thời gian thực mà không cần quyền root
Phát triển ứng dụng MacThrottle
- Tạo ứng dụng chỉ dành cho thanh menu bằng SwiftUI và MenuBarExtra
- Hiển thị trạng thái qua màu biểu tượng nhiệt kế (xanh lá → đỏ)
- Đặt
LSUIElement trong Info.plist thành true để vô hiệu hóa biểu tượng Dock
Cách tiếp cận ban đầu: helper powermetrics chạy bằng root
- Ban đầu, để dùng
powermetrics cần quyền root, tác giả đã
dựng tiến trình helper bằng LaunchDaemon và script bash
/usr/local/bin/mac-throttle-thermal-monitor ghi trạng thái vào tệp /tmp mỗi 10 giây
- Ứng dụng đọc định kỳ tệp đó để hiển thị
Cải tiến: dùng thông báo IPC của thermald
- Chuyển sang cách đăng ký trực tiếp sự kiện
notifyd
- Không cần quyền root, mã nguồn cũng đơn giản hơn
Hiển thị nhiệt độ và tốc độ quạt
- Hiển thị đồ thị nhiệt độ CPU/GPU và tốc độ quạt
- Ban đầu, khi dùng API riêng tư của IOKit, nhiệt độ hiển thị thấp hơn thực tế (~80°C)
- Tham khảo dự án mã nguồn mở Stats và chuyển sang dùng giao diện SMC
- Cần dùng các khóa khác nhau theo từng thế hệ SoC (
Tp0D, Tf0E, v.v.)
- Nếu SMC không hoạt động thì fallback sang IOKit
Triển khai đồ thị trên thanh menu
- Đồ thị hiển thị đồng thời 3 loại thông tin
- Màu nền: trạng thái nhiệt (xanh lá ~ đỏ)
- Đường liền: nhiệt độ CPU
- Đường đứt: tỷ lệ tốc độ quạt
- Thu thập dữ liệu mỗi 2 giây, giữ lịch sử trong 10 phút
- Cung cấp tooltip bằng
onContinuousHover, và
thêm .drawingGroup để dùng GPU rendering, giúp hiển thị mượt ngay cả trên màn hình 120Hz
Thông báo macOS và tự chạy
- Bổ sung tính năng gửi thông báo khi trạng thái nhiệt thay đổi
- Có thể thông báo khi chuyển sang trạng thái nhất định hoặc khi phục hồi
- Hỗ trợ thiết lập tự chạy khi đăng nhập bằng API
SMAppService
- Điều khiển qua các phương thức
register() / unregister() / status
Phân phối và sử dụng
- Do không có tài khoản Apple Developer nên không thể notarization chính thức
- Khi cài từ GitHub Releases, cần tự phê duyệt trong
Privacy and Security
- Trên một số máy Mac, cần tự build bằng Xcode mới có thể chạy
- Cách cài đặt và build được ghi trong README trên GitHub
Kết luận
- MacThrottle là công cụ gọn nhẹ giúp giám sát trạng thái thermal throttling của Apple Silicon Mac theo thời gian thực
- Hoạt động không cần quyền root, đồng thời mang lại phản hồi trực quan, thông báo và đồ thị, giúp
lập trình viên và người dùng tác vụ hiệu năng cao nhận biết trạng thái nhiệt của hệ thống
1 bình luận
Ý kiến trên Hacker News
Tôi từng dùng MacBook Pro i9 bản 2019, và có vẻ hàm phát hiện thermal throttling có thể viết đơn giản thế này
Chỉ là đùa thôi, nhưng việc mua một CPU i9 đắt tiền mà hiệu năng lại còn kém hơn i7 thực sự khá thất vọng
Tôi cũng không rõ lý do, nhưng làm vậy thì hiện tượng throttling biến mất
Dù vậy tôi vẫn tiếp tục dùng vì đã quen với quy trình làm việc trên macOS và Logic
Có thể tôi sẽ chuyển sang Linux, nhưng hiện tại nó vẫn là một cỗ máy dùng khá ổn
Mỗi lần dùng hai màn hình ngoài cùng Adobe Creative Suite là máy bị throttling rất nặng, nhưng miếng pad này đã giải quyết được
Nhược điểm là mặt đáy máy nóng lên nên khó để trên đùi, nhưng tôi hoàn toàn không hối hận
Giờ tôi đã đổi sang M3 MacBook Air (24GB RAM) và rất hài lòng
Nếu vẫn còn dùng mẫu 2019 thì tôi rất khuyên nên cân nhắc mod thermal pad cho VRM
Bên Dell cũng cải thiện rõ rệt ngay khi đổi từ i9 sang i7
Đúng kiểu bị lừa bởi marketing “số to hơn = CPU tốt hơn”
Sau đó tôi chuyển sang M1 Max và đúng là như sang một thế giới khác
Giờ tôi đã nâng cấp lên M3 Max, và Apple Silicon có vẻ sẽ còn trụ được lâu
Vừa khởi động là quạt đã quay, và khi cắm thiết bị Thunderbolt thì cũng hay bị kernel panic
M1 Max MBP mà tôi đang dùng bây giờ thì ổn định hoàn hảo
Dự án trông khá ổn
Nhưng việc phát triển trên macOS ngày càng khó hơn, và ngay cả khi phát hiện được throttling thì tôi vẫn nghi ngờ là thực tế có thể làm gì với nó
Không chỉnh được tốc độ quạt, mà undervolt cũng không thể phải không?
Đường cong mặc định quá chậm nên throttling xảy ra trước
Trên Apple Silicon, dùng High Power Mode thì quạt sẽ quay nhanh hơn
Giờ tôi không còn dùng đường cong tùy chỉnh nữa, nhưng trên 14" M4 Max thì khá ồn
MacBook Air thì không có quạt, nên chỉ còn cách để máy tự tản nhiệt
Với thiết lập mặc định thì máy lên hơn 90 độ, nên tôi đã chỉnh bảo thủ hơn
Liên kết GitHub
Thỉnh thoảng có tiến trình chạy quá đà làm máy bị throttling, đến lúc nhận ra thì pin đã tụt mất một nửa
Vấn đề này xảy ra khá thường xuyên khi có nhiều ứng dụng chạy nền
Nếu đưa lên Homebrew thì có thể nhận ký mã và công chứng miễn phí
Nếu được phân phối theo cách đó thì sẽ rất tuyệt
Giả thuyết của tôi là vấn đề không nằm ở CPU mà là bộ điều khiển USB đang làm bão hòa nhiệt
Có vẻ không phải CPU/GPU mà là cả thân máy bị quá nhiệt, làm cản trở việc tản nhiệt rồi cuối cùng dẫn tới throttling
Cần thử nghiệm thêm với adapter hoặc màn hình khác
Có lẽ bạn nói đúng
Khi cắm vào màn hình 4K 144Hz rồi mở Zoom hoặc nhiều luồng video thì máy nóng lên rất nhiều
Có lẽ không hẳn do bộ điều khiển USB mà chỉ đơn giản là tải quá cao
Có vẻ trang web đã sập vì lưu lượng tăng đột biến
Kho mã nguồn là angristan/MacThrottle
Trong iStat Menus, nếu CPU 100% nhưng mức tiêu thụ điện thấp thì có thể nghĩ là throttling,
nhưng hiện tượng tương tự cũng xảy ra khi cắm vào bộ sạc USB-C công suất thấp
Sẽ hay hơn nếu thêm tính năng phát hiện công suất sạc
Khi vừa sạc vừa dùng thì máy nóng lên nên throttling rất nặng, nhưng sạc trước buổi chơi thì hết hẳn
Từ đó tôi hiểu vì sao các thế hệ sau lại có bộ đổi nguồn công suất lớn hơn
Chẳng phải nhiệt độ mới là biến điều khiển trực tiếp sao?
Nếu hiển thị mức dùng CPU và điện năng hệ thống trên thanh menu thì có thể nhận ra bất thường ngay
exelban/stats
Thấy CPU usage cao mà điện năng lại giảm là tôi nhận ra ngay
Hy vọng MacBook Air M5 tiếp theo sẽ có làm mát bằng vapor chamber
Hiện giờ có vẻ Apple đang ưu tiên giảm tiếng ồn hơn là khả năng tản nhiệt
Vì vậy tôi buộc tốc độ quạt tối thiểu cao hơn
Khi phần thân đạt cân bằng nhiệt với môi trường thì khả năng tỏa nhiệt cũng chạm giới hạn
Nếu có quạt thì chỉ với tấm đồng và luồng gió cũng đã đủ giải quyết
Cuối cùng đây vẫn là vấn đề của định luật bảo toàn năng lượng
Có vẻ có lỗi thông báo thermal pressure
Không biết trong ứng dụng bạn có gặp vấn đề như vậy không
Vấn đề liên quan
ProcessInfo.processInfo.thermalStateNhưng với cách nhận thông báo qua thermald mà tôi đang dùng hiện tại thì không có vấn đề đó
Tôi thắc mắc vì sao lại dùng
@_silgen_nameđể khai báo trực tiếp Darwin APIimport Darwinkhông truy cập được sao?import Darwinthì API đó không được expose