พื้นหลัง
Blast เป็นเครือข่าย Ethereum Layer 2 ที่เปิดตัวโดย Pacman (Tieshun Roquerre หรือที่รู้จักในชื่อ Tieshun) ผู้ก่อตั้ง Blur เปิดตัว mainnet เมื่อวันที่ 29 กุมภาพันธ์ ปัจจุบันมีการให้คำมั่นสัญญาประมาณ 19,500 ETH และ 640,000 stETH บน Blast mainnet
โปรเจ็กต์ที่ถูกโจมตี Munchables เป็นโปรเจ็กต์ระดับพรีเมียมที่ชนะการแข่งขัน Bigbang ซึ่งจัดโดย Blast
เจ้าหน้าที่ Blast จะออกคะแนนธรรมดาให้กับผู้ใช้ที่จำนำ ETH บน Blast mainnet:
เพื่อสนับสนุนให้ผู้ใช้มีส่วนร่วมในโครงการ DeFi บนระบบนิเวศ Blast เจ้าหน้าที่ของ Blast จะเลือกโครงการคุณภาพสูงเพื่อรับคำแนะนำ และสนับสนุนให้ผู้ใช้ให้คำมั่นสัญญา ETH เป็นครั้งที่สองใน DeFi เพื่อรับคะแนนที่เพิ่มขึ้นเร็วขึ้นและคะแนนทอง ดังนั้นจึงมีค่อนข้างมาก ผู้ใช้เพียงไม่กี่รายให้คำมั่นสัญญา ETH บนเครือข่ายหลัก Blast ให้กับโครงการ DeFi ที่สร้างขึ้นใหม่
ความสมบูรณ์และความปลอดภัยของโครงการ DeFi เหล่านี้ยังไม่ได้รับการตรวจสอบ และสัญญาเหล่านี้มีข้อควรพิจารณาด้านความปลอดภัยเพียงพอที่จะปกป้องเงินหลายสิบล้านหรือหลายร้อยล้านดอลลาร์ของผู้ใช้หรือไม่
ภาพรวมกิจกรรม
ไม่ถึงหนึ่งเดือนหลังจากที่ Blast mainnet ออนไลน์ การโจมตี SSS Token (Super Sushi Samurai) เกิดขึ้นเมื่อวันที่ 21 มีนาคม 2024 มีข้อผิดพลาดลอจิกในการถ่ายโอนในสัญญา Token ซึ่งทำให้ผู้โจมตีสามารถเพิ่ม SSS Token ของ ระบุบัญชีที่ไม่มีความสมดุล ในที่สุดโครงการก็สูญเสียมากกว่า 1,310 ETH (ประมาณ 4.6 ล้านดอลลาร์)
น้อยกว่าหนึ่งสัปดาห์หลังจากการโจมตี SSS Token การโจมตีครั้งใหญ่อีกครั้งก็เกิดขึ้นที่ Blast โครงการ Munchables ถูกกวาดล้างโดยผู้โจมตีด้วย 17413.96 ETH รวมมูลค่าประมาณ 62.5 ล้านดอลลาร์สหรัฐ
ครึ่งชั่วโมงหลังจากเกิดธุรกรรมการโจมตี 73.49 WETH ในสัญญาโครงการก็ถูกแฮ็กเกอร์ขโมยไปโดยที่อยู่อื่น
ในขณะนี้ ยังมี 7276 WETH, 7758267 USDB และ 4 ETH เก็บไว้ในที่อยู่สัญญาของฝ่ายโครงการซึ่งจะตกไปอยู่ในมือของแฮกเกอร์เมื่อใดก็ได้ แฮกเกอร์มีอำนาจที่จะเอาเงินทั้งหมดของ ทั้งโครงการมูลค่ารวมประมาณ 97 ล้านเหรียญสหรัฐ มีความเสี่ยง
ทันทีหลังจากเหตุการณ์ดังกล่าว zachXBT นักสืบออนไลน์ชื่อดังของ X (Twitter) ชี้ให้เห็นว่าสาเหตุของการโจมตีครั้งนี้คือการจ้างแฮกเกอร์จากบางประเทศ
มาดูกันว่า แฮ็กเกอร์จากบางประเทศ โจมตีมูลค่าเกือบ 100 ล้านดอลลาร์ได้อย่างไร
การบูรณะในสถานที่
ผู้เสียหายพูดออกมา
[UTC+ 0 ] เมื่อเวลา 21:37 น. ของวันที่ 26 มีนาคม 2024 (5 นาทีหลังการโจมตี) Munchables โพสต์อย่างเป็นทางการบน X (Twitter) โดยระบุว่ากำลังถูกโจมตี
จากการสืบสวนของนักสืบออนไลน์ Zach ผู้โจมตีมาทำงานพัฒนาเกม เขาเป็นคนหยาบมากและดูเหมือนแฮ็กเกอร์ชาวจีนจริงๆ เราไล่เขาออกภายในหนึ่งเดือน เขายังพยายามให้เราจ้างหนึ่งในนั้นของเขา เพื่อนที่น่าจะเป็นแฮกเกอร์เหมือนกัน แฮกเกอร์
เนื่องจากการโจมตีนี้สร้างความเสียหายอย่างมากให้กับผู้ใช้ในชุมชน เราจึงเริ่มการสอบสวนออนไลน์ทันที เรามาดูรายละเอียดการโจมตีของ “แฮ็กเกอร์จากบางประเทศ” ในเชิงลึกกันดีกว่า
ฉากแรก
[UTC+ 0 ] เมื่อเวลา 21:32 น. ของวันที่ 26 มีนาคม 2024 เกิดการโจมตีที่เกี่ยวข้องกับ 17413.96 ETH เกิดขึ้น
เราสามารถเห็นธุรกรรมการโจมตีนี้ผ่าน Blastscan: https://blastscan.io/tx/0x9a7e4d16ed15b0367b8ad677eaf1db6a2a54663610696d69e1b4aa1a08f55c95
สัญญาที่เสียหาย (0x 29..1 F) เป็นสัญญาพร็อกซีที่เก็บเงินที่สัญญาไว้ของผู้ใช้ เราจะเห็นว่าผู้โจมตีเรียกใช้ฟังก์ชันปลดล็อคของสัญญาจำนำ ผ่านการตรวจสอบการอนุญาตทั้งหมด และโอนออกไป ETH ทั้งหมดใน สัญญาไปที่ที่อยู่ของผู้โจมตี 1 (0x 6 E..c 5)
ดูเหมือนว่าผู้โจมตีเรียกฟังก์ชันปลดล็อคที่มีพฤติกรรมคล้ายการถอนเงินและนำ ETH ส่วนใหญ่ไปจากสัญญาที่ถูกบุกรุก (0x 29..1 F)
ฝ่ายโครงการลืมล็อคห้องนิรภัยหรือไม่?
มีการตรวจสอบที่เกี่ยวข้องสองรายการสำหรับการปลดล็อคในสัญญาที่เสียหาย (0x 29..1 F) มาดูทีละรายการ
อันดับแรก เราพบว่าในระหว่างกระบวนการตรวจสอบสิทธิ์ มีการเรียกวิธีการ isRegistered ของสัญญา (0x 16..A 0) เพื่อตรวจสอบว่า msg.sender ปัจจุบันคือที่อยู่ของแฮ็กเกอร์ 1 (0x 6 E..c 5) ลงทะเบียนแล้ว:
คำตอบคือ ผ่านการตรวจสอบ
สิ่งนี้เกี่ยวข้องกับสัญญา (0x 16..A 0) และสัญญาเชิงตรรกะล่าสุดที่เกี่ยวข้อง (0x e 7..f 1)
[UTC+ 0 ] เมื่อเวลา 08:39 น. ของวันที่ 24 มีนาคม 2024 (2 วันก่อนการโจมตี) สัญญาเชิงตรรกะที่สอดคล้องกับสัญญา (0x 16..A 0) ได้รับการอัปเกรด
ธุรกรรมการอัพเกรดสัญญาเชิงตรรกะ:
https://blastscan.io/tx/0x9c431e09a80d2942319853ccfdaae24c5de23cedfcef0022815fdae42a7e2ab6
สัญญาตรรกะได้รับการอัพเดตเป็น 0x e 7..f 1
สามารถดูที่อยู่สัญญาเชิงตรรกะดั้งเดิมได้ที่นี่ ซึ่งก็คือ 0x 9 e..CD
https://blastscan.io/tx/0x7ad050d84c89833aa1398fb8e5d179ddfae6d48e8ce964f6d5b71484cc06d003
ในเวลานี้ เราสงสัยว่าแฮ็กเกอร์ได้อัปเดตสัญญาการใช้งานลอจิกของสัญญาพร็อกซีและเปลี่ยน 0x 9 e..CD ให้เป็น 0x e 7..f 1 ที่เป็นอันตราย โดยทำการข้ามสิทธิ์การตรวจสอบให้เสร็จสิ้น
จริงเหรอ?
ใน Web3.0 คุณไม่จำเป็นต้องเดาหรือฟังผู้อื่น คุณเพียงต้องเชี่ยวชาญเทคโนโลยีเพื่อรับคำตอบด้วยตัวเอง
เมื่อเปรียบเทียบสองสัญญา (ไม่ใช่สัญญาโอเพ่นซอร์ส) มีความแตกต่างที่ชัดเจนระหว่างสัญญา 0x 9 e..CD ดั้งเดิมและ 0x e 7..f 1 ที่อัปเดต:
ส่วนฟังก์ชันเตรียมใช้งานของ 0x e 7..f 1 ถูกนำไปใช้ดังนี้:
ส่วนฟังก์ชันการเริ่มต้นของ 0x 9 e..CD จะถูกนำไปใช้ดังนี้:
จะเห็นได้ว่าผู้โจมตีตั้งค่าที่อยู่ของผู้โจมตี (0x 6 e..c 5) เป็นการลงทะเบียนในสัญญาเชิงตรรกะดั้งเดิม (0x 9 e..CD) และยังมีที่อยู่ของผู้โจมตีอีกสองแห่ง 0x c 5 ..0 d, 0x bf..87 จะถูกลงทะเบียนด้วย และฟิลด์ 0 ของพวกมันจะถูกตั้งค่าเป็นเวลาบล็อกระหว่างการกำหนดค่าเริ่มต้น การใช้ฟิลด์ 0 จะอธิบายในภายหลัง
ในความเป็นจริง ตรงกันข้ามกับสิ่งที่เราคาดเดา สัญญาตรรกะที่แท้จริงกับประตูหลังมีอยู่ตั้งแต่ต้น และการอัปเดตที่ตามมาก็เป็นเรื่องปกติ!
เดี๋ยวก่อน การอัปเดตนี้ปรากฏเมื่อเวลา 08:39 น. ของวันที่ 24 มีนาคม 2024 [UTC+ 0] (2 วันก่อนการโจมตี) นั่นคือก่อนเหตุการณ์นี้สัญญาเชิงตรรกะได้กลายเป็นสัญญาที่ไม่มีแบ็คดอร์ เพราะเหตุใด ผู้โจมตียังสามารถดำเนินการให้เสร็จสิ้นได้หรือไม่ การโจมตี?
นี่เป็นเพราะการเรียกผู้รับมอบสิทธิ์ ดังนั้นการอัปเดตสถานะการจัดเก็บจริงจึงอยู่ในสัญญา (0x 16..A 0) ซึ่งส่งผลให้แม้ว่าสัญญาตรรกะจะได้รับการอัปเดตในภายหลังเป็นสัญญาตรรกะโดยไม่มีแบ็คดอร์ 0x e 7.. f 1 ช่องที่เปลี่ยนแปลงในสัญญา (0x 16..A 0) จะยังไม่ได้รับการกู้คืน
มาตรวจสอบกัน:
อย่างที่คุณเห็น ช่องที่สอดคล้องกันในสัญญา (0x 16....A 0) มีค่า
ซึ่งช่วยให้ผู้โจมตีสามารถผ่านการตรวจสอบเมธอด isRegistered ได้:
ผู้โจมตีเปลี่ยนสัญญาลับๆ ให้เป็นสัญญาปกติในภายหลังเพื่อซ่อนความจริงที่ว่ามีการติดตั้งประตูลับไว้แล้ว
นอกจากนี้ กระบวนการปลดล็อคยังเกี่ยวข้องกับการตรวจสอบครั้งที่สองด้วย:
ในส่วนของการตรวจสอบเวลาล็อค ส่วนนี้คือเพื่อให้แน่ใจว่าทรัพย์สินที่ถูกล็อคจะไม่ถูกโอนก่อนหมดอายุ
ผู้โจมตีต้องแน่ใจว่าเวลาบล็อกเมื่อเรียกใช้การปลดล็อคนั้นมากกว่าเวลาหมดอายุของการล็อคที่ต้องการ (ฟิลด์ 3)
การตรวจสอบส่วนนี้เกี่ยวข้องกับสัญญาที่เสียหาย (0x 29..1 F) และสัญญาเชิงตรรกะที่เกี่ยวข้อง 0x f 5..cd
ในการทำธุรกรรมเวลา 11:54 น. ของวันที่ 21 มีนาคม 2024 [UTC+ 0] (5 วันก่อนการโจมตี)
https://blastscan.io/tx/0x3d08f2fcfe51cf5758f4e9ba057c51543b0ff386ba53e0b4f267850871b88170
เราจะเห็นว่าสัญญาเชิงตรรกะดั้งเดิมของสัญญาที่เสียหาย (0x 29..1 F) คือ 0x 91..11 และเพียงสี่นาทีต่อมาที่
https://blastscan.io/tx/0xea1d9c0d8de4280b538b6fe6dbc3636602075184651dfeb837cb03f8a19ffc4f
อัปเกรดเป็น 0x f 5..cd
นอกจากนี้เรายังเปรียบเทียบสัญญาทั้งสองฉบับและพบว่าผู้โจมตียังใช้กลอุบายในฟังก์ชันเริ่มต้นเช่นเมื่อก่อน
การใช้งานฟังก์ชันเริ่มต้นบางส่วนของ 0x f 5..cd:
การใช้งานฟังก์ชันเริ่มต้นบางส่วนของ 0x 91..11:
จะเห็นได้ว่าเห็นได้ชัดว่ามีการใช้วิธีเดิมอีกครั้งเพื่อยุ่งเกี่ยวกับจำนวน ETH และเวลาปลดล็อคแล้วแทนที่ด้วยสัญญาปกติเพื่อหลอกลวงผู้อื่น เมื่อทีมงานโครงการและนักวิจัยด้านความปลอดภัยกำลังแก้ไขจุดบกพร่องทั้งหมด สัญญาเชิงตรรกะที่เห็นเป็นเรื่องปกติ และเนื่องจากสัญญาทั้งหมดเป็นสัญญาที่ไม่ใช่โอเพ่นซอร์ส จึงยากยิ่งขึ้นที่จะเห็นแก่นแท้ของปัญหาอย่างชัดเจน
จนถึงตอนนี้ เราเข้าใจธุรกรรมนี้ที่เกี่ยวข้องกับ 17413 ETH และผู้โจมตีทำได้อย่างไร แต่มีข้อมูลมากมายที่อยู่เบื้องหลังเหตุการณ์นี้หรือไม่?
จากการวิเคราะห์ข้างต้น เราพบว่าแฮ็กเกอร์สร้างที่อยู่ 3 รายการไว้ในสัญญา:
0x 6 e..c 5 (ที่อยู่ของผู้โจมตี 1)
0x c 5..0 d (ที่อยู่ของผู้โจมตี 2)
0x bf..87 (ที่อยู่ของผู้โจมตี 3)
อย่างไรก็ตาม เราเห็นเพียง 0x 6 e..c 5 ในธุรกรรมการโจมตีที่เราพบด้านบน ที่อยู่อีก 2 แห่งทำอะไร และความลับอะไรที่ซ่อนอยู่ในที่อยู่ (0), _dodoApproveAddress และ _uniswapV3Factorty
ฉากที่สอง
ก่อนอื่นเรามาดูที่อยู่ของผู้โจมตี 3 (0x bf..87) ซึ่งขโมย 73.49 WETH ด้วยวิธีการเดียวกัน:
https://blastscan.io/tx/0xfc7bfbc38662b659bf6af032bf20ef224de0ef20a4fd8418db87f78f9370f233
และโจมตีที่อยู่แหล่งที่มาของก๊าซ (0x 97..de) และจัดเตรียมค่าธรรมเนียมการจัดการให้กับทั้ง 0x c 5..0 d (ที่อยู่ของผู้โจมตี 2) และ 0x bf..87 (ที่อยู่ของผู้โจมตี 3)
แหล่งที่มาของ 0.1 ETH ที่โจมตีที่อยู่แหล่งที่มาของก๊าซ (0x 97..de) มาจาก owlto.finance (สะพานข้ามสายโซ่)
0x c 5..0 d (ที่อยู่ของผู้โจมตี 2) ไม่ได้ทำการโจมตีใดๆ หลังจากได้รับค่าธรรมเนียมการจัดการ แต่จริงๆ แล้วมันเป็นแผนที่ซ่อนอยู่ มาดูกันต่อไป
ตามธุรกรรมการช่วยเหลืออย่างเป็นทางการ ที่อยู่เดิมของสัญญาที่เสียหาย (0x 29..1 F) ไม่ใช่แค่ 73.49 WETH เท่านั้น จนกระทั่งสิ้นสุดการโจมตี ยังคงมี 7276.5 WETH และ 7758267 USDB
ข้อตกลงการกู้ภัย:
https://blastscan.io/tx/0x1969f10af9d0d8f80ee3e3c88d358a6f668a7bf4da6e598e5be7a3407dc6d5bb
ผู้โจมตีวางแผนที่จะขโมยทรัพย์สินเหล่านี้ในตอนแรก คุณจะเห็นว่า เดิมทีที่อยู่ 0x c 5..0 d (ที่อยู่ของผู้โจมตี 2) ถูกใช้เพื่อขโมย USDB
_dodoApproveAddress ที่นี่คือ 0x000000000000000000000000430000000000000000000000000000000000003
คือที่อยู่ของ usdb
0x bf..87 (ที่อยู่ของผู้โจมตี 3) ที่อยู่นี้ใช้เพื่อขโมยข้อมูล:
_uniswap V3 Factory ที่นี่คือ 0x000000000000000000000000430000000000000000000000000000000000004
คือที่อยู่ของเวท
และ 0x 6 e..c 5 (ที่อยู่ของผู้โจมตี 1) มีหน้าที่ขโมยที่อยู่ (0) ซึ่งเป็นสินทรัพย์ดั้งเดิม ETH
ด้วยการตั้งค่าฟิลด์ 0 ผู้โจมตีสามารถขโมยทรัพย์สินที่เกี่ยวข้องผ่านตรรกะต่อไปนี้:
คำถาม
เหตุใดผู้โจมตีจึงไม่ขโมยทรัพย์สินทั้งหมด
ตามทฤษฎีแล้วเขาสามารถขโมยทรัพย์สินทั้งหมดได้ ซึ่งก็คือ WETH และ USDB ที่เหลือ
0x bf..87 (ที่อยู่ของผู้โจมตี 3) ขโมยเพียง 73.49 WETH 0x bf..87 (ที่อยู่ของผู้โจมตี 3) สามารถนำ 7350 WETH ไปทั้งหมดได้จริงหรือคุณสามารถใช้ 0x c 5..0 d (ที่อยู่ของผู้โจมตี 2) ได้ ไปทั้งหมด 7758267 USDB ทำไมมันหยุดหลังจากรับ WETH เพียงเล็กน้อย เราไม่รู้ อาจต้องใช้นักสืบลูกโซ่ที่มีชื่อเสียงเพื่อดำเนินการสอบสวนภายในเชิงลึก
https://blastscan.io/tx/0xfc7bfbc38662b659bf6af032bf20ef224de0ef20a4fd8418db87f78f9370f233
เหตุใดผู้โจมตีจึงไม่โอน 17413 ETH ไปยัง Ethereum mainnet
ดังที่เราทุกคนทราบกันดีอยู่แล้วว่าเป็นไปได้ที่เครือข่ายหลักของ Blast จะสามารถสกัดกั้น ETH เหล่านี้ผ่านวิธีการแบบรวมศูนย์และปล่อยให้มันอยู่ที่นี่อย่างถาวรโดยไม่ทำให้ผู้ใช้สูญเสียจำนวนมาก อย่างไรก็ตาม เมื่อ ETH เหล่านี้เข้าสู่เครือข่ายหลักของ Ethereum จะไม่มีทางสกัดกั้นได้ มัน.
เราประเมินสะพานข้ามสายโซ่ Blast ในปัจจุบัน ไม่มีการจำกัดจำนวนสะพานข้ามสายโซ่อย่างเป็นทางการ แต่ต้องใช้เวลา 14 วันจึงจะออก ซึ่งเพียงพอสำหรับเจ้าหน้าที่ Blast ในการเตรียมแผนการสกัดกั้น
Cross-chain Bridge ของบุคคลที่สามสามารถให้เครดิตได้ในเวลาใกล้เคียงเรียลไทม์เช่นเดียวกับแหล่งที่มาของค่าธรรมเนียมของผู้โจมตีและสามารถดำเนินการ Cross-Chain ให้เสร็จสิ้นได้อย่างรวดเร็ว เหตุใดผู้โจมตีจึงไม่ Cross-Chain ในทันที
ในความเป็นจริง ผู้โจมตีดำเนินการข้ามเครือข่ายในช่วงแรก (ภายใน 2 นาทีของการโจมตี):
https://blastscan.io/tx/0x10cf2f2b884549979a3a1dd912287256229458ef40d56df61738d6ea7d9d198f
นอกจากนี้ มันใช้เวลา 20 วินาทีกว่าที่เงินจะมาถึงเครือข่ายหลักของ Ethereum ตามทฤษฎี ผู้โจมตีสามารถดำเนินการข้ามเครือข่ายและถ่ายโอน ETH จำนวนมากข้ามเครือข่ายก่อนที่สะพานข้ามเครือข่ายจะสามารถแทรกแซงได้ด้วยตนเอง
สำหรับสาเหตุที่สามารถเป็นได้เพียง 3 ETH ต่อครั้ง เหตุผลก็คือขีดจำกัดสภาพคล่องของ cross-chain bridge ตั้งแต่ Blast ถึง ETH:
สะพานข้ามสายโซ่อีกอันที่รองรับ Blast รองรับแม้แต่น้อย:
หลังจากการทำธุรกรรมข้ามสายโซ่นี้ผู้โจมตีไม่ได้ดำเนินการข้ามสายโซ่อื่น ๆ ต่อไป เราไม่ทราบสาเหตุ ดูเหมือนว่า แฮ็กเกอร์จากบางประเทศ ไม่ได้เตรียมการอย่างเพียงพอสำหรับการถอนเงินจาก Blast
เกิดอะไรขึ้นหลังการโจมตี
จากคำติชมของผู้ใช้ชุมชน Nearisbuilding เขาพบข้อมูลประจำตัวของผู้โจมตีเพิ่มเติม และพบวิธีที่จะกระตุ้นให้ผู้โจมตีคืนเงิน
https://twitter.com/Nearisbuilding/status/1772812190673756548
ในท้ายที่สุด ด้วยความสนใจและความพยายามของชุมชนการเข้ารหัส แฮ็กเกอร์จากประเทศใดประเทศหนึ่ง อาจเป็นเพราะเขากลัวที่จะเปิดเผยตัวตนของเขา จึงได้มอบคีย์ส่วนตัวของผู้โจมตีทั้งสามรายที่อยู่ข้างต้นให้กับฝ่ายโครงการและส่งคืนทั้งหมด กองทุน ฝ่ายโครงการยังดำเนินธุรกรรมช่วยเหลือ โอนเงินทั้งหมดจากสัญญาที่เสียหายไปยังสัญญาหลายลายเซ็นเพื่อความปลอดภัย