Áª·¢¿ÆÐ¾Æ¬RootkitÎó²îÆÊÎö£¨CVE-2020-0069£©

Ðû²¼Ê±¼ä 2020-06-24

Ò»¡¢Îó²îÅä¾°


2020Äê3Ô£¬£¬£¬£¬£¬¹È¸èÐÞ²¹ÁËÒ»¸ö±£´æÓÚÁª·¢¿ÆÐ¾Æ¬ÖеÄÇå¾²Îó²î£¨CVE-2020-0069£©£¬£¬£¬£¬£¬Îó²îÓ°Ïì20Óà¿îÁª·¢¿ÆÐ¾Æ¬ºÍÊý°ÙÍòAndroid×°±¸¡£¡£¡£¡£¸ÃÎó²î±£´æÓÚMediaTek Command QueueÇý¶¯£¨CMDQÏÂÁîÐÐÁÐÇý¶¯£©£¬£¬£¬£¬£¬ÔÊÐíÍâµØ¹¥»÷ÕßʵÏÖ¶ÔÎïÀíÄÚ´æµØµãµÄí§Òâ¶Áд£¬£¬£¬£¬£¬´Ó¶øµ¼ÖÂȨÏÞÌáÉý¡£¡£¡£¡£


¶þ¡¢ÊÜÓ°Ïì¹ú²úÊÖ»úÐͺÅ


Huawei GR3 TAG-L21

Huawei Y5II

Huawei Y6II MT6735 series

Lenovo A5

Lenovo C2 series

Lenovo Tab E7

Lenovo Tab E8

Lenovo Tab2 A10-70F

Meizu M5c

Meizu M6

Meizu Pro 7 Plus

Oppo A59 series

Oppo A5s

Oppo A7x -- up to Android 8.x

Oppo F5 series/A73 -- up to A.39

Oppo F7 series -- Android 8.x only

Oppo F9 series -- Android 8.x only

Oppo R9xm series

Xiaomi Redmi 6/6A series

ZTE Blade A530

ZTE Blade D6/V6

ZTE Quest 5 Z3351S


Èý¡¢CMDQÇý¶¯¼òÎö


DMA£¨Ö±½ÓÄÚ´æ»á¼û£©ÊÇÔÊÐíרÓÃÓ²¼þÖ±½Ó´ÓÖ÷´æ´¢Æ÷(RAM)·¢ËÍ»òÎüÊÕÊý¾ÝµÄÒ»ÖÖÌØÕ÷¡£¡£¡£¡£ÆäÄ¿µÄÊÇͨ¹ýÔÊÐí´óÄÚ´æ»á¼û¶ø²»¹ý¶àÕ¼ÓÃCPUÀ´¼ÓËÙϵͳ¡£¡£¡£¡£MediaTek Command QueueÇý¶¯(CMDQÏÂÁîÐÐÁÐÇý¶¯)ÔÊÐí´ÓÓû§²ãÓëDMA¿ØÖÆÆ÷ͨѶ£¬£¬£¬£¬£¬ÒÔʵÏÖýÌå»òÏÔʾÏà¹ØµÄʹÃü¡£¡£¡£¡£


»ùÓÚRedmi 6/6A Ô´´úÂëÆÊÎö£¬£¬£¬£¬£¬ÔÚcmdq_driver.hÍ·ÎļþÖУ¬£¬£¬£¬£¬ÉùÃ÷cmdqÇý¶¯µÄIOCTLŲÓÃÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


CMDQ_IOCTL_ALLOC_WRITE_ADDRESSÖ¸ÁîΪ·ÖÅÉÒ»¸öDMA»º³åÇø¡£¡£¡£¡£

CMDQ_IOCTL_FREE_WRITE_ADDRESSÖ¸ÁîΪÊÍ·ÅÒ»¸öDMA»º³åÇø¡£¡£¡£¡£

CMDQ_IOCTL_READ_WRITE_ADDRESSÖ¸ÁîΪ¶Áȡһ¸öDMA»º³åÇøÖеÄÊý¾Ý¡£¡£¡£¡£

CMDQ_IOCTL_EXEC_COMMANDÖ¸ÁîÔËÐз¢ËÍÆäËûÏÂÁî¡£¡£¡£¡£


1¡¢·ÖÅÉÀú³Ì


ͨ¹ýCMDQ_IOCTL_ALLOC_WRITE_ADDRESSŲÓÃcmdqCoreAllocWriteAddress ()º¯Êý£¬£¬£¬£¬£¬·ÖÅÉÒ»¸öDMA»º³åÇø£¬£¬£¬£¬£¬¸Ãº¯ÊýÒªº¦´úÂëʵÏÖÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


È»ºó£¬£¬£¬£¬£¬Å²ÓÃcmdq_core_alloc_hw_buffer()º¯Êý·ÖÅÉDMA»º³åÇø£¬£¬£¬£¬£¬pWriteAddr->vaÊÇÐéÄâµØµã£¬£¬£¬£¬£¬pWriteAddr->paΪÎïÀíµØµã£¬£¬£¬£¬£¬Á½ÕßÖðÒ»¶ÔÓ¦¡£¡£¡£¡£²¢ÕûÀí»º³åÇø¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


×îºó£¬£¬£¬£¬£¬½«ÎïÀíµØµã¸³Öµµ½*paStart£¬£¬£¬£¬£¬²¢½«pWriteAddr½á¹¹ÌåÌí¼Óµ½gCmdqContext.writeAddrListÁ´±íÖС£¡£¡£¡£


2¡¢Ö´ÐÐÏÂÁîÀú³Ì


ÔÚCMDQ_IOCTL_EXEC_COMMANDŲÓÃÖУ¬£¬£¬£¬£¬½ÓÄÉcmdqCommandStruct½á¹¹Ìå×÷Ϊ²ÎÊý£¬£¬£¬£¬£¬½á¹¹Ìå½ç˵ÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


pVABaseÖ¸ÏòÓû§²ã´æ·ÅÏÂÁîµÄ»º³åÇø£¬£¬£¬£¬£¬»º³åÇø¾Þϸ·ÅÔÚblockSizeÖС£¡£¡£¡£ÆäÖÐcmdqReadAddressStruct½á¹¹Ìå½ç˵ÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


DmaAddressesÊÇÒª¶ÁÈ¡µÄÎïÀíµØµã£¬£¬£¬£¬£¬¶ÁÈ¡µÄÖµ´æ·ÅÔÚvaluesÖС£¡£¡£¡£ÔÚCMDQ_IOCTL_EXEC_COMMANDÏÂÁîµÄÖ´ÐÐÀú³Ì£¬£¬£¬£¬£¬ÊµÏÖ´úÂëÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


º¯ÊýŲÓ÷¾¶ÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


Cmdq_core_acquire_task()º¯Êý»á½«command°ó¶¨µ½taskÖÐÖ´ÐС£¡£¡£¡£ÏêϸʵÏÖÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


ŲÓÃcmdq_core_find_free_task()º¯Êý»ñȡһ¸ö¿ÕÏÐtask¡£¡£¡£¡£Äõ½¿ÕÏÐtask²¢¾ÙÐÐһЩ³õʼ»¯ÉèÖ㬣¬£¬£¬£¬È»ºó×îÏÈŲÓÃcmdq_core_insert_read_reg_command()º¯ÊýÖ´ÐÐÏÂÁî¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


¸Ãº¯ÊýʵÏÖÆÊÎö£¬£¬£¬£¬£¬ÏÈ¿½±´Óû§²ã´«ÈëµÄÏÂÁîµ½DMA»º³åÇøÖС£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


pCommandDesc->pVABaseÊÇ´æ·ÅÏÂÁîµÄÄÚ´æÆðʼµØµã¡£¡£¡£¡£¿£¿£¿£¿£¿£¿£¿½±´ÍêÏÂÁîºó£¬£¬£¬£¬£¬ºóÃæ·Ö¼¸ÖÖ·½·¨×îºó¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾

ÕâÀï²»×öÉ£¬£¬£¬£¬£¬×îºó¿½±´EOCºÍJUMPÖ¸Áî×îºó¡£¡£¡£¡£ÕâÀïÒ²Êǽ«Óû§²ã´«ÈëµÄÏÂÁ±´¹ýÀ´¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


´Ócmdq_core_acquire_task()º¯ÊýÖзµ»Øºó£¬£¬£¬£¬£¬ÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


ŲÓÃcmdq_core_consume_waiting_list()º¯ÊýÖ´ÐÐtask¡£¡£¡£¡£ÏÈ´ÓÆÚ´ýÐÐÁÐÖлñÈ¡task¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


È»ºó£¬£¬£¬£¬£¬»ñÈ¡¿ÕÏÐÄÚºËÏ̡߳£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


×îºó£¬£¬£¬£¬£¬½«task°ó¶¨µ½threadÖÐÈ¥Ö´ÐС£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


ËÄ¡¢¶ÁдÏÂÁîÆÊÎö


ÒÔcmdq_test.c²âÊÔ´úÂëΪÀý£¬£¬£¬£¬£¬ÆÊÎöÃ÷È·Ò»¸öÍêÕûµÄ¶ÁдÏÂÁî½á¹¹¡£¡£¡£¡£cmdqÇý¶¯Öнç˵ÁËÁ½Àà¼Ä´æÆ÷£¬£¬£¬£¬£¬Ò»ÀàÊǵصã¼Ä´æÆ÷ÓÃÓÚ´æ·ÅµØµã£¬£¬£¬£¬£¬Ò»ÀàÊÇÊýÖµ¼Ä´æÆ÷ÓÃÓÚ´æ·Å¶ÁÈ¡»òдÈëµÄÊýÖµ¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


regResultsÊÇÐéÄâµØµã£¬£¬£¬£¬£¬Å²ÓÃcmdq_core_alloc_hw_buffer()º¯Êý·ÖÅÉÒ»¸ödmaµØµã£¬£¬£¬£¬£¬regResultsMVAÓëÖ®¶ÔÓ¦£¬£¬£¬£¬£¬È»ºóÉèÖÃregResultsÖеÄÊý¾Ý¡£¡£¡£¡£¿£¿£¿£¿£¿£¿£×îÏÈÆ´½Ó¶ÁÈ¡ºÍдÈëÏÂÁ


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


½«regResults[0]µÄµØµãдÈëCMDQ_DATA_REG_DEBUG_DSTÀàÐ͵ĵصã¼Ä´æÆ÷ÖС£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


È»ºó£¬£¬£¬£¬£¬´ÓCMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷ÖжÁÈ¡Êý¾Ý²¢Ð´Èëµ½CMDQ_DATA_REG_DEBUGÊýÖµ¼Ä´æÆ÷ÖС£¡£¡£¡£Õâʱ¼ä£¬£¬£¬£¬£¬CMDQ_DATA_REG_DEBUGÊýÖµ¼Ä´æÆ÷ÖеÄÖµÓ¦¸ÃΪ0xdeaddead¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


½Ó×Å£¬£¬£¬£¬£¬½«regResults[1]µÄµØµãת´æµ½CMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷ÖС£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


×îºó£¬£¬£¬£¬£¬½«CMDQ_DATA_REG_DEBUGÊýÖµ¼Ä´æÆ÷ÖеÄ0xdeaddeadдÈëµ½CMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷ÖÐÉúÑĵÄregResults[1]µÄµØµãÖУ¬£¬£¬£¬£¬¼´regResults[1]=0xdeaddead¡£¡£¡£¡£ÅжÏregResults[0]ºÍregResults[1]ÊÇ·ñÏàµÈ¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


ÈôÊÇÏàµÈ£¬£¬£¬£¬£¬ËµÃ÷¶ÁдÀֳɡ£¡£¡£¡£


Îå¡¢PoCÆÊÎöÓë²âÊÔ


£¨1£©PoC´úÂëÖУ¬£¬£¬£¬£¬Ö´ÐÐд²Ù×÷µÄÒªº¦´úÂëÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


дÈëÀú³ÌÖУ¬£¬£¬£¬£¬ÏȽ«value[count]ÒÆ¶¯µ½CMDQ_DATA_REG_DEBUGÊýÖµ¼Ä´æÆ÷ÖУ¬£¬£¬£¬£¬È»ºó½«pa_address+offsetµØµãÒÆ¶¯µ½CMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷ÖУ¬£¬£¬£¬£¬×îºó½«CMDQ_DATA_REG_DEBUGÊýÖµ¼Ä´æÆ÷ÖеÄvalueдÈëµ½CMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷ÖÐÉúÑĵÄpa_address+offsetµØµãÖУ¬£¬£¬£¬£¬¼´*(pa_address+offset)= value[count]¡£¡£¡£¡£


£¨2£©PoC´úÂëÖУ¬£¬£¬£¬£¬Ö´ÐжÁ²Ù×÷µÄÒªº¦´úÂëÈçÏ£º


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


¶ÁÈ¡Àú³ÌÖУ¬£¬£¬£¬£¬µÚÒ»²½ÏȽ«pa_address+offsetµØµãÒÆ¶¯µ½CMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷ÖУ¬£¬£¬£¬£¬È»ºó´ÓCMDQ_DATA__REG_DEBUG_DSTµØµã¼Ä´æÆ÷Öд洢µÄµØµãpa_address+offsetÖжÁÈ¡Êý¾Ý·Åµ½CMDQ_DATA_REG_DEBUGÊý¾Ý¼Ä´æÆ÷ÖУ¬£¬£¬£¬£¬ÔÙ½«dma_address+offsetµØµãÒÆ¶¯µ½CMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷ÖУ¬£¬£¬£¬£¬×îºó½«CMDQ_DATA_REG_DEBUGÊýÖµ¼Ä´æÆ÷ÖÐÉúÑĵÄÊý¾ÝдÈëµ½CMDQ_DATA_REG_DEBUG_DSTµØµã¼Ä´æÆ÷Öд洢µÄdma_address+offsetµØµãÖУ¬£¬£¬£¬£¬¼´*(dma_address+ offset) = *(pa_address + offset)¡£¡£¡£¡£


£¨3£©ÔÚReami6²âÊÔ»úÖУ¬£¬£¬£¬£¬Ö´ÐÐPoC²âÊÔ£¬£¬£¬£¬£¬Àֳɽ«LinuxÐ޸ijÉminix¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾


²Î¿¼Á´½Ó£º

[1]https://github.com/MiCode/Xiaomi_Kernel_OpenSource/tree/cactus-p-oss/drivers/misc/mediatek/cmdq

[2]https://github.com/quarkslab/CVE-2020-0069_poc/blob/master/jni/kernel_rw.c

[3]https://blog.quarkslab.com/cve-2020-0069-autopsy-of-the-most-stable-mediatek-rootkit.html

[4]https://forum.xda-developers.com/android/development/amazing-temp-root-mediatek-armv8-t3922213

[5]https://source.android.com/security/bulletin/2020-03-01



ÍòÀû¹ú¼Ê¹ÙÍøÆð¾¢·ÀÓùʵÑéÊÒ£¨ADLab£©


ADLab½¨ÉèÓÚ1999Ä꣬£¬£¬£¬£¬ÊÇÖйúÇå¾²ÐÐÒµ×îÔ罨ÉèµÄ¹¥·ÀÊÖÒÕÑо¿ÊµÑéÊÒÖ®Ò»£¬£¬£¬£¬£¬Î¢ÈíMAPPÍýÏë½¹µã³ÉÔ±£¬£¬£¬£¬£¬¡°ºÚȸ¹¥»÷¡±¿´·¨Ê×ÍÆÕß¡£¡£¡£¡£×èÖ¹ÏÖÔÚ£¬£¬£¬£¬£¬ADLabÒÑͨ¹ýCVEÀÛ¼ÆÐû²¼Çå¾²Îó²î1000Óà¸ö£¬£¬£¬£¬£¬Í¨¹ý CNVD/CNNVDÀÛ¼ÆÐû²¼Çå¾²Îó²î800Óà¸ö£¬£¬£¬£¬£¬Ò»Á¬¼á³Ö¹ú¼ÊÍøÂçÇå¾²ÁìÓòÒ»Á÷Ë®×¼¡£¡£¡£¡£ÊµÑéÊÒÑо¿Æ«Ïòº­¸Ç²Ù×÷ϵͳÓëÓ¦ÓÃϵͳÇå¾²Ñо¿¡¢Òƶ¯ÖÇÄÜÖÕ¶ËÇå¾²Ñо¿¡¢ÎïÁªÍøÖÇÄÜ×°±¸Çå¾²Ñо¿¡¢WebÇå¾²Ñо¿¡¢¹¤¿ØÏµÍ³Çå¾²Ñо¿¡¢ÔÆÇå¾²Ñо¿¡£¡£¡£¡£Ñо¿Ð§¹ûÓ¦ÓÃÓÚ²úÆ·½¹µãÊÖÒÕÑо¿¡¢¹ú¼ÒÖØµã¿Æ¼¼ÏîÄ¿¹¥¹Ø¡¢×¨ÒµÇ徲ЧÀ͵È¡£¡£¡£¡£


ÍòÀû¹ú¼Ê¹ÙÍø(ÖйúÓÎ)ÓÐÏÞ¹«Ë¾