2 คะแนน โดย GN⁺ 2024-06-06 | 1 ความคิดเห็น | แชร์ทาง WhatsApp
  • Entropy เป็นเครื่องมือ CLI ที่สแกนหา บรรทัดที่มีเอนโทรปีสูง ในโค้ดเบสขนาดใหญ่ เพื่อค้นหาสตริงที่ดูเหมือนค่า secret
  • บรรทัดที่มีเอนโทรปีสูงจะถูกมองว่าเป็นสิ่งที่ มีโอกาสเป็น secret สูง และเน้นใช้งานเพื่อค้นหาค่า secret ที่รั่วไหลอยู่ในโค้ดเบส
  • รองรับการติดตั้งและการใช้งานผ่าน การติดตั้งจากซอร์สด้วย Go, go run, Homebrew และ Docker
  • สามารถใช้ตัวเลือก -top, -ext, -ignore-ext เพื่อกำหนดจำนวนผลลัพธ์ นามสกุลไฟล์ที่จะรวม และนามสกุลไฟล์ที่จะยกเว้น
  • เมื่อรันผ่าน Docker ต้องเมานต์ไดเรกทอรีปัจจุบันไปที่ /data และใส่ /data ไว้ท้ายคำสั่งเพื่อให้สแกนไฟล์ระบบภายในเครื่อง

Entropy ทำอะไร

  • Entropy เป็นเครื่องมือ CLI ที่สแกนโค้ดเบสเพื่อค้นหา บรรทัดที่มีเอนโทรปีสูง
  • บรรทัดที่มีเอนโทรปีสูงมักเป็นค่า secret จึงช่วยในการค้นหา การรั่วไหลของ secret ภายในโค้ดเบส

วิธีติดตั้งและการรัน

  • ติดตั้งด้วย Go

    • วิธีติดตั้งที่แนะนำคือการติดตั้งจากซอร์สด้วย Go
    • หลังติดตั้งแล้วให้รันด้วยคำสั่ง entropy
go install github.com/EwenQuim/entropy@latest
entropy
  • มีวิธีรันแบบคำสั่งบรรทัดเดียวให้ใช้งานด้วย
go run github.com/EwenQuim/entropy@latest
  • ติดตั้งด้วย Homebrew

    • คำสั่งติดตั้งด้วย Homebrew มีดังนี้
brew install ewenquim/repo/entropy
entropy
  • รันด้วย Docker

    • การรันด้วย Docker ใช้วิธีเมานต์ไดเรกทอรีปัจจุบันไปที่ /data ของคอนเทนเนอร์
docker run --rm -v $(pwd):/data ewenquim/entropy /data

ตัวอย่างตัวเลือกหลัก

  • -h: ดูตัวเลือกที่ใช้งานได้
entropy -h
  • -top: กำหนดจำนวนผลลัพธ์อันดับต้น ๆ ที่จะแสดง
  • -ext: กำหนดนามสกุลไฟล์ที่จะสแกน
entropy -top 20 -ext go,py,js
  • -ignore-ext: กำหนดนามสกุลไฟล์ที่จะยกเว้น
  • สามารถส่งทั้งไฟล์และโฟลเดอร์เป็นอาร์กิวเมนต์ร่วมกันได้
entropy -top 5 -ignore-ext min.js,pdf,png,jpg,jpeg,zip,mp4,gif my-folder my-file1 my-file2

ข้อควรระวังเมื่อใช้ Docker

  • ตัวเลือก -v ของ Docker ใช้สำหรับเมานต์ไดเรกทอรีปัจจุบันเข้าไปในคอนเทนเนอร์
  • /data คือไดเรกทอรีเริ่มต้นที่เครื่องมือใช้ค้นหาไฟล์
  • หาก ไม่เพิ่ม /data ไว้ท้ายคำสั่ง เครื่องมือจะค้นหาภายในคอนเทนเนอร์แทนไฟล์ระบบในเครื่อง
docker run --rm -v $(pwd):/data ewenquim/entropy -top 20 -ext go,py,js /data
docker run --rm -v $(pwd):/data ewenquim/entropy -top 5 /data/my-folder /data/my-file

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

 
GN⁺ 2024-06-06
ความคิดเห็นจาก Hacker News
  • น่าสนใจ ถ้าเป็นผมคงทำประมาณนี้โดยอาศัยหลักว่า entropy สูงจะบีบอัดได้ไม่ดี
    perl -lne 'next unless $_; $z = qx(echo "$_" | gzip | wc -c); printf "%5.2f %s\n", $z/length($_), $_'
    แต่แนวทางนี้ใช้แต่ละบรรทัดเหมือนเป็นพจนานุกรม ไม่ใช่ทั้งไฟล์ ดังนั้นบรรทัดที่สั้นมากจะบีบอัดได้ไม่ดีและทำให้มีปัญหาเล็กน้อย
    มันจับบรรทัดอย่าง return map { $_ > 1 ? 1 : ($_ < 0 ? 0 : $_) } @vs; ได้ ซึ่งแม้จะเป็นโค้ดที่ถูกต้อง แต่ก็ดูเหมือนมี entropy ค่อนข้างสูงจริง ๆ
    ในทางกลับกัน ถ้าเติมคอมเมนต์ภาษาอังกฤษธรรมชาติเข้าไป ก็หลอกไม่ให้ตรวจพบบรรทัดที่มี entropy สูงได้
    ตอนนี้กำลังเดินทางเลยยังดูละเอียดไม่ได้ แต่ถ้าเอาคำสั่ง Perl นี้มาเทียบกับเครื่องมือนี้น่าจะสนุก ข้อดีของคำสั่ง Perl คือมันรันได้ทันทีบนเครื่องแทบทุกเครื่องที่ไม่ใช่ Windows ดังนั้นไม่จำเป็นต้องทรงพลังมากก็อาจถูกนำไปใช้ได้

    • เมื่อนานมาแล้วผมเรียน Go ระหว่างแก้โจทย์ Advent of Code และทุกครั้งที่แก้เสร็จ เพื่อนร่วมห้องก็จะคะยั้นคะยอให้ผมเอาโค้ดให้ดู แล้วเขียนคำตอบที่ยาว 10–50 บรรทัดใน Go ใหม่เป็น Ruby บรรทัดเดียว
      พร้อมกับล้อ Go และโปรแกรมกระท่อนกระแท่นของผมไม่หยุด และแม้ไม่ได้ตั้งใจ วันนั้นผมก็ได้เรียน Ruby ไปเยอะเหมือนกัน
    • ถ้าวัดขนาดไฟล์จากทุกบรรทัดในไฟล์ยกเว้นบรรทัดที่กำลังทดสอบ แล้วเพิ่มบรรทัดนั้นเข้าไปค่อยวัดอีกครั้ง ส่วนต่างของขนาด น่าจะเป็นตัวชี้วัดที่ยุติธรรมกว่า
      จะเอาไฟล์โค้ดทั้งหมดมาต่อกันแล้วทดสอบทีละบรรทัดทั้ง repository ก็ได้ แต่คงช้าเกินไป
    • คงใช้ตัวบีบอัดที่ดีกว่า gzip แต่ผมเคยใช้ทริกนี้หลายครั้งแล้ว
      xz หรือ zstd อาจเป็นตัวเลือกที่ดีกว่า และถ้ามองว่าอัตราการบีบอัดที่ดีที่สุดคือการประมาณ entropy ที่ดีกว่า ก็อาจดูผลงานที่ชนะ Hutter Prize [1] ได้
      [1] http://prize.hutter1.net/
    • สงสัยว่ามีเครื่องมือบรรทัดคำสั่งอย่าง zip ตัวไหนที่สามารถ กำหนดพจนานุกรมล่วงหน้า จากไฟล์หนึ่งไฟล์หรือมากกว่า แล้วใช้พจนานุกรมนั้นบีบอัดไฟล์ขนาดเล็กได้บ้างไหม
      แน่นอนว่าตอนแตกไฟล์ก็คงต้องส่งพจนานุกรมนั้นเป็นอินพุตแยกต่างหากด้วย
    • ผมใช้ secret scanner ของ Yelp เป็น pre-commit hook อยู่ และตั้งค่าได้ค่อนข้างง่ายผ่านกลไกการติดตั้งของ pre-commit
  • ปัญหานี้ก้าวข้ามได้ด้วยการตั้งรหัสผ่านฐานข้อมูลทั้งหมดเป็น abcd

    • ใน codebase ของเรา เครื่องมือนี้ตรวจเจอ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz1234567890" ว่าเป็น บรรทัดที่มี entropy สูง
    • ชื่อผู้ใช้: postgres
      รหัสผ่าน: postgres
    • นึกถึง https://xkcd.com/936/ เลย "correct horse battery staple" คงมี entropy ต่ำ เพราะเป็นแค่สตริงของคำที่ดูธรรมดา
  • สงสัยว่ามีบทความดี ๆ ที่พูดถึง วิธีใช้ entropy กับงานแบบนี้ ไหม ผมสงสัยมานานว่าคนเขาใช้กันจริง ๆ อย่างไร และมันได้ผลไหม แต่ยังไม่เคยลงไปขุดเอง
    ก่อนอื่น การนิยาม “entropy” ของข้อความก็ดูคลุมเครือแล้ว ที่นี่ใช้แบบง่าย ๆ ประมาณ -Sum(x log(x)) โดย x = countOccurences(char) / len(text) ซึ่งทำให้เกิดคำถามหลายอย่างว่าจริง ๆ แล้วมันทำงานได้ดีแค่ไหน
    สตริงต้องยาวแค่ไหน? ภาษาธรรมชาติมี entropy ที่เกือบคงที่ไหม? มีวิธีที่ดีกว่านี้หรือเปล่า?
    ตัวอย่างเช่น "vorpal" ควรมี entropy ต่ำกว่า "hJ6&:a" อย่าง “ชัดเจน” ตัวหลังดูเหมือนใช้ชุดอักขระที่ใหญ่กว่าภาษาธรรมชาติมาก และแม้จะไม่ใช่แบบนั้น ลำดับอักขระก็สำคัญ เพราะตัวแรกฟังดูเหมือนคำจริง ถึงจะเป็นคำที่ Carroll สร้างขึ้นก็ตาม
    แต่ “entropy” ที่ทุกคนใช้กันนี้ไม่รู้เรื่องพวกนั้นเลย ทั้งสองคงมี “entropy” เท่ากันเป๊ะ
    มันอาจทำงานได้ดีพอสำหรับเครื่องมือค้นหารหัสผ่านบน GitHub อีกตัวหนึ่ง แต่ผมสงสัยว่ามีอะไรที่ดีกว่านี้ไหม มีมาตรวัดที่วัดความสุ่มของข้อความได้อย่างมีความหมายมากกว่านี้หรือเปล่า?
    โปรเจกต์แบบนี้มีเป็นสิบ ๆ และทุกคนใช้ “entropy” เหมือนเป็นเรื่องแน่นอน แต่ผมไม่เคยเห็นงานวิจัยจริงจังในหัวข้อนี้เลย

    • Entropy เป็นมาตรวัด ความซับซ้อนหรือความไร้ระเบียบ ของสัญญาณ จุดที่น่าสนใจคือความไร้ระเบียบนั้นสัมพันธ์กับฐานหรือพจนานุกรมที่เหมาะสม
      บางอย่างอาจดูซับซ้อนใน encoding หนึ่ง แต่มี entropy ต่ำใน encoding ที่ถูกต้อง
      ถ้าจะตัดสิน entropy ของสัญญาณให้แม่นยำ ต้องรู้ฐานที่ถูกต้อง หรืออนุมานจากบริบท
      ถ้าจะทำให้เครื่องมือในบทความต้นทางแข็งแรงขึ้น วิธีที่ดีคือเตรียมพจนานุกรมที่คำนวณไว้ล่วงหน้าสำหรับช่วงข้อความทั่วไป เช่น source code หรือภาษาธรรมชาติ แล้วใช้แต่ละพจนานุกรม encode สตริงเพื่อเปรียบเทียบ ความสามารถในการบีบอัด
      สตริงที่มี entropy สูงอย่างค่าลับจะบีบอัดได้ไม่ดีด้วยพจนานุกรมทุกชุดที่มี
    • Entropy ของสตริงเฉพาะหนึ่ง ๆ ไม่ใช่แนวคิดทางคณิตศาสตร์ที่เข้มงวด ตามนิยามแล้ว สตริงที่รู้จักอยู่แล้วมีได้เพียงค่าเดียว ดังนั้น “entropy” จึงเป็น 0 บิต
      เหตุผลที่เราแยกข้อมูลที่ไม่สุ่มออกจากข้อมูลสุ่มได้ คือในบรรดาสถานะทั้งหมดที่เป็นไปได้ มีเพียงสับเซตเล็ก ๆ เท่านั้นที่มนุษย์ถือว่ามีประโยชน์ และเราพอรู้ว่าสับเซตนั้นมีลักษณะอย่างไร จึงพอประเมินได้ว่าสตริงหนึ่ง ๆ ถูกสร้างขึ้นจากกระบวนการแบบไหน
      แน่นอนว่าการทดสอบเชิงสถิติอย่าง https://en.wikipedia.org/wiki/Diehard_tests ดีพอจะแยกข้อมูล entropy ต่ำกับ entropy สูงได้ แต่เครื่องสร้างเลขสุ่มเทียมสมัยนี้ไม่มีปัญหาในการผ่านการทดสอบเหล่านี้ทั้งหมด แม้ “entropy” จริง ๆ จะมีแค่ค่า seed กับความซับซ้อนของอัลกอริทึมก็ตาม
    • Kolmogorov complexity ของสตริงใด ๆ คำนวณไม่ได้
  • เครื่องมือที่น่าดูประกอบกัน:
    trufflehog: https://github.com/trufflesecurity/trufflehog
    detect-secrets: https://github.com/Yelp/detect-secrets
    semgrep secrets: https://semgrep.dev/products/semgrep-secrets -- เป็นแบบเสียเงิน แต่บางกรณีอาจรวมอยู่ในไลเซนส์ที่มีอยู่แล้ว

    • สำหรับการค้นหาสตริงที่น่าสนใจและค่าลับ PyWhat ก็น่าดูเช่นกัน: https://github.com/bee-san/pyWhat
    • noseyparker ก็ใช้ได้ดี: https://github.com/praetorian-inc/noseyparker
      ผมมองว่าโซลูชันเหล่านี้ดีกว่ามากในการค้นหาค่าลับ เมื่อเทียบกับแนวทางง่ายๆ ที่อิงเอนโทรปี
      จริงอยู่ที่เอนโทรปีมีความทั่วไปมากกว่า แต่เครื่องมือเหล่านี้ก็ลงตัวดีแล้ว และผ่านการพิสูจน์กับชุดข้อมูลจำนวนมากจริงๆ
  • เมื่อหลายปีก่อน DrJones เคยช่วยไว้ ด้วยการถามว่า สตริงที่มีเอนโทรปีสูง คืออะไร[0] และลิงก์บทความดีๆ ที่เกี่ยวข้อง[1] ให้
    [0] https://news.ycombinator.com/item?id=13304641
    [1] https://www.splunk.com/en_us/blog/security/random-words-on-e...

  • นึกถึงโปรแกรม ent ที่ใช้กันมานาน
    https://fourmilab.ch/random/

  • ถ้าสแกนไปถึง ประวัติ git ทั้งหมดของโปรเจกต์ได้ก็น่าจะมีประโยชน์ แม้ค่าลับจะเคยถูก commit แล้วถูกลบออกภายหลัง แต่มันก็ยังอาจหลงเหลืออยู่ในประวัติได้

  • ไม่เข้าใจว่าทำไมต้องติดตั้ง Go เพื่อรันเครื่องมือนี้ จุดเด่นอย่างหนึ่งของ Go คือผู้พัฒนาสามารถแจกจ่าย ไบนารีเดี่ยว ที่ใช้งานได้เลยไม่ใช่หรือ?

    • เพราะเป็นเครื่องมือด้านความปลอดภัย การเชื่อถือไบนารีตั้งแต่แรกจึงขัดกับวัตถุประสงค์ ถ้ามีซอร์ส อย่างน้อยก็ยังมีทางเลือกให้ตรวจสอบได้ว่ามันทำอะไรจริงๆ
    • อยากเอาขึ้น Homebrew แต่ PR ถูกปฏิเสธ เลยน่าจะต้องทำ brew tap เอง หรือโน้มน้าวให้เขารับ
      มีแผนจะทำ Docker image ด้วย
      พูดตรงๆ คือไม่คิดว่าจะได้รับความนิยมขนาดนี้ ดังนั้น repository ยังไม่ได้อยู่ในสภาพพร้อม 100%
    • ตอนนี้ Docker container ใช้งานได้แล้ว และมีเอกสารอยู่บนหน้าเว็บ
  • โมเดลภาษา อย่าง Llama 3 น่าจะสามารถโมเดลระดับความน่าประหลาดใจราย token เพื่อค้นหาบริเวณที่น่าประหลาดใจที่สุด หรือก็คือบริเวณที่มีเอนโทรปีสูงที่สุดได้
    อย่างในตัวอย่างหนึ่ง ตัวอักษรทั้งชุดอาจมีเอนโทรปีสูงในบางมุมมอง แต่สำหรับโมเดลภาษาที่คุ้นเคยกับโค้ด การมี alphabet แบบ Base62 เป็นค่าคงที่ใน codebase น่าจะไม่ใช่เรื่องน่าประหลาดใจเลย