ข้ามไปยังเนื้อหา

จำนวนทศนิยมของออราเคิลไม่ตรงกัน

ความคลาดเคลื่อนของทศนิยมคือการใช้สเกลหน่วยผิดกับคำตอบออราเคิล จำนวนโทเค็น อัตรา wrapper หรือค่าโปรโตคอล จนการกู้ การสร้าง การแลกคืน และการชำระบัญชีผิดหลายลำดับขนาด

อัปเดต

จัดทำขึ้นเพื่อการศึกษาเท่านั้น ไม่ใช่คำแนะนำการลงทุน การลงทุนอาจทำให้สูญเสียเงินลงทุนได้

คำตอบโดยตรง

จำนวนทศนิยมของออราเคิลไม่ตรงกันเมื่อสัญญาตีความจำนวนเต็มดิบด้วยเลขชี้กำลังของหน่วย ทิศทางราคา หรือสเกลภายในที่ผิด จำนวนทศนิยมของฟีด โทเค็น และโทเค็นอ้างอิง สเกลอัตราแลกเปลี่ยนของ wrapper หรือ share ตลอดจนรูปแบบ WAD หรือ RAY ของโปรโตคอล เป็นคนละค่าและไม่ขึ้นต่อกัน การที่ frontend แสดงค่าดูถูกต้องไม่ได้พิสูจน์ว่าสัญญาผู้ใช้ข้อมูลคำนวณแบบเดียวกัน

สำหรับจำนวนโทเค็นฐานดิบ A_raw ที่มีทศนิยม d_t และคำตอบฟีดค่าบวก P_raw ซึ่งเสนอราคาหนึ่งโทเค็นฐานเป็นโทเค็นอ้างอิงที่มีทศนิยม d_p จำนวนโทเค็นอ้างอิงดิบที่มีทศนิยม d_q คือ V_raw = round(A_raw * P_raw * 10^d_q / 10^(d_t + d_p)) สูตรนี้ใช้ได้เฉพาะทิศทางราคาที่ระบุ และต้องตรวจสอบฟีด หน่วย ชนิดข้อมูล และกฎการปัดเศษก่อน ค่าที่อะแดปเตอร์ปรับหน่วยแล้วต้องไม่ถูกปรับซ้ำ

ERC-20 decimals() เป็นข้อมูลประกอบเพื่อการแสดงผลที่ไม่บังคับ ไม่ใช่หลักประกันว่าโทเค็นทุกชนิดใช้ 18 ทศนิยม ฟังก์ชัน decimals() ของฟีดอธิบายคำตอบของฟีดนั้น ไม่ใช่สเกลของโทเค็นหรือโปรโตคอล เลขคณิตแบบตรวจสอบอาจหยุด overflow ด้วยการ revert แต่ตรวจไม่พบสูตรที่มีมิติผิด และอาจทำให้เกิด denial of service หากผลคูณระหว่างทาง overflow ทั้งที่ผลลัพธ์สุดท้ายยังแสดงได้

กลไกการทำงาน

  1. ระบุเชน บล็อก สัญญาผู้ใช้ข้อมูล อะแดปเตอร์ พร็อกซีและตัวรวมผลของฟีด โทเค็นหรือ vault เวอร์ชัน compiler และไลบรารีคณิตศาสตร์ รวมถึงสถานะการอัปเกรด
  2. จัดทำรายการจำนวนเต็มทุกค่าพร้อมชนิดและหน่วย ได้แก่ จำนวนโทเค็นดิบ ทศนิยมโทเค็น คำตอบฟีดแบบมีเครื่องหมาย ทศนิยมฟีด ทิศทางสินทรัพย์ฐานและอ้างอิง อัตรา wrapper หรือ share สเกลภายในโปรโตคอล และทศนิยมโทเค็นผลลัพธ์
  3. ตรวจสอบแหล่งก่อนแปลงค่า ได้แก่ ที่อยู่และทิศทางที่ถูกต้อง คำตอบค่าบวก เวลาและสถานะ อายุและช่วงที่ยอมรับได้ ความหมายของแหล่งสำรอง และกฎระยะผ่อนผันของ sequencer L2 เมื่อเกี่ยวข้อง
  4. สร้างสูตรที่มีมิติเดียวจากหน่วยดิบของข้อมูลเข้าไปยังหน่วยดิบของผลลัพธ์ แยกกรณีเพิ่มและลดสเกลอย่างชัดเจน จำกัดเลขชี้กำลังฐานสิบทุกค่า และปรับหน่วยแต่ละองค์ประกอบเพียงครั้งเดียว
  5. ใช้การคูณหารแบบเต็มความแม่นยำที่พิสูจน์แล้ว หรือการตัดทอนร่วมที่มีขอบเขต หลีกเลี่ยงการสูญเสียเศษจากหารก่อนคูณ ผลคูณระหว่างทาง overflow การวนค่าจากเลขคณิตที่ไม่ตรวจสอบ และการ cast เครื่องหมายหรือขนาดที่ไม่ปลอดภัย
  6. กำหนดการปัดลง ปัดขึ้น หรือใกล้ที่สุดสำหรับแต่ละการดำเนินการทางเศรษฐกิจ หลักประกัน หนี้ การกู้ การสร้าง การแลกคืน ค่าธรรมเนียม การชำระบัญชี และการแปลง share ของ vault อาจต้องใช้ทิศทางอนุรักษนิยมต่างกัน
  7. ทดสอบเวกเตอร์อ้างอิงและคุณสมบัติกับจำนวนสุดขั้ว ชุดทศนิยม ราคากลับด้าน ฟีดผสม คำตอบศูนย์ ติดลบ และล้าสมัย การอัปเกรด และ dust กระทบยอดผลบนเชนกับแบบจำลองความแม่นยำสูงที่เป็นอิสระ และจำกัดความเสี่ยงที่ได้รับผลกระทบ

การปรับหน่วยคือการวิเคราะห์มิติ ไม่ใช่การจัดรูปแบบ BTC/USD และ USD/BTC ต้องใช้สูตรกลับด้าน การเปลี่ยนป้ายชื่อไม่ได้กลับราคา ฟีดผสมต้องระบุสเกลและเวลาของแต่ละองค์ประกอบ การหารจำนวนเต็มของ Solidity ตัดเศษเข้าหาศูนย์ การจัดรูปสมการที่เท่ากันทางพีชคณิตจึงอาจให้ผลบนเชนต่างกัน mulDiv แบบเต็มความแม่นยำแก้ปัญหาขนาดของผลคูณระหว่างทาง แต่ผู้เรียกยังต้องส่งตัวตั้ง ตัวหาร หน่วย ขอบเขต และทิศทางปัดเศษให้ถูกต้อง

ตัวอย่างคำนวณ

  • ทศนิยม 8 เทียบกับ 18 หลัก ฟีด BTC/USD คืนค่า 6,000,000,000,000 โดยมี d_p = 8 ราคาจึงเป็น 60,000 USD/BTC หากตีความคำตอบดิบว่ามี 18 ทศนิยม จะได้ 0.000006 USD/BTC ซึ่งประเมินต่ำไป 10^10 ไม่ใช่ 10^9 การปรับราคาเป็น WAD ให้ค่า 6,000,000,000,000 * 10^(18 - 8) = 60,000,000,000,000,000,000,000
  • หน่วยของจำนวน ราคา และผลลัพธ์ A_raw = 2,500,000 แทนโทเค็น 2.5 หน่วยที่ d_t = 6 ส่วน P_raw = 200,000,000 แทนโทเค็นอ้างอิง 2 หน่วยที่ d_p = 8 สำหรับมูลค่าอ้างอิงภายใน 18 ทศนิยม 2,500,000 * 200,000,000 * 10^18 / 10^(6 + 8) = 5,000,000,000,000,000,000 หรือ 5 quote tokens หากละตัวหารของโทเค็น จะประเมินสถานะสูงเกินจริง 10^6
  • ราคากลับด้านและการตัดเศษ ETH/USD ที่สเกล WAD คือ 2,000 * 10^18 ส่วน USD/ETH ที่สเกลเดียวกันคือ floor(10^36 / (2,000 * 10^18)) = 500,000,000,000,000 หรือ 0.0005 ETH/USD อีกกรณีหนึ่ง เมื่อ A_raw = 999,999 d_t = 6 และราคา 2 * 10^18 การคูณหารแบบเต็มความแม่นยำให้ 1,999,998,000,000,000,000 แต่หากหารจำนวนด้วย 10^6 ก่อนจะได้ 0 และสูญเสียมูลค่าทั้งหมด
  • ผลคูณระหว่างทาง overflow และการปัดเศษ กำหนด x = 2^200 y = 2^100 และตัวหาร 2^100 ผลลัพธ์ที่ถูกต้องคือ 2^200 ซึ่งอยู่ใน uint256 แต่ x * y = 2^300 ไม่อยู่ในขอบเขต การคูณแบบตรวจสอบจะ revert ส่วนแบบไม่ตรวจสอบจะวนค่า ขณะที่ mulDiv แบบเต็มความแม่นยำคืน 2^200 การหารจำนวนเต็ม 5 / 2 ปัดลงเป็น 2 แต่กฎปัดขึ้นให้ 3 การปัดเศษจึงเป็นส่วนหนึ่งของ invariant ทางเศรษฐกิจ

ความเสี่ยง

  • ใช้เชน ฟีด พร็อกซี อะแดปเตอร์ โทเค็น vault หรือที่อยู่สัญญาผู้ใช้ข้อมูลผิด
  • กลับทิศสินทรัพย์ฐานและอ้างอิงโดยไม่แปลงเป็นราคากลับด้าน
  • สมมติว่าโทเค็นมี 18 ทศนิยม หรือข้อมูลประกอบที่ไม่บังคับไม่มีหรือผิด
  • สมมติว่าฟีดมี 8 ทศนิยมแทนการอ่านและยึดค่าจริง
  • สับสนระหว่างทศนิยมของโทเค็นอ้างอิงกับสเกล WAD RAY ตลาด หรือบัญชีของโปรโตคอล
  • ละทศนิยมของ wrapper share ดัชนี หรืออัตราแลกเปลี่ยน
  • ใช้ตัวคูณสเกลซ้ำหลังอะแดปเตอร์ปรับหน่วยแล้ว
  • ละตัวคูณสเกลหรือตัวหารที่จำเป็น
  • cast คำตอบแบบมีเครื่องหมายเป็นไม่มีเครื่องหมายก่อนตรวจสอบว่าค่าเป็นบวก
  • ยอมรับผลฟีดที่เป็นศูนย์ ล้าสมัย ไม่สมบูรณ์ ถูกจำกัด หรือไม่ถูกต้อง
  • เลขชี้กำลังทศนิยมหรือการคำนวณเลขยกกำลังฐานสิบ underflow overflow หรือเกินขอบเขต
  • ผลคูณระหว่างทาง overflow แม้ผลหารสุดท้ายจะอยู่ในขอบเขต
  • เลขคณิตที่ไม่ตรวจสอบ bit shift หรือการลดขนาดแบบชัดแจ้งทำให้ค่าหมุนวนหรือถูกตัดโดยไม่รู้ตัว
  • การหารก่อนคูณทำลายความแม่นยำหรือทำให้ dust กลายเป็นศูนย์
  • ใช้การปัดลง ปัดขึ้น หรือใกล้ที่สุดผิดกับการดำเนินการทางเศรษฐกิจ
  • การแปลงซ้ำสะสมการสูญเสียความแม่นยำหรือการรั่วไหลของมูลค่าอย่างเป็นระบบ
  • เปรียบเทียบราคา เพดาน อัตราส่วน เปอร์เซ็นต์ basis point WAD และ RAY ในหน่วยต่างกัน
  • การอัปเกรดฟีด โทเค็น พร็อกซี อะแดปเตอร์ หรือ vault ทำให้สมมติฐานทศนิยมที่ cache ไว้ใช้ไม่ได้
  • การจัดรูปแบบของ frontend กระเป๋า RPC หรือ indexer ซ่อนการคำนวณบนเชนที่ต่างกัน
  • การประเมินผิดขยายผลต่อการกู้ การสร้าง การแลกคืน การชำระบัญชี เพดาน หนี้เสีย หรือการออก share ที่ไม่เป็นธรรม

ความเข้าใจผิดที่พบบ่อย

  • “โทเค็น ERC-20 ทุกตัวใช้ 18 ทศนิยม” เมธอดข้อมูลประกอบ ERC-20 ไม่บังคับ และสินทรัพย์ที่ใช้งานจริงมีค่าและพฤติกรรมต่างกัน
  • “ฟีดราคา USD ทุกตัวใช้ 8 ทศนิยม” ความละเอียดของฟีดเป็นคุณสมบัติของอินเทอร์เฟซใน deployment ที่ระบุ ต้องอ่านและบันทึกเวอร์ชัน
  • “จำนวนเต็มดิบที่มากพิสูจน์ว่ามีการบิดเบือน” ขนาดดิบไม่มีความหมายหากไม่ทราบหน่วย ทิศทาง ทศนิยม เวลา และสเกลผู้ใช้ข้อมูล
  • “Solidity 0.8 ทำให้การปรับสเกลถูกต้อง” การตรวจ overflow อาจ revert แต่ไม่แก้หน่วยผิด การตัดเศษ การ cast หรือนโยบายปัดเศษ
  • “คูณก่อนหารหรือเพิ่มทศนิยมย่อมเพิ่มความแม่นยำเสมอ” อาจทำให้ overflow ปรับสเกลซ้ำ หรือคงหน่วยผิด เลขคณิตเต็มความแม่นยำยังต้องมีสูตรถูกต้อง

หัวข้อที่เกี่ยวข้อง

แหล่งที่มา

  • Data Feeds API Reference - Chainlink Documentation (เข้าถึงเมื่อ: 2026-08-13)
  • Chainlink Data Feeds - Chainlink Documentation (เข้าถึงเมื่อ: 2026-08-13)
  • ERC-20: Token Standard - Ethereum Improvement Proposals (เข้าถึงเมื่อ: 2026-08-13)
  • Types - Solidity Documentation (เข้าถึงเมื่อ: 2026-08-13)
  • Expressions and Control Structures - Solidity Documentation (เข้าถึงเมื่อ: 2026-08-13)
  • Utils - OpenZeppelin Contracts Documentation (เข้าถึงเมื่อ: 2026-08-13)
  • Oracles - Aave Protocol Documentation (เข้าถึงเมื่อ: 2026-08-13)
  • Compound v2 Price Feed - Compound Documentation (เข้าถึงเมื่อ: 2026-08-13)
การนำทาง

ค้นหาในวิกิ...