Windows SMB Ghost£¨CVE-2020-0796£©Â©¶´·ÖÎö

Ðû²¼Ê±¼ä 2020-04-09

©¶´½éÉÜ


2020Äê3ÔÂ10ÈÕ£¬Î¢ÈíÔÚÆä¹Ù·½SRCÐû²¼ÁËCVE-2020-0796µÄÄþ¾²Í¨¸æ£¨ADV200005£¬Microsoft Guidance for Disabling SMBv3 Compression£©,ͨ¸æÌåÏÖÔÚWindows SMBv3°æ±¾µÄ¿Í»§¶ËºÍ·þÎñ¶Ë´æÔÚÔ¶³Ì´úÂëÖ´ÐЩ¶´ ¡£Í¬Ê±Ö¸³ö¸Ã©¶´´æÔÚÓÚMicroSoft Server Message Block 3.1.1ЭÒé´¦ÖÃÌض¨ÇëÇó°üµÄ¹¦Ð§ÖУ¬¹¥»÷ÕßÀûÓø鶴¿ÉÔÚÄ¿±êSMB Server»òÕßClientÖÐÖ´ÐÐÈÎÒâ´úÂë ¡£


¶«É­Æ½Ì¨ADLabÄþ¾²Ñо¿ÈËÔ±ÔڶԸ鶴½øÐÐÑо¿µÄ¹ý³ÌÖз¢ÏÖÄ¿Ç°Á÷´«µÄһЩ©¶´·ÖÎö´æÔÚijЩÎÊÌ⣬Òò´Ë¶Ô¸Ã©¶´½øÐÐÁËÉîÈëµÄ·ÖÎö£¬²¢ÔÚWindows 10ϵͳÉϽøÐÐÁ˸´ÏÖ ¡£



©¶´¸´ÏÖ


½ÓÄÉWindows 10 1903°æ±¾½øÐи´ÏÖ ¡£ÔÚ©¶´ÀûÓúó£¬ÑéÖ¤·¨Ê½ÌáȨ½áÊøºó´´½¨ÁËÒ»¸ösystemȨÏÞµÄcmd shell£¬Èçͼ1Ëùʾ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ1 CVE-2020-0796µ±µØÌáȨ


©¶´»ù±¾Ô­Àí


CVE-2020-0796©¶´´æÔÚÓÚÊÜÓ°Ïì°æ±¾µÄWindowsÇý¶¯srv2.sysÖÐ ¡£Windows SMB v3.1.1 °æ±¾Ôö¼ÓÁ˶ÔѹËõÊý¾ÝµÄÖ§³Ö ¡£Í¼2ËùʾΪ´øѹËõÊý¾ÝµÄSMBÊý¾Ý±¨ÎĵÄ×é³É ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ2 ´øѹËõÊý¾ÝµÄSMBÊý¾Ý±¨ÎĽṹ


ƾ¾Ý΢ÈíMS-SMB2ЭÒéÎĵµ£¬SMB Compression Transform HeaderµÄ½á¹¹Èçͼ3Ëùʾ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ3 SMB Compression Transform HeaderÊý¾Ý½á¹¹


ProtocolId£º4×Ö½Ú£¬ÀιÌΪ0x424D53FC

OriginalComressedSegmentSize£º4×Ö½Ú£¬Ô­Ê¼µÄδѹËõÊý¾Ý¾Þϸ

CompressionAlgorithm£º2×Ö½Ú£¬Ñ¹ËõËã·¨

Flags £º2×Ö½Ú£¬Ïê¼ûЭÒéÎĵµ

Offset/Length£ºÆ¾¾ÝFlagsµÄȡֵΪOffset»òÕßLength£¬OffsetÌåÏÖÊý¾Ý°üÖÐѹËõÊý¾ÝÏà¶ÔÓÚµ±Ç°½á¹¹µÄÆ«ÒÆ

srv2.sysÖд¦ÖÃSMBv3ѹËõÊý¾Ý°üµÄ½âѹº¯ÊýSrv2DecompressDataδÑϸñУÑéÊý¾Ý°üÖÐOriginalCompressedSegmentSizeºÍOffset/Length×ֶεĺϷ¨ÐÔ ¡£¶øÕâÁ½¸ö×Ö¶ÎÓ°ÏìÁËSrv2DecompressDataÖÐÄÚ´æ·ÖÅ亯ÊýSrvNetAllocateBufferµÄ²ÎÊý ¡£Èçͼ4ËùʾµÄSrv2DecompressDataº¯Êý·´±àÒë´úÂ룬SrvNetAllocateBufferʵ¼ÊµÄ²ÎÊýΪOriginalCompressedSegmentSize+Offset ¡£ÕâÁ½¸ö²ÎÊý¶¼Ö±½ÓÀ´Ô´ÓÚÊý¾Ý°üÖÐSMB Compression Transform HeaderÖеÄ×ֶΣ¬¶øº¯Êý²¢Î´ÅжÏÕâÁ½¸ö×Ö¶ÎÊÇ·ñºÏ·¨£¬¾ÍÖ±½Ó½«ÆäÏà¼Óºó×÷ΪÄÚ´æ·ÖÅäµÄ²ÎÊý(unsigned intÀàÐÍ£© ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ4 Srv2DecompressDataº¯ÊýµÄÒªº¦´úÂë


ÕâÀOriginalCompressedSegmentSize+Offset¿ÉÄÜСÓÚʵ¼ÊÐèÒª·ÖÅäµÄÄÚ´æ¾Þϸ£¬´Ó¶øÔÚºóÐøµ÷Óýâѹº¯ÊýSmbCompressionDecompress¹ý³ÌÖдæÔÚÔ½½ç¶ÁÈ¡»òÕßдÈëµÄ·çÏÕ ¡£


ÌáȨÀûÓùý³Ì


Ä¿Ç°ÒѹûÈ»µÄÕë¶Ô¸Ã©¶´µÄµ±µØÌáȨÀûÓðüÂÞÈçϵÄÖ÷Òª¹ý³Ì£º

£¨1£©ÑéÖ¤·¨Ê½Ê×ÏÈ´´½¨µ½SMS serverµÄ»á»°Á¬½Ó£¨¼ÇΪsession£© ¡£

£¨2£©ÑéÖ¤·¨Ê½»ñÈ¡×ÔÉítokenÊý¾Ý½á¹¹ÖÐprivilege³ÉÔ±ÔÚÄÚºËÖеĵØÖ·£¨¼ÇtokenAddr£© ¡£

£¨3£©ÑéÖ¤·¨Ê½Í¨¹ýsession·¢ËÍ»ûÐÎѹËõÊý¾Ý£¨¼ÇΪevilData£©¸øSMB server´¥·¢Â©¶´ ¡£ÆäÖУ¬evilData°üÂÞtokenAddr¡¢È¨ÏÞÊý¾Ý¡¢Òç³öռλÊý¾Ý ¡£

£¨4£©SMS serverÊÕµ½evilDataºó´¥·¢Â©¶´£¬²¢ÐÞ¸ÄtokenAddrµØÖ·´¦µÄȨÏÞÊý¾Ý£¬´Ó¶øÌáÉýÑéÖ¤·¨Ê½µÄȨÏÞ ¡£

£¨5£©ÑéÖ¤·¨Ê½»ñȡȨÏÞºó¶Ôwinlogon½øÐпØÖÆ£¬À´´´½¨systemÓû§shell ¡£


©¶´ÄÚ´æ·ÖÅä·ÖÎö


Ê×ÏÈ£¬¿´Ò»ÏÂÒѹûÈ»ÀûÓõÄevilDataÊý¾Ý°üµÄÄÚÈÝ£¬Èçͼ5Ëùʾ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ5 ÌáȨpoc·¢Ë͵ĴøѹËõÊý¾ÝµÄSMBÊý¾Ý°ü


Êý¾Ý°üµÄÄÚÈݺܼòµ¥£¬ÆäÖм¸¸öÒªº¦×Ö¶ÎÊý¾ÝÈçÏ£º

OriginalSize£º0xffffffff

Offset£º0x10

Real compressed data£º13×Ö½ÚµÄѹËõÊý¾Ý£¬½âѹºóӦΪ1108×Ö½Ú¡¯A¡¯¼Ó8×Ö½ÚµÄtokenµØÖ· ¡£

SMB3 raw data£ºÊµ¼ÊÉÏÊÇÓÉ2¸ö8×Ö½ÚµÄ0x1FF2FFFFBC£¨×ܳ¤0x10)¼ÓÉÏ0x13×Ö½ÚµÄѹËõÊý¾Ý×é³É ¡£

´ÓÉÏÃæµÄ©¶´Ô­Àí·ÖÎö¿ÉÖª£¬Â©¶´³ÉÒòÊÇSrv2DecompressDataº¯Êý¶Ô±¨ÎÄ×Ö¶Îȱ·¦ºÏ·¨ÐÔÅжÏÔì³ÉÄÚ´æ·ÖÅä²»Í× ¡£Ôڸ鶴Êý¾Ý°üÖУ¬OriginalSize ÊÇÒ»¸ö»ûÐÎÖµ ¡£OriginalSize + Offset = 0xffffffff + 0x10 = 0xf ÊÇÒ»¸öºÜСµÄÖµ£¬Æ佫»áͨ±¨¸øSrvNetAllocateBuffer½øÐе÷Óã¬ÏÂÃæ¾ßÌå·ÖÎöÄÚ´æ·ÖÅäÇé¿ö ¡£SrvNetAllocateBufferµÄ·´±àÒë´úÂëÈçͼ6 ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ6 SrvNetAllocateBufferÄÚ´æ·ÖÅä¹ý³Ì


ÓÉÓÚ´«¸øSrvNetAllocateBufferµÄ²ÎÊýΪ0xf£¬Æ¾¾ÝSrvNetAllocateBufferµÄ´¦ÖÃÁ÷³Ì¿ÉÖª£¬¸ÃÇëÇóÄڴ潫´ÓSrvNetBufferLookasides±íÖзÖÅä ¡£ÕâÀïÐèҪעÒâµÄÊÇ£¬±äÁ¿SrvDisableNetBufferLookAsideList¸ú×¢²á±íÏîÏà¹Ø£¬ÏµÍ³Ä¬ÈÏ״̬ÏÂSrvDisableNetBufferLookAsideListΪ0 ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ7 SrvDisableNetBufferLookAsideList±äÁ¿³õʼ»¯¹ý³Ì


SrvNetBufferLookasides±íͨ¹ýº¯ÊýSrvNetCreateBuffer³õʼ»¯£¬Êµ¼ÊSrvNetCreateBufferÑ­»·µ÷ÓÃÁËSrvNetBufferLookasideAllocate·ÖÅäÄڴ棬µ÷ÓÃSrvNetBufferLookasideAllocateµÄ²ÎÊý·Ö±ðΪ[¡®0x1100¡¯, ¡®0x2100¡¯, ¡®0x4100¡¯, ¡®0x8100¡¯, ¡®0x10100¡¯, ¡®0x20100¡¯, ¡®0x40100¡¯, ¡®0x80100¡¯, ¡®0x100100¡¯] ¡£ÔÚÕâÀÄÚ´æ·ÖÅä²ÎÊýΪ0xf£¬¶ÔÓ¦µÄlookaside±íΪ0x1100¾ÞϸµÄ±íÏî ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ8 SrvNetCreateBuffer·´±àÒë´úÂë


SrvNetBufferLookasideAllocateº¯Êýʵ¼ÊÊǵ÷ÓÃSrvNetAllocateBufferFromPoolÀ´·ÖÅäÄڴ棬Èçͼ9Ëùʾ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ9 SrvNetBufferLookasideAllocate·´±àÒë´úÂë


ÔÚº¯ÊýSrvNetAllocateBufferFromPoolÖУ¬¶ÔÓÚÓû§ÇëÇóµÄÄÚ´æ·ÖÅä¾Þϸ£¬ÄÚ²¿Í¨¹ýExAllocatePoolWithTagº¯Êý·ÖÅäµÄÄÚ´æʵ¼ÊÒª´óÓÚÇëÇóÖµ£¨¶à³ö²¿ÃÅÓÃÓÚ´æ´¢²¿ÃÅÄÚ´æÏà¹ØÊý¾Ý½á¹¹£© ¡£ÒÔÇëÇó·ÖÅä0x1100¾ÞϸΪÀý£¬¾­¹ýһϵÁÐÅжϺó£¬×îºó·ÖÅäµÄÄÚ´æ¾Þϸallocate_size = 0x1100 + E8 + 2*(MmSizeOfMdl + 8) ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ10 SrvNetAllocateBufferFromPoolº¯Êý·´±àÒë´úÂë


ÄÚ´æ·ÖÅäÍê±ÏÖ®ºó£¬SrvNetAllocateBufferFromPoolº¯Êý»¹¶Ô·ÖÅäµÄÄÚ´æ½øÐÐÁËһϵÁгõʼ»¯²Ù×÷£¬×îºó·µ»ØÁËÒ»¸öÄÚ´æÐÅÏ¢½á¹¹ÌåÖ¸Õë×÷Ϊº¯ÊýµÄ·µ»ØÖµ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ11  SrvNetAllocateBufferFromPool³õʼ»¯ÄÚ´æÊý¾Ý


ÕâÀïÐèҪעÒâÈçϵÄÊý¾Ý¹Øϵ£ºSrvNetAllocateBufferFromPoolº¯Êý·µ»ØÖµreturn_bufferÖ¸ÏòÒ»¸öÄÚ´æÊý¾Ý½á¹¹£¬¸ÃÄÚ´æÊý¾Ý½á¹¹ÆðʼµØַͬʵ¼Ê·ÖÅäÄڴ棨º¯ÊýExAllocatePoolWithTag·ÖÅäµÄÄڴ棩ÆðʼµØÖ·µÄµÄÆ«ÒÆΪ0x1150£»return_buffer+0x18λÖÃÖ¸ÏòÁËʵ¼Ê·ÖÅäÄÚ´æÆðʼµØÖ·Æ«ÒÆ0x50λÖô¦£¬¶ø×îÖÕreturn_buffer»á×÷Ϊº¯ÊýSrvNetAllocateBufferµÄ·µ»ØÖµ ¡£ÆäÄÚ´æ½á¹¹¹ØϵÈçͼ12 ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾


ͼ12 SrvNetAllocateBuffer£¨0xf)·µ»ØµÄÄÚ´æÊý¾Ý½á¹¹


©¶´ÄÚ´æÆÆ»µ·ÖÎö


»Øµ½Â©¶´½âѹº¯ÊýSrv2DecompressData£¬ÔÚ½øÐÐÄÚ´æ·ÖÅäÖ®ºó£¬Srv2DecompressDataµ÷Óú¯ÊýSmbCompressionDecompress¿ªÊ¼½âѹ±»Ñ¹ËõµÄÊý¾Ý ¡£Æ亯ÊýÂß¼­Èçͼ13Ëùʾ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ13 Srv2DecompressData½âѹѹËõÊý¾Ý


ʵ¼ÊÉÏ£¬¸Ãº¯Êýµ÷ÓÃÁËWindows¿âº¯ÊýRtlDecompressBufferEx2À´ÊµÏÖ½âѹ£¬Æ¾¾ÝRtlDecompressBufferEx2µÄº¯ÊýÔ­ÐÍÀ´¶ÔÓ¦·ÖÎöSmbCompressionDecompressº¯ÊýµÄ¸÷¸ö²ÎÊý ¡£


SmbCompressionDecompress(CompressAlgo£¬//ѹËõËã·¨

Compressed_buf£¬//Ö¸ÏòÊý¾Ý°üÖеÄѹËõÊý¾Ý  

Compressed_size£¬//Êý¾Ý°üÖÐѹËõÊý¾Ý¾Þϸ£¬¼ÆËãµÃµ½  

UnCompressedBuf,//½âѹºóµÄÊý¾Ý´æ´¢µØÖ·£¬*(alloc_buffer+0x18)+0x10    

UnCompressedSize,//ѹËõÊý¾Ýԭʼ¾Þϸ,Ô´ÓÚÊý¾Ý°üOriginalCompressedSegmentSize  

FinalUnCompressedSize)//×îÖÕ½âѹºóÊý¾Ý¾Þϸ


´Ó·´±àÒë´úÂë¿ÉÒÔ¿´³ö£¬º¯ÊýSmbCompressionDecompressÖÐÉú´æ½âѹºóÊý¾ÝµÄµØַΪ*(alloc_buffer+0x18)+0x10µÄλÖã¬Æ¾¾ÝÄÚ´æ·ÖÅä¹ý³Ì·ÖÎö£¬alloc_buffer + 0x18Ö¸ÏòÁËʵ¼ÊÄÚ´æ·ÖÅäÆðʼλÖÃÆ«ÒÆ0x50´¦£¬ËùÒÔ¿½±´Ä¿µÄµØַΪʵ¼ÊÄÚ´æ·ÖÅäÆðʼµØÖ·Æ«ÒÆ0x60λÖô¦ ¡£


ÔÚ½âѹ¹ý³ÌÖУ¬Ñ¹ËõÊý¾Ý½âѹºó½«´æ´¢µ½Õâ¸öµØÖ·Ö¸ÏòµÄÄÚ´æÖÐ ¡£Æ¾¾ÝevilDataÊý¾ÝµÄ½á¹¹¹ý³Ì£¬½âѹºóµÄÊý¾ÝΪռ¿ÓÊý¾ÝºÍtokenAddr ¡£¿½±´µ½¸Ã´¦µØÖ·ºó£¬tokenAddr½«ÁýÕÖÔ­ÄÚ´æÊý¾Ý½á¹¹ÖÐalloc_buffer+0x18´¦µÄÊý¾Ý ¡£Ò²¾ÍÊǽâѹËõº¯ÊýSmbCompressionDecompress·µ»Øºó£¬alloc_buffer+0x18½«Ö¸ÏòÑéÖ¤·¨Ê½µÄtokenAddrÄں˵ØÖ· ¡£¿½±´¹ý³ÌÈçͼ14ºÍ15Ëùʾ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ14 ½âѹ¿½±´¹ý³Ì


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ15½âѹÍê³ÉºóÄÚ´æ½á¹¹


¼ÌÐø¿´Srv2DecompressDataµÄºóÐø´¦ÖÃÁ÷³Ì£¬½âѹÀֳɺ󣬺¯ÊýÅжÏoffsetµÄ½á¹û²»Îª0 ¡£²»Îª0Ôò½øÐÐÄÚ´æÒƶ¯£¬Äڴ濽±´µÄ²ÎÊýÈçÏ£º


memmove(*(alloc_buffer+0x18)£¬SMB_payload£¬offset)

´Ëʱ£¬alloc_buffer+0x18ÒѾ­Ö¸ÏòÑéÖ¤·¨Ê½µÄtokenAddrÄں˵ØÖ·£¬¶øSMB_payload´ËʱָÏòevilDataÖеÄȨÏÞÊý¾Ý£¬offsetÔòΪ0x10 ¡£Òò´Ë£¬Õâ¸öÄÚ´æÒƶ¯Íê³Éºó£¬È¨ÏÞÊý¾Ý½«Ð´ÈëtokenAddr´¦ ¡£ÕâÒâζ×Å£¬SMS ServerÀÖ³ÉÐÞ¸ÄÁËÑéÖ¤·¨Ê½µÄȨÏÞ£¬´Ó¶øʵÏÖÁËÑéÖ¤·¨Ê½µÄÌáȨ£¡


»¹ÓÐÒ»¸öϸ½ÚÐèҪעÒ⣬ÔÚ½âѹʱ£¬Srv2DecompressDataº¯Êý»áÅжÏʵ¼ÊµÄ½âѹºóÊý¾Ý¾ÞϸFinalUnCompressedSizeÊÇ·ñºÍÊý¾Ý°üÖÐԭʼÊý¾Ý¾ÞϸOriginalCompressedSegmentSizeÒ»Ö£¬Èçͼ16Ëùʾ ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾


ͼ16 Srv2DecompressData¼ì²éѹËõÊý¾Ý¾Þϸ


°´ÀíÀ´ËµÊµ¼Ê½âѹºóµÄÊý¾Ý¾ÞϸΪ0x1100£¬²»¼´ÊÇÊý¾Ý°üÖеÄԭʼѹËõÊý¾Ý¾Þϸ0xffffffff£¬ÕâÀïÓ¦¸Ã½øÈëµ½ºóÃæÄÚ´æÊͷŵÄÁ÷³Ì ¡£È»¶ø£¬Êµ¼ÊÉÏÔÚº¯ÊýSmbCompressionDecompressÖУ¬µ÷ÓÃRtlDecompressBufferEx2Àֳɺó»áÖ±½Ó½«OriginalCompressedSegmentSize¸³Öµ¸øFinalUnCompressedSize ¡£ÕâÒ²ÊǸ鶴¹ØÓÚÈÎÒâµØַдÈëÀֳɵÄÒªº¦Ö®Ò» ¡£


¶«É­¡¤(ÖйúÇø)¹Ù·½ÍøÕ¾

ͼ17 SmbCompressionDecompres¸³ÖµFinalUnCompressedSize


©¶´ÐÞ¸´½¨Òé


CVE-2020-0796ÊÇÄÚ´æÆÆ»µÂ©¶´£¬¾«ÐÄÀûÓÿɵ¼ÖÂÔ¶³Ì´úÂëÖ´ÐУ¬Í¬Ê±ÍøÂçÉÏÒѾ­·ºÆð¸Ã©¶´µÄµ±µØÌáȨÀûÓôúÂë ¡£ÔÚ´Ë£¬½¨ÒéÊÜÓ°Ïì°æ±¾WindowsÓû§¼°Ê±Æ¾¾Ý΢Èí¹Ù·½Â©¶´·À»¤Í¨¸æ¶Ô¸Ã©¶´½øÐзÀ»¤ ¡£


²Î¿¼Á´½Ó£º

1.https://fortiguard.com/encyclopedia/ips/48773

2.https://portal.msrc.microsoft.com/en-US/security-guidance/advisory/ADV200005

3.https://portal.msrc.microsoft.com/en-US/security-guidance/advisory/CVE-2020-0796

4.https://www.catalog.update.microsoft.com/Search.aspx?q=KB4551762

5.https://github.com/danigargu/CVE-2020-0796

6.https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-smb2/5606ad47-5ee0-437a-817e-70c366052962

7.https://docs.microsoft.com/en-us/windows-hardware/drivers/ddi/ntifs/nf-ntifs-rtldecompressbufferex2