Android NDK รองรับ HWAddress Sanitizer หรือที่เรียกว่า HWASan ตั้งแต่ NDK r21 และ Android 10 (API ระดับ 29) HWASan ใช้ได้เฉพาะในอุปกรณ์ Arm แบบ 64 บิตเท่านั้น
HWASan เป็นเครื่องมือตรวจหาข้อผิดพลาดด้านหน่วยความจําที่คล้ายกับ ASan เมื่อเทียบกับ ASan แบบคลาสสิก HWASan มีดังนี้
- ภาระงานของ CPU ที่คล้ายกัน (~2 เท่า)
- ค่าใช้จ่ายเพิ่มเติมเกี่ยวกับขนาดโค้ดที่คล้ายกัน (40 – 50%)
- การใช้ RAM น้อยลงมาก (10% - 35%)
HWASan จะตรวจหาข้อบกพร่องชุดเดียวกับ ASan ดังนี้
- บัฟเฟอร์สแต็กและฮีปที่ล้นหรือต่ำกว่าเกณฑ์
- การใช้งานฮีปหลังจากมีการปลดปล่อย
- การใช้สแต็กนอกขอบเขต
- ฟรีแบบคู่หรือฟรีแบบอิสระ
นอกจากนี้ HWASan ยังตรวจหาสิ่งต่อไปนี้ด้วย
- การใช้กองหลังจากการคืนค่า
แอปตัวอย่าง
แอปตัวอย่างจะแสดงวิธีกำหนดค่าตัวแปรของบิวด์สำหรับ Hwasan
สร้าง
หากต้องการสร้างโค้ดเนทีฟ (JNI) ของแอปด้วย HWAddress Sanitizer ให้ทําดังนี้
ndk-build
ในไฟล์ Application.mk
APP_STL := c++_shared # Or system, or none, but not c++_static.
APP_CFLAGS := -fsanitize=hwaddress -fno-omit-frame-pointer
APP_LDFLAGS := -fsanitize=hwaddress
CMake
ในไฟล์ build.gradle
ของโมดูล ให้ทำดังนี้
android {
defaultConfig {
externalNativeBuild {
cmake {
# Can also use system or none as ANDROID_STL, but not c++_static.
arguments "-DANDROID_STL=c++_shared"
}
}
}
}
สําหรับแต่ละเป้าหมายใน CMakeLists.txt ให้ทำดังนี้
target_compile_options(${TARGET} PUBLIC -fsanitize=hwaddress -fno-omit-frame-pointer)
target_link_options(${TARGET} PUBLIC -fsanitize=hwaddress)
เมื่อใช้ NDK 27 ขึ้นไป คุณจะใช้สิ่งต่อไปนี้ใน build.gradle
ได้โดยไม่ต้องเปลี่ยน CMakeLists.txt
android {
defaultConfig {
externalNativeBuild {
cmake {
arguments "-DANDROID_SANITIZE=hwaddress"
}
}
}
}
ซึ่งจะไม่ทำงานเมื่อใช้ ANDROID_USE_LEGACY_TOOLCHAIN_FILE=false
Android 14 ขึ้นไป: เพิ่ม wrap.sh
หากใช้ Android 14 ขึ้นไป คุณสามารถใช้สคริปต์ wrap.sh เพื่อเรียกใช้แอปที่แก้ไขข้อบกพร่องได้ในอุปกรณ์ Android เครื่องใดก็ได้ คุณข้ามขั้นตอนนี้ได้หากเลือกที่จะทําตามขั้นตอนในวิธีการตั้งค่า
ทำตามวิธีการเพื่อแพ็กเกจสคริปต์ wrap.sh เพื่อเพิ่มสคริปต์ wrap.sh ต่อไปนี้สำหรับ arm64-v8a
#!/system/bin/sh
LD_HWASAN=1 exec "$@"
เรียกใช้
หากคุณใช้ Android เวอร์ชันเก่ากว่า 14 หรือไม่ได้เพิ่มสคริปต์ wrap.sh ให้ทำตามวิธีการตั้งค่าก่อนเรียกใช้แอป
เรียกใช้แอปตามปกติ เมื่อตรวจพบข้อผิดพลาดด้านหน่วยความจำ แอปจะขัดข้องด้วย SIGABRT และพิมพ์ข้อความโดยละเอียดไปยัง Logcat สำเนาข้อความจะอยู่ในไฟล์ในส่วน /data/tombstones
และมีลักษณะดังนี้
ERROR: HWAddressSanitizer: tag-mismatch on address 0x0042a0826510 at pc 0x007b24d90a0c
WRITE of size 1 at 0x0042a0826510 tags: 32/3d (ptr/mem) in thread T0
#0 0x7b24d90a08 (/data/app/com.example.hellohwasan-eRpO2UhYylZaW0P_E0z7vA==/lib/arm64/libnative-lib.so+0x2a08)
#1 0x7b8f1e4ccc (/apex/com.android.art/lib64/libart.so+0x198ccc)
#2 0x7b8f1db364 (/apex/com.android.art/lib64/libart.so+0x18f364)
#3 0x7b8f2ad8d4 (/apex/com.android.art/lib64/libart.so+0x2618d4)
0x0042a0826510 is located 0 bytes to the right of 16-byte region [0x0042a0826500,0x0042a0826510)
allocated here:
#0 0x7b92a322bc (/apex/com.android.runtime/lib64/bionic/libclang_rt.hwasan-aarch64-android.so+0x212bc)
#1 0x7b24d909e0 (/data/app/com.example.hellohwasan-eRpO2UhYylZaW0P_E0z7vA==/lib/arm64/libnative-lib.so+0x29e0)
#2 0x7b8f1e4ccc (/apex/com.android.art/lib64/libart.so+0x198ccc)
ข้อความนี้อาจตามด้วยข้อมูลการแก้ไขข้อบกพร่องเพิ่มเติม ซึ่งรวมถึงรายการเธรดที่กำลังทำงานในแอปพลิเคชัน แท็กของการจัดสรรหน่วยความจำที่อยู่ใกล้เคียง และค่ารีจิสเตอร์ CPU
ดูข้อมูลเพิ่มเติมเกี่ยวกับข้อความแสดงข้อผิดพลาด HWASan ได้ที่การทำความเข้าใจรายงาน HWASan
การสร้างไฟล์ปฏิบัติการของบรรทัดคำสั่ง
คุณสามารถสร้างและเรียกใช้ไฟล์ปฏิบัติการที่เครื่องมือวัดประสิทธิภาพ HWASan ตรวจสอบแล้วใน Android 14 ขึ้นไป คุณใช้การกำหนดค่าเดียวกันกับที่อธิบายไว้ในการสร้างสำหรับ ndk-build หรือ CMake สำหรับไฟล์ปฏิบัติการได้ พุชไฟล์ที่เรียกใช้งานได้ไปยังอุปกรณ์ที่ใช้ Android 14 ขึ้นไป แล้วเรียกใช้ตามปกติโดยใช้เชลล์
หากคุณใช้ libc++ ให้ตรวจสอบว่าคุณใช้ STL ที่แชร์และพุชไปยังอุปกรณ์ รวมถึงตั้งค่า LD_LIBRARY_PATH
เป็นไดเรกทอรีที่มี STL ดังกล่าวเมื่อเรียกใช้ไบนารี
หากคุณไม่ได้ใช้ Gradle โปรดดูเอกสารประกอบ NDK เพื่อดูวิธีสร้างจากบรรทัดคำสั่งด้วย CMake และ ndk-build
Android 13 หรือเวอร์ชันก่อนหน้า: การตั้งค่า
หากอุปกรณ์ใช้ Android 14 ขึ้นไป คุณสามารถข้ามขั้นตอนนี้และทำตามวิธีการใช้ wrap.sh ในส่วนสร้าง นอกจากนี้ คุณยังเลือกที่จะทำตามส่วนนี้และข้ามวิธีการใช้ wrap.sh ได้ด้วย
ก่อนที่จะเป็น Android 14 แอปพลิเคชัน HWASan ต้องใช้ Android รุ่น HWASan จึงจะทำงานได้ คุณสามารถแฟลชอิมเมจ HWASan ที่คอมไพล์ไว้ล่วงหน้าลงในอุปกรณ์ Pixel ที่รองรับ บิลด์มีให้บริการใน ci.android.com ซึ่งคุณสามารถคลิกสี่เหลี่ยมจัตุรัสของบิลด์ที่ต้องการเพื่อรับลิงก์บิลด์แฟลช ซึ่งคุณจะต้องทราบชื่อรหัสของโทรศัพท์
คุณอาจไปที่ flash.android.com โดยตรงจะง่ายกว่า เนื่องจากขั้นตอนเริ่มต้นด้วยการสแกนอุปกรณ์และแสดงเฉพาะบิลด์ที่คุณใช้ได้ รูปภาพต่อไปนี้แสดงขั้นตอนการตั้งค่าในเครื่องมือนี้
เปิดใช้โหมดนักพัฒนาแอปในอุปกรณ์และเชื่อมต่อกับคอมพิวเตอร์โดยใช้สาย USB คลิกเพิ่มอุปกรณ์ใหม่ เลือกอุปกรณ์จากกล่องโต้ตอบ แล้วคลิกเชื่อมต่อ
หลังจากเชื่อมต่ออุปกรณ์แล้ว ให้คลิกอุปกรณ์เพื่อกำหนดค่าบิลด์
ในช่องเลือกรหัสบิลด์ ให้เลือกสาขา aosp-master-with-phones-throttled
เพื่อเลือกรูปภาพที่ถูกต้องสำหรับอุปกรณ์ที่คุณเชื่อมต่อโดยอัตโนมัติ
คลิกติดตั้งเพื่อแฟลชอุปกรณ์
ดูรายละเอียดเพิ่มเติมเกี่ยวกับการตั้งค่าที่จำเป็นได้ในเอกสารประกอบเกี่ยวกับเครื่องมือแฟลช Android หรือจะดูวิธีการสร้างภาพ HWASan จากแหล่งที่มาในเอกสารประกอบ AOSP ก็ได้