1 คะแนน โดย GN⁺ 2024-10-17 | 2 ความคิดเห็น | แชร์ทาง WhatsApp
  • ผลการรัน NPU benchmark บน SoC แบบ Arm ของ Qualcomm ใน Microsoft Surface Pro 11th Edition พบว่าค่าประมวลผลที่วัดได้ต่ำกว่าประสิทธิภาพเร่งความเร็วที่ Windows AI PC โฆษณาไว้อย่างมาก
  • การทดสอบถูกจัดขึ้นโดยใช้ Onnx Runtime และตัวให้บริการการรัน Qualcomm QNN เพื่อรันงาน MatMul ขนาดใหญ่ ที่มีลักษณะใกล้เคียงกับเลเยอร์ที่กินต้นทุนสูงในโมเดลตระกูล transformer
  • ในตัวอย่างผลลัพธ์ CPU ทำได้ 821 Gigaops/s, ส่วน NPU ทำได้ 225 Gigaops/s ในคอนฟิกแบบ quantization ที่มีอินพุต/เอาต์พุตเป็น float และ 573 Gigaops/s ในคอนฟิกที่ใช้อินพุต/เอาต์พุตแบบ 8-bit ด้วย
  • ค่า 573 Gigaops/s ของ NPU คิดเป็นเพียง 1.3% ของตัวเลข 45 Teraops/s ในสื่อการตลาดของ Microsoft Surface Pro 11th Edition และเมื่อรันโมเดลเดียวกันบน Nvidia Geforce RTX 4080 Laptop GPU จะได้ 3.2ms หรือ 2,160 Gigaops/s
  • ผลลัพธ์ปัจจุบันอ้างอิง ณ วันที่ 2 ตุลาคม 2024 และแม้ยังคาดหวังได้ว่าซอฟต์แวร์ เฟรมเวิร์ก และไดรเวอร์อาจช่วยลด latency ลงได้ในอนาคต แต่ใน benchmark นี้ CPU ยังเร็วกว่า NPU

จุดประสงค์ของ benchmark Qualcomm NPU บน Surface

  • Microsoft ทำตลาด Surface แท็บเล็ตที่ใช้ SoC แบบ Arm ของ Qualcomm ในฐานะ AI PC บน Windows โดยโปรโมตว่าสามารถรันโมเดลแมชชีนเลิร์นนิงได้เร็วและมีประสิทธิภาพมากขึ้น
  • Useful Sensors มองบวกต่อฮาร์ดแวร์ Qualcomm และ NPU และได้ลงเวลาและทรัพยากรเพื่อนำแอป third-party ของตนมา port ลงแพลตฟอร์มนี้
  • เนื่องจากยังมีตัวอย่างโค้ดหรือ benchmark ไม่มากนักที่แสดงให้นักพัฒนาภายนอกเห็นว่าจะทำอย่างไรให้ได้ผลลัพธ์ที่เร็ว ผู้พัฒนาจึงเผยแพร่ประสิทธิภาพที่สังเกตได้จริงในรูปแบบโปรเจกต์อิสระขนาดเล็ก
  • ประสิทธิภาพที่วัดได้ต่ำกว่าคาดมาก และแม้จะเคยเห็นฮาร์ดแวร์ชุดเดียวกันทำงานได้มีประสิทธิภาพบนแพลตฟอร์มอื่นอย่าง Android จึงยังเปิดไว้สำหรับความเป็นไปได้ที่จะปรับปรุงได้ผ่านการเปลี่ยนแปลงด้านแอปพลิเคชัน เฟรมเวิร์ก และไดรเวอร์ในอนาคต

สภาพแวดล้อมการรันและข้อจำกัดในการติดตั้ง

  • การทดสอบใช้สคริปต์ Python บน Windows
    • ณ วันที่ 2 ตุลาคม 2024 Python จาก Microsoft Store ยังไม่รองรับสถาปัตยกรรม Arm จึงไม่เหมาะกับการรันแพ็กเกจที่จำเป็นต่อการเข้าถึง Qualcomm NPU
    • ในผลลัพธ์นี้ใช้ ไฟล์ติดตั้ง Python 3.11.9 Arm64
  • ยังไม่มีแพ็กเกจ Onnx ที่ build ไว้ล่วงหน้าสำหรับ Windows on Arm จึงต้องใช้ CMake และคอมไพเลอร์ของ Visual Studio
    • ติดตั้ง CMake ด้วย winget install cmake
    • Visual Studio ใช้ Visual Studio Community Edition และเลือก workload Desktop C++ Development ตอนติดตั้ง
  • ติดตั้งแพ็กเกจ Python ในโฟลเดอร์รีโพด้วย py -m pip install -r requirements.txt
    • Onnx branch เป็นเวอร์ชันที่ backport การแก้ไขการคอมไพล์ py launcher อย่างเป็นทางการลงใน Onnx 1.16
    • Qualcomm Onnx Runtime ใช้คอมบิเนชันนี้เพราะ Onnx รุ่นใหม่กว่าจะขึ้นข้อผิดพลาด Unsupported model IR version
    • แพ็กเกจ Qualcomm Onnx Runtime ใช้ nightly build

การรัน benchmark และการตีความผลลัพธ์

  • รัน benchmark ด้วย py benchmark_matmul.py
  • Onnx Runtime จะแสดง log จำนวนมากระหว่างการรันช่วงแรก
    • ตัวอย่างเช่น จะมีข้อความจาก cpuinfo ว่าไม่รู้จักรุ่นชิป Snapdragon(R) X 12-core X1E80100 @ 3.40 GHz
    • ยังมี log ของขั้นตอนสรุปกราฟและขั้นตอนเสร็จสิ้นด้วย
  • ผล benchmark จริงจะแสดงตอนท้าย
    • NPU quantized compute, float I/O accuracy difference is 0.0100
    • NPU quantized compute and I/O accuracy difference is 0.0060
    • CPU took 8.42ms, 821,141,860,688 ops per second
    • NPU (quantized compute, float I/O) took 30.63ms, 225,667,671,183 ops per second
    • NPU (quantized compute and I/O) took 12.05ms, 573,475,650,364 ops per second
  • สองบรรทัดแรกแสดง ค่าความต่างด้านความแม่นยำ เพื่อตรวจว่าผลลัพธ์เชิงตัวเลขของ CPU และ NPU สอดคล้องกันหรือไม่
  • สามบรรทัดสุดท้ายแสดงเวลาแบบ wall-clock ของการรันโมเดลตั้งแต่ต้นจนจบ และปริมาณงานต่อวินาทีที่คำนวณจาก latency นั้น

โมเดลที่ใช้วัดและวิธี quantization

  • benchmark นี้ถูกออกแบบมาเพื่อจำลอง การคูณเมทริกซ์ขนาดใหญ่ 6 ชุด ที่คล้ายกับเลเยอร์ซึ่งใช้เวลามากในโมเดล transformer อย่าง OpenAI Whisper
    • รูปร่างอินพุตคือ (6, 1500, 256) X (6, 256, 1500)
    • รูปร่างผลลัพธ์คือ (6, 1500, 1500)
    • โมเดลประกอบด้วยโหนด MatMul เดียว โดยมีอินพุต 2 ตัวและเอาต์พุต 1 ตัว
  • โมเดลถูกสร้างขึ้นแบบ on-the-fly ด้วยเฟรมเวิร์กโมเดล Onnx แล้วส่งต่อให้ Onnx Runtime
  • โมเดลอ้างอิงเป็นเวอร์ชัน float ล้วน และรันบน CPU เท่านั้น
  • หากต้องการให้ NPU รันได้อย่างมีประสิทธิภาพ โดยมากจำเป็นต้องใช้ โมเดลแบบ quantized และ float16 รองรับอย่างจำกัด
  • แนวทางแรกสำหรับ NPU ใช้เมธอด ORT ทางการ quantize_static()
    • เพื่อความสะดวก เทนเซอร์อินพุตและเอาต์พุตยังคงเป็น 32-bit float
    • มีการแปลงค่าที่ต้นและท้ายกราฟตอนรันไทม์ และให้ส่วนคำนวณที่เหลือรันแบบ 8-bit
  • ในคอนฟิกนี้ งานแปลงค่าของ NPU ช้ามาก และใน npu_quant_profile.csv ส่วนแปลงค่ากินเวลามากกว่า 75% ของเวลาทั้งหมด
  • แนวทางที่สองคือสร้างกราฟโมเดลที่เทียบเท่ากันโดยโปรแกรม โดยใช้อินพุตและเอาต์พุตแบบ 8-bit
    • วิธี quantized compute and I/O นี้มักเร็วกว่าเวอร์ชัน float I/O ราว 3 เท่า
    • จากการ profiling เวลาส่วนใหญ่ถูกใช้ไปกับการคูณเมทริกซ์ตามที่คาดไว้

ตัวแปรที่นำมาพิจารณาในการวัดประสิทธิภาพ

  • มีการพิจารณาว่าเป็นงานแบบ compute bound หรือไม่ โดยเลือก shape ของเมทริกซ์ให้ใกล้เคียงสี่เหลี่ยมมากขึ้น
    • โมเดล transformer สมัยใหม่ต่างจากโมเดล convolution รุ่นเก่าตรงที่อาศัยการคูณเมทริกซ์ขนาดใหญ่
    • หากเลเยอร์มีลักษณะใกล้กับการคูณเมทริกซ์-เวกเตอร์มากขึ้น การนำ weight กลับมาใช้ซ้ำจะลดลง และการดึงค่าจาก DRAM อาจกลายเป็นคอขวด
    • มิติ k ของเมทริกซ์เดิมใน tiny Whisper คือ 64 แต่ benchmark นี้เพิ่มเป็น 256 เพื่อเปิดพื้นที่ให้มีการปรับแต่ง SIMD มากขึ้น
  • การตั้งค่าพลังงานถูกปรับไปทางเพิ่มประสิทธิภาพ
    • พยายามตั้งค่า Windows energy ทั้งหมดเป็น Best Performance
    • รัน benchmark ขณะเสียบไฟกับแท็บเล็ต
    • ตัวเลือกเซสชัน htp_performance_mode ของ Qualcomm Onnx Runtime ถูกตั้งเป็น sustained_high_performance เพราะให้ latency รวมต่ำที่สุดในการทดลอง
  • โครงสร้างโมเดลถูกจำกัดให้เป็นการคูณเมทริกซ์เดี่ยวเพื่อให้ตีความได้ง่าย
    • แม้จะทำหลายเลเยอร์, convolution หรือ weight แบบ static ได้ แต่เลือก MatMul เดี่ยวที่มีอินพุตแบบ dynamic เพื่อสะท้อนโครงสร้าง transformer ที่ใช้กันแพร่หลายใน LLM และโมเดลสมัยใหม่
  • ยังมีความเป็นไปได้ของความผิดพลาดในการตั้งค่า
    • ใช้ unsigned 8-bit quantization และองค์ประกอบ qdq ภายในกราฟ
    • แม้จะพยายามทำตามแนวปฏิบัติที่ดีในเอกสาร แต่อาจยังหลุดจาก fast path ของไดรเวอร์หรือการทำงานของตัวเร่ง
  • ยังมีการพิจารณาตัวเลือก API สำหรับเข้าถึง AI acceleration บน Windows
    • ดูเหมือน DirectML จะรองรับเฉพาะการเข้าถึง GPU
    • ดูเหมือน OpenVino จะไม่สามารถรันบนฮาร์ดแวร์ Arm นี้ได้
    • การใช้ Qualcomm QNN SDK โดยตรงก็ให้ผลประสิทธิภาพใกล้เคียงกัน
    • TensorFlow Lite ไม่รองรับ Windows for Arm
    • จากการสำรวจและทดลองนี้ Onnx ดูเป็นเฟรมเวิร์กที่เหมาะที่สุดสำหรับการได้ประสิทธิภาพเร่งด้วย NPU เพราะได้รับการสนับสนุนทั้งจาก Microsoft และ Qualcomm

การตีความผลลัพธ์

  • ผลลัพธ์นี้อ้างอิง ณ วันที่ 2 ตุลาคม 2024 และวัดบน Microsoft Surface Pro 11th Edition
    • SoC คือ Snapdragon(R) X 12-core X1E80100 @ 3.40 GHz
  • แม้ตัดงานแปลง float ออกแล้ว ผลของ NPU ก็ยังช้ากว่า CPU
    • ในมุมมองของ accelerator ถือว่าไม่ใช่ผลลัพธ์ที่น่าพอใจ
    • อย่างไรก็ตาม ยังไม่ตัดความเป็นไปได้ว่ามันอาจมีข้อดีด้านประสิทธิภาพพลังงานหรือ sustained performance
  • ค่าประสิทธิภาพสูงสุดของ NPU ที่วัดได้คือ 573 billion ops/s ซึ่งเท่ากับ 1.3% ของตัวเลข 45 trillion ops/s ในสื่อการตลาดของ Microsoft Surface Pro 11th Edition
  • เมื่อรันโมเดลเดียวกันบน Nvidia Geforce RTX 4080 Laptop GPU ใช้เวลา 3.2ms
    • คิดเป็น 2,160 billion ops/s
    • สูงกว่าค่าที่วัดได้จาก NPU บน Surface เกือบ 4 เท่า

2 ความคิดเห็น

 
bungker 2024-10-18

ผมเข้าใจมาตลอดว่า npu ของ ryzen เร็วกว่า cpu อยู่เล็กน้อย แต่พอเห็นแบบนี้แล้วความอยากได้ Snapdragon ลดฮวบเลย

 
GN⁺ 2024-10-17
ความคิดเห็นจาก Hacker News
  • ดูจากผลแล้ว โดยรวมเหมือนว่า การใช้ทรัพยากรประมวลผล ยังทำได้ไม่ดีนัก CPU 8.4ms, GPU 3.2ms ต่างกันน้อยเกินไป และในกรณีนี้น่าจะคาดหวังความต่างระดับ 10–20 เท่าได้
    สาเหตุอาจเป็น onnxruntime ก็ได้ ดูเหมือนมีผู้ผลิตฮาร์ดแวร์บางรายที่ปล่อยแค่หน่วยประมวลผลออกมา แต่การสนับสนุนที่ดีจริง ๆ ยังไม่ตามมา ต้องรอดูว่าจะเปลี่ยนได้เร็วแค่ไหน
    อีกอย่าง หลายคนมักเข้าใจผิดว่าเป้าหมายของ NPU คือ “ความเร็ว” แต่แก่นจริง ๆ คือ ใช้พลังงานต่ำ ถ้าจะเน้นความเร็ว ต้องกำจัดคอขวดหน่วยความจำ และสุดท้ายก็จะไปออกแบบ ASIC ที่มีหน่วยความจำของตัวเอง NPU ในอุปกรณ์ส่วนใหญ่ติดอยู่กับ SoC รอบ ๆ CPU เพื่อใช้ offload งานประมวลผล AI
    ถ้ารันเบนช์มาร์กนี้แบบลูปไม่สิ้นสุดบนอุปกรณ์ทั้งสามคือ CPU/NPU/GPU แล้ววัดการใช้พลังงาน น่าจะน่าสนใจ คาดว่า NPU จะต่ำที่สุดและมีจำนวนการคำนวณต่อวัตต์ดีที่สุดด้วย

    • เริ่มสงสัยว่าเหตุผลที่แท้จริงของ NPU อาจเป็น การตลาด ก็ได้ อาจเป็นกระแสประมาณว่า “NVDA มีมูลค่า 3.3 ล้านล้านดอลลาร์ งั้นใส่อะไรสักอย่างที่เป็น AI ลงในผลิตภัณฑ์เราบ้างเถอะ”
    • NPU มีเป้าหมายเรื่อง offload เยอะเหมือนกัน ขึ้นอยู่กับการใช้งาน CPU กับ GPU อาจยุ่งกับงานอื่นอยู่ ดังนั้น NPU จึงเป็นแบนด์วิดท์เพิ่มเติมที่ใช้ได้โดยไม่แย่งกัน
      เช่น ในฟิลเตอร์ภาพถ่าย AI นั้น GPU อาจกำลังเรนเดอร์พรีวิว ส่วน CPU ก็น่าจะยุ่งกับ UI และการรับอินพุตจากผู้ใช้
    • นี่แหละคือ คูเมือง ของ Nvidia แทบทุกอย่างมีเคอร์เนลที่ปรับแต่งสำหรับ CUDA และบางกรณีก็มี Apple Accelerate พอใช้ได้
      Apple Accelerate เคยเป็นเส้นทางแทบจะ唯一เดียวในการเข้าถึงหน่วยเมทริกซ์ของ CPU ก่อน M4 และ NPU ถ้าอยากใช้อย่างอื่น ก็ต้องเตรียมส่งแพตช์ให้เฟรมเวิร์กแมชชีนเลิร์นนิงที่เลือก หรือเตรียมเขียนโค้ดฝึกและ inference เอง
    • ผมใช้ onnxruntime ทำแอปด้วย C ล้วน ๆ อยู่ และประสิทธิภาพดีกว่าแอปคล้ายกันที่ทำด้วย Python ค่อนข้างมาก ยังมีช่องให้ปรับปรุงประสิทธิภาพได้อีกเยอะ
      สุดท้าย Python ก็เรียก C อยู่ดี แต่ก็น่าสนใจมากว่าประสิทธิภาพหายไปมากแค่ไหน
    • ดูเหมือนว่ายังไม่ได้จับเวลาอย่างถูกต้อง และโดยทั่วไป “เวลา” ที่เอาไปใช้ในการตลาดก็มักไม่ตรงกับค่าที่คนทั่วไปคิดว่าเป็นการวัดเสมอไป ถึงอย่างนั้นตัวเลขการตลาดบางทีก็เปรียบเทียบได้ง่าย
      ถ้าใช้ GPU ต้องพิจารณาด้วยว่าในเวลาที่วัดนั้นรวม งานแบบ asynchronous หรือไม่
      ถ้าใช้ time.time() แบบซื่อ ๆ CPU ก็แค่บันทึกเวลา ส่วน model(input.cuda()).cuda() จะส่งข้อมูลไปยังหน่วยความจำ GPU และเริ่มคำนวณ แต่เพราะเป็น asynchronous เวลาสิ้นสุดจึงอาจถูกบันทึกโดยไม่เกี่ยวว่าผลลัพธ์พร้อมจริงหรือยัง
      เป็นพฤติกรรมที่คาดเดายากถ้าไม่รู้จักระบบและฮาร์ดแวร์ ไม่ใช่แค่ Python เท่านั้น ภาษาแทบทั้งหมดถูกออกแบบให้คอมไพล์ออกมาในรูปแบบที่เหมาะสมกว่าตัวโค้ดที่เขียน และเมื่อไม่มีการล็อกก็จะไม่บล็อกงานของ CPU
      ถ้าจะวัดงาน GPU จริง ๆ ต้องดู CUDA event timer ใน PyTorch ใช้วิธี torch.cuda.Event(enable_timing=True)
      นอกจากนี้ ขนาดและรูปแบบหน่วยความจำก็ซับซ้อน เบนช์มาร์กนี้ใช้รูปแบบที่ไม่เป็นผลดีกับ NPU โดยปกติ NPU และ GPU ต้องการ channels last ดังนั้น [1,1500,1500,6] จึงถูกกว่า [1,6,1500,1500]
      ตัวเลข 1500 กับ 6 ก็เป็นเลขแปลก ๆ ไม่ดีต่อ NPU และเมื่อคิดว่าอุปกรณ์แบบนี้ยังใหม่อยู่ การสูญเสียประสิทธิภาพอาจค่อนข้างมาก
      รายละเอียดเพิ่มเติมเขียนไว้ที่ https://news.ycombinator.com/item?id=41864828
  • NPU เหล่านี้กิน พื้นที่ซิลิคอน ไปไม่น้อย ถ้าท้ายที่สุดแทบไม่ได้ใช้งานก็คงน่าเสียดายจริง ๆ ผมหาการวิเคราะห์ไดที่แยกเฉพาะ NPU ออกจาก Snapdragon X ไม่เจอ แต่ฝั่ง AMD ที่มีเป้าหมายคล้ายกันประมาณ 50 TOPS ดูได้ที่นี่ และมันกินพื้นที่ประมาณเท่าคอร์ CPU ประสิทธิภาพสูง 3 คอร์
    https://www.techpowerup.com/325035/amd-strix-point-silicon-p...

    • หวังว่ากระแส LLM จะจบลง แล้ว สามัญสำนึกและประสิทธิภาพ บางส่วนจะกลับมาอีกครั้ง โดยส่วนตัวผมไม่มีอะไรที่ต้องใช้ฮาร์ดแวร์ส่วนเพิ่มนี้ และ “GenAI” ก็ไม่ได้ช่วยอะไรผมเลย รวมถึงไม่ช่วยงานที่เกี่ยวกับอาชีพด้วย
      ที่แย่กว่านั้นคือดูเหมือนคนส่วนใหญ่ก็ไม่ได้ต้องการเหมือนกัน และผลสำรวจล่าสุดบางส่วนก็แสดงให้เห็นว่าความไม่พอใจต่อการแทรกซึมของ AI มีมากกว่า ไม่ควรต้องจ่ายเงินเพิ่มให้ของแบบนี้ และควรเป็นตัวเลือกเท่านั้น
      ถ้าทำแบบนั้น ยอดขายจะแสดงให้เห็นว่ามีคนอยากจ่ายพรีเมียมให้ “AI” น้อยแค่ไหน และจะทำให้ชัดเจนว่ามันถูกโหมเกินจริงและไม่จำเป็นเพียงใด
    • ชิปยุคใหม่ต้องเหลือสัดส่วนหนึ่งของไดไว้เป็น dark silicon ไม่อย่างนั้นมันจะละลายหรือ throttling จนแทบไร้ประโยชน์ องค์ประกอบแบบนี้ก็รวมอยู่ในสัดส่วนนั้นด้วย
      ดังนั้นเป้าหมายของชิ้นส่วนแบบนี้คือให้ถูกใช้งาน แต่ไม่ถูกใช้งานมากเกินไป
      แทนที่จะเป็น NPU อาจเอาทรานซิสเตอร์และพื้นที่ไดนั้นไปใช้ได้หลายอย่าง แต่คงไม่ได้ใส่คอร์ CPU ประสิทธิภาพสูงเพิ่ม เพราะจะทำให้ความหนาแน่นพลังงานสูงเกินไป เกิดปัญหาความร้อนที่แก้ยากถ้าไม่มีการ throttling ถาวร
      [1] https://en.wikipedia.org/wiki/Dark_silicon
    • ผมก็คิดเหมือนกัน ตอนนี้ถ้าจะซื้อระบบที่มี NPU ยังต้องตั้งใจหาอยู่ เลยยังไม่มี แต่คาดว่าในอนาคตมันอาจถูกรวมมาเป็นค่าเริ่มต้น
      สำหรับคนที่ไม่รันโมเดล มันดูเหมือนเป็นการสิ้นเปลือง และผมก็สงสัยว่ามีวิธีเอาไปใช้ประโยชน์อย่างอื่นได้อย่างไรบ้าง
    • Snapdragon X ยังคงเป็น 12 คอร์ และเป็นโครงสร้างแบบ homogeneous ที่ทุกคอร์เหมือนกัน Strix Point ก็ 12 คอร์เหมือนกัน แต่เป็นโครงสร้าง 4+8 และแม้แต่คอร์ “เล็ก” ก็ไม่ได้ยอมเสียประสิทธิภาพจนแทบไม่มีเหตุผลในการมีอยู่เหมือนคอร์เล็กของดีไซน์ ARM
      ซอฟต์แวร์สำหรับผู้บริโภคไม่ได้สเกลไปถึงระดับนั้นอยู่แล้ว เลยสงสัยว่าจะเอาทรานซิสเตอร์ไปจัดสรรให้ CPU เพิ่มแล้วทำอะไรได้
      คล้ายกับเหตุผลที่ Apple ใส่วิดีโอเอนจินจำนวนมากใน SoC ด้วยงบทรานซิสเตอร์ที่รับได้ ก็ไม่ได้มีที่อื่นให้เอาไปใช้มากนัก การเพิ่มประสิทธิภาพ single-thread ไม่ได้ถูกจำกัดด้วยจำนวนทรานซิสเตอร์อย่างเดียวอีกต่อไป และซอฟต์แวร์ก็ทำ multithreading ได้ไม่ดี
  • ผมเคยคิดว่าจุดประสงค์ของอุปกรณ์แบบนี้ไม่ใช่ความเร็ว แต่คือการรัน โมเดลขนาดเล็กด้วยพลังงานต่ำมาก ผมใช้โน้ตบุ๊ก AMD รุ่นใหม่ที่มี NPU อยู่ พอเปิดเอฟเฟกต์วิดีโอที่บอกว่ารันบน NPU การใช้พลังงานไม่เปลี่ยน แต่ถ้าใช้ Nvidia Studio Effects การใช้พลังงานจะเพิ่มขึ้น
    NPU ดูเหมือนจะมีไว้สำหรับโมเดลที่ปรับแต่งมาอย่างมากเพื่อทำงานเล็ก ๆ เช่น การสบตา เบลอพื้นหลัง โมเดลแก้ไขอัตโนมัติ การถอดเสียง และ OCR โดยเฉพาะบน Windows ผมเข้าใจว่ามันรัน OCR ทั้งหน้าจอและ embedding สำหรับการค้นหาเพื่อใช้กับฟีเจอร์ rewind

    • โดยเฉพาะถ้าอุปกรณ์นั้นเป็น Xilinx FPGA ก็ยิ่งใช่ สิ่งที่ใส่มาใน Ryzen มือถือรุ่นใหม่มีประสิทธิภาพดีกว่าถึง 5 เท่า
      ช่วงนี้ AMD ทำงานได้ยอดเยี่ยม แต่ดูเหมือนจะไม่ได้โฆษณาเสียงดังนัก อันนี้น่าสนใจเป็นพิเศษ: https://lore.kernel.org/lkml/DM6PR12MB3993D5ECA50B27682AEBE1...
      แก้ไข: มันไม่ใช่ FPGA วันนี้เพิ่งได้รู้
    • ความเข้าใจของผมก็เหมือนกัน ประเด็นหลักคือ พลังงานต่ำและ latency ต่ำ
      ลองประเมินโมเดล CoreML บน macOS ก็จะเห็นได้ ANE ใช้เวลาประมาณครึ่งหนึ่งของ GPU และ GPU ใช้เวลาประมาณครึ่งหนึ่งของ CPU อัตราส่วนจริงขึ้นอยู่กับโมเดล
    • พลังงานต่ำหมายถึง โทเค็นที่ถูกลง และนำไปสู่การใช้งานที่รับภาระได้มากขึ้นและยั่งยืนขึ้น ผมคิดว่าประโยชน์ที่ผู้บริโภคได้รับโดยรวมอยู่ตรงนี้ GPU ที่กินไฟมากดูจะเหมาะกับงานวิจัย งานเชิงพาณิชย์ และองค์กรขนาดใหญ่มากกว่า
      ชิปที่จะคุกคาม Nvidia น่าจะเป็นชิปและหน่วยความจำที่ราคาถูกพอจะรันโมเดลที่ดีพอใช้บนอุปกรณ์ส่วนบุคคลอย่างสมาร์ตโฟนได้
      หากคนทั่วไปเห็นพ้องว่า LLM มีประโยชน์ และยอมจ่ายพรีเมียมเพิ่มเล็กน้อยกับราคาอุปกรณ์ ผมคิดว่าอนาคตของเทคโนโลยีนี้โดยแก่นแล้วคือโมเดลส่วนบุคคลที่ให้ความเป็นส่วนตัวในตัวเอง
      ปริมาณข้อมูลส่วนตัวที่ผู้คนเทลงไปในที่อย่าง ChatGPT นั้นน่าตกใจมาก ดูใน Reddit จะเห็นว่าผู้ที่ติดแอปแฟนสาวเสมือน AI มักส่งต่อรสนิยมที่มืดที่สุด คำสารภาพที่เปราะบาง และแม้แต่บทสนทนาที่อาจเข้าข่ายอาชญากรรมให้บริษัทแอปนิรนาม
      Google เองก็ระบุชัดเจนว่าหากเปิดประวัติ Gemini ไว้ ก็อาจมีการตรวจสอบเนื้อหาการสนทนาได้
      การทำนายโทเค็นที่ซับซ้อนซึ่งต้องใช้โมเดลใหญ่กว่าอาจถาม LLM บนคลาวด์ได้ แต่สำหรับผู้บริโภค ความเป็นส่วนตัวต้องได้รับการรับประกันอย่างแน่นอน
      ผมไม่คิดว่าผู้ช่วยส่วนตัวทั่วไป การแชต และการค้นหาข้อมูลในชีวิตประจำวันจำเป็นต้องใช้การอนุมานระดับล้ำสุดหรือ LLM แบบโชว์ความสามารถพิเศษ
    • จากสิ่งที่ได้ยินตอนเปิดตัวการรู้จำเสียงบนอุปกรณ์ใน Pixel และจากผลที่ได้ลองรันงาน ONNX บน Apple Neural Engine กับ CPU หลังออกจาก Google แล้ว ผมคิดว่าคำพูดนี้ถูกต้อง
      อย่างไรก็ตาม ข้อสรุปเฉพาะในบทความยังน่าสงสัยอยู่บ้าง มันเป็น ONNX ของ Qualcomm และอาจเก่าแล้ว ฝั่ง Android มักบ่นกันมากเรื่องวิศวกรรมซอฟต์แวร์ของ Qualcomm
      แต่ทิศทางนั้นถูกต้อง คำกล่าวอ้างเรื่องการเร่ง AI ในฮาร์ดแวร์ผู้บริโภคส่วนใหญ่แทบจะเป็นการคุยโวโดยทั่วไป ข้อยกเว้นคือ A) ใช้ซอฟต์แวร์ 1P หรือ B) มีใครบางคนภายใน 1P ที่อยากให้คุณใช้ฟีเจอร์นั้นจริง ๆ
    • ใช่ แต่คุณคงไม่อยาก เขียนโปรแกรมให้อุปกรณ์พวกนี้ด้วย Python โดยเฉพาะเมื่อเป็นอุปกรณ์ใหม่ การปรับแต่งอาจยังพอร์ตมาไม่ดี จึงคาดหวังประสิทธิภาพดี ๆ ได้ยาก
      แม้ใช้ของอย่าง TensorRT ก็ไม่น่าจะเร็วเท่าการเขียนเองตั้งแต่ต้น และนี่ก็เป็นเหตุผลที่ Nvidia ทุ่มกำลังคนจำนวนมาก แต่ก็เข้าใกล้ได้พอสมควรและลดเวลาเขียนลงได้มาก
      อุปกรณ์แบบนี้โดยทั่วไปถูกปรับแต่งมาสำหรับงานที่คล้าย ๆ กันและทำซ้ำ ๆ ดังนั้นผมคิดว่าข้อมูลบางส่วนที่เก็บมาจากตรงนี้อาจไม่ถูกต้อง
      ผมยังไม่เคยใช้งานชิป NPU เหล่านี้โดยตรง แต่ยากจะเชื่อถือ timing ได้ timing ของ CUDA ช่วงท้ายมีโอกาสสูงที่วัดไม่ถูกต้องตามโค้ด การวัด timing ไม่ง่ายอย่างที่คิด
      จำนวนการคำนวณที่โฆษณาไว้นับเฉพาะการคำนวณที่ทำบน NPU โดยตรง ขณะที่ต้นฉบับอาจรวมงาน CPU เข้าไปในการวัด NPU และ GPU ด้วย เอกสารมีเครื่องมือ benchmark อยู่ จึงน่าจะใช้แนวทางใกล้เคียงกัน และผมก็อยากรู้ว่าหลัง warm-up แล้ว variance เป็นอย่างไร
      รูปแบบข้อมูลก็ดูเหมือนจะผิดด้วย ที่นี่ต้องใช้ channels last เอกสารก็ยืนยันเรื่องนี้
      ตัวเลข 1500 ก็ดูแปลก จึงอาจเกิดความผิดพลาดเพิ่มเติมได้ ผลลัพธ์อาจต่างออกไปเมื่อเป็น 1536, 2048, 256 หรือค่าที่เล็กกว่านั้น โมเดลจริงไม่ได้ประมวลผลภาพเต็มความละเอียด และหากปรับสถาปัตยกรรมให้เหมาะกับโมเดล ข้อมูลเรื่อง shape จะสำคัญ ในแมชชีนเลิร์นนิง การปรับแต่ง shape ค่อนข้างสำคัญ
      ดูเอกสารแบบเร็ว ๆ แล้ว การตั้งค่าก็ดูไม่เหมาะสม “Model Workflow” บอกว่าต้องการข้อมูลเป็นเลขทศนิยม 8 บิตหรือ 16 บิต แต่เลขทศนิยมก็มีหลายชนิด bfloat ของ PyTorch ไม่เหมือนกับ torch.half หรือ torch.float16
      mixed precision ยังเป็นหัวข้อที่ชวนสับสนอยู่ ดังนั้นหากมีปัญหาแบบนี้ก็ควรตรวจดูให้ดี ไม่แนะนำให้รันแค่ขั้นตอน quantization มาตรฐานแล้วจบ แค่ใช้เป็นจุดเริ่มต้นได้ แต่ถ้ายังไม่ “ดีพอ” ก็ไม่ควรหยุดแค่นั้น
      ถึงอย่างนั้นผมไม่ได้คิดว่าผลลัพธ์นี้ไร้ประโยชน์ เพียงแต่ต้องปรับปรุง เรื่องแบบนี้ซับซ้อนกว่าที่คิด และส่วนใหญ่เป็นเพราะเทคโนโลยียังใหม่ รายละเอียดยังอยู่ระหว่างการจัดระเบียบ
      เมื่อเทียบกับ CPU หรือ GPU โดยเฉพาะ CUDA ควรจำไว้ว่ามีการทุ่มแรงงานระดับหลายแสนคน-ชั่วโมง และแม้แต่ไลบรารีระดับสูงอย่าง Python ก็มีอย่างน้อยหลายหมื่นคน-ชั่วโมง อุปกรณ์เหล่านี้ยังไม่พร้อมนักสำหรับการใช้งานโดยตรงในระดับ abstraction ของภาษาที่ผู้ใช้ทั่วไปชอบ แต่ถ้ายอมทำงานใกล้กับฮาร์ดแวร์มากขึ้น ก็มีประโยชน์ไม่น้อย
      หากจะวัดงาน GPU แบบ asynchronous ใน PyTorch ควรใช้ CUDA events และ torch.cuda.synchronize() แทนการเอา CPU timer ไปคร่อม output ของโมเดล
      [1] https://www.thonking.ai/p/what-shapes-do-matrix-multiplicati...
  • การนำโมเดลไปปรับใช้บน NPU ต้องอาศัย การปรับแต่งตามโปรไฟล์ ค่อนข้างมาก หากเอาโมเดลที่รันบน CPU ได้ดีมาใช้โดยไม่ปรับแต่งสำหรับ NPU ผลลัพธ์มักน่าผิดหวัง

    • ความงามของ CPU อยู่ที่มันสามารถเคี้ยวโค้ดมั่ว ๆ แค่ไหนก็ได้ให้ทำงานด้วยความเร็วที่สมเหตุสมผล
    • ทุกครั้งที่คุยกับคนที่ทำงานกับสิ่งอย่าง IREE หรือ OpenXLA ผมรู้สึกว่าการเข้าใจและใช้งาน คอมไพเลอร์กับรันไทม์ เหล่านั้นเองก็เป็นอาชีพหนึ่งแล้ว
  • คำอธิบายในรีโพสitory GitHub ให้ข้อมูลมีประโยชน์กว่าบล็อกมาก
    ถ้ารันการคูณเมทริกซ์ int8 ด้วย onnx ประสิทธิภาพอยู่ที่ประมาณ 0.6TF
    https://github.com/usefulsensors/qc_npu_benchmark

  • บอกว่าทำให้เมทริกซ์อินพุตใกล้เคียงสี่เหลี่ยมจัตุรัสมากขึ้นเพื่อให้ทำ tiling และ reuse ได้ แต่ก็ไม่น่าแปลกใจหากการปรับแต่งที่เป็นไปได้จำนวนมากไม่ได้เข้าไปอยู่ใน Onnx
    ดูเหมือน Qualcomm จะไม่เปิดให้เข้าถึง NPU โดยตรง แต่คาดหวังให้ผู้ใช้แปลงโมเดลผ่านเฟรมเวิร์กแล้วส่งต่อเข้าไป จากประสบการณ์ของผม เครื่องมือแปลงมักไม่ค่อยดีนักและพลาดการปรับแต่งไปมาก
    ดังนั้นอาจไม่ใช่ “NPU ไม่ดี” แต่เป็น “เครื่องมือแปลงไม่ดี” มากกว่า ผมจะรอจนกว่าจะเข้าถึงได้โดยตรง และไม่ไว้ใจเครื่องมือแปลง
    ผมมองว่า NPU เหมาะกับโมเดลแมชชีนเลิร์นนิงขนาดเล็กมาก ๆ และการประมาณฟังก์ชันที่เร็วมาก นั่นคือการใช้งานที่ผมตั้งใจไว้ ถึง LLM จะกำลังมาแรง แต่มีงานเฉพาะทางจำนวนมหาศาลที่โมเดลเล็กมีประโยชน์จริง ๆ

    • ช่วยยกตัวอย่างงานเฉพาะทางที่โมเดลเล็กมีประโยชน์ได้ไหม? ถ้าเป็นไปได้ อยากได้ตัวอย่างที่แม้จะเป็นโมเดลเล็ก แต่ รันต่อเนื่อง จนอยู่ในแคชได้ และมีคุณค่ากับผู้ใช้จำนวนมากพอที่จะคุ้มกับการ占แคชนั้น
      ไม่ได้หมายความว่าไม่มีของแบบนั้น แต่พูดตรง ๆ คือผมไม่ค่อยรู้ว่ามันคืออะไร เลยอยากทราบ
    • ผมก็เข้ามาเพื่อจะพูดเรื่องนี้เหมือนกัน ยังไม่เคยใช้ Elite X แต่ในอุปกรณ์รุ่นก่อน ๆ โดยเฉพาะ 865 ตัวเร่งอย่าง compute DSP และ NPU ที่เล็กกว่ามากต้องใช้การตั้งค่าที่เฉพาะเจาะจงมาก การคอมไพล์ด้วย toolchain เฉพาะ การสื่อสารแบบ RPC อะไรทำนองนั้น
      หวังว่า NPU ของ Elite X จะเข้าถึงได้ง่ายขึ้นเพราะ Copilot+ แต่ประเด็นคือมันไม่มีทางง่ายแบบ “รันโมเดลทั่วไปแล้วมันจะเทเลพอร์ตไป NPU อย่างมหัศจรรย์” แน่นอน
  • RTX 4080 น่าจะทำได้ประมาณ 40 TFLOPS แต่ในนี้รายงานแค่ 216,000 ล้านการดำเนินการต่อวินาที ระดับนี้ทำให้คิดว่าควรตรวจสอบเบนช์มาร์กใหม่
    เป็นไปได้สูงว่ามีข้อผิดพลาดร้ายแรงในการวัด FLOPS การที่ CPU ชนะ NPU เป็นเรื่องที่เป็นไปได้ แต่ถ้าจะเปรียบเทียบให้ถูกต้อง ควรเบนช์มาร์กการคูณเมทริกซ์หลายชุดโดยไม่มีการซิงโครไนซ์แอปพลิเคชัน

    • นั่นเป็นแค่ส่วนหนึ่งเท่านั้น แค่ไล่อ่านเอกสารคร่าว ๆ ก็เห็นว่า inference บน CPU ก็ไม่ได้ทำในรูปแบบที่เปรียบเทียบกันได้เช่นกัน
  • เบนช์มาร์กเป็น การคูณเมทริกซ์ รูปแบบ (6, 1500, 256) X (6, 256, 1500) ซึ่งในโลก AI ไม่ได้ใหญ่เท่าไร หากเป็นเมทริกซ์ที่ใหญ่กว่านี้มาก ช่องว่างก็น่าจะยิ่งกว้างขึ้น
    ตัวอย่างเช่น แม้แต่หนึ่งในโมเดลขนาดเล็กอย่าง Llama 3.1 8B ก็มีการคูณเมทริกซ์แบบ (batch, 14336, 4096) x (batch, 4096, 14336)
    ผมมองว่าเบนช์มาร์กนี้ยังไม่สมจริงพอ

  • ผมลองรัน qprof ซึ่งเป็นโปรไฟเลอร์ NPU ของ Qualcomm กับเบนช์มาร์กนี้แล้ว จากผลโปรไฟล์ งานถูกแจกไปยังเวกเตอร์คอร์ ไม่ใช่เทนเซอร์คอร์ที่ให้พลังประมวลผลส่วนใหญ่ของ NPU
    คำนวณคร่าว ๆ แล้ว HMX ดูจะแรงกว่า HVX 30 เท่า
    ภาระงานค่อนข้างเล็ก จึงใช้ความสามารถของฮาร์ดแวร์ได้ไม่เต็มที่เพราะโอเวอร์เฮดของการทำ quantization/dequantization อินพุต/เอาต์พุต และการแมป NCHW-NHCW การ padding น้ำหนักและอินพุตให้เป็นพหุคูณของ 64 ก็น่าจะช่วยประสิทธิภาพได้เช่นกัน
    กราฟโปรไฟล์: https://imgur.com/a/2OKR93e
    ประสิทธิภาพการคำนวณ HVX โดยประมาณคือ 4 * 2 * 1.43 * 1024 / 8 = 1.46TOPS ที่ int8 โดย 4 คือจำนวนเวกเตอร์คอร์, 2 คือจำนวนการดำเนินการต่อไซเคิล, 1.43GHz คือความถี่ HVX, 1024bit คือความกว้างของเวกเตอร์รีจิสเตอร์ และ 8bit คือความละเอียด

    • รูปแบบสมการผิด และควรเป็น 4 * 2 * 1.43 * 1024 / 8
  • ชื่อบทความจริง ๆ ควรเป็น “Benchmarking Qualcomm's NPU on the Microsoft Surface Tablet”
    นี่ไม่ใช่บทความเกี่ยวกับ NPU โดยทั่วไป แต่เป็นการดู NPU รุ่นหนึ่งด้วยเบนช์มาร์กเฉพาะและชุดไลบรารี/เฟรมเวิร์กเฉพาะ ดังนั้นในทางปฏิบัติจึงพิสูจน์อะไรไม่ได้เลย

    • ชื่อมาจากบทความต้นฉบับ https://petewarden.com/2024/10/16/ai-pcs-arent-very-good-at-... และ URL ถูก dang เปลี่ยน: https://news.ycombinator.com/item?id=41863591
    • แต่บรรยากาศคือถ้าอยากได้คลิกมากขึ้น ก็ต้องโจมตีคนให้มากพอ รู้สึกว่าที่นี่ก็ค่อย ๆ เต็มไปด้วยบทความและชื่อแบบนี้มากขึ้นเรื่อย ๆ