สวัสดีครับในวันที่ 17 พฤศจิกายน 2568 ที่ผ่านมาทางบริษัท Siam Thanat Hack ได้มีการปล่อยโจทย์ของงาน STH mini web CTF 2025/2 ออกมาและผมได้มีการไปลองเล่นและได้เขียน write up นี้ขึ้นมาเพื่อมาลุ้นรับของรางวัลจากทางทีมงานครับ 🙏😅
เริ่มเลยหลังจากเข้ามาที่เว็บไซต์ที่โจทย์ให้มาจะปรากฎหน้าที่ไว้สำหรับทำการสมัครและล็อกอินดังรูป
ซึ่งถ้าตามสไตล์ของโจทย์เว็บที่ออกโดย STH แล้วจะต้องเริ่มด้วยการดู page source ก่อนเพราะทุกครั้งมันจะมีอะไรซ่อนอยู่ตลอด (จากประสบการณ์ของผมเอง 🙂)
หลังจากที่ดู page source และเลื่อนลงมาล่างสุดจะเห็นว่ามี firebase-config โผล่อยู่ทั้ง apiKey, projectId, databaseURL ... ซึ่งจากข้อมูลของ databaseURL ทำให้เรารู้ว่าเว็บนี้ใช้ real time database ของ firebase ผมเลยลองอ่านข้อมูลทั้งหมดใน real time database โดยการ GET ไปที่ databaseURL และเติม .json ไว้หลังสุด
ซึ่งจะเห็นว่าติด Permission denied แต่ status code มันขึ้นว่า 401 Unauthorized ผมเลยคิดว่าถ้าเราสมัครเป็น user แล้วมันอาจจะดูได้ก็ได้ ผมเลยลองกลับไปสมัครที่หน้าเว็บ
ซึ่งหลังจากสมัครเสร็จสิ้นผมได้ไปดูที่หน้า Network ใน Dev tool และสังเกตุว่าตอนเรากดสมัครมันจะมีการยิง api signUp และ response ที่ตอบกลับมาจะเป็นตัวของ Token หรือข้อมูลต่างๆของ user ที่เราสร้าง
จะเห็นว่ามี idToken ของผู้ใช้อยู่ด้วย ผมเลยจะลองดูข้อมูลใน real time database อีกรอบแต่ครั้งนี้จะใส่ตัวของ idToken ไปด้วย
จากรูปหลังจากใส่ตัวของ idToken ลงไปแล้วจะได้ว่าเราสามารถอ่านข้อมูลทั้งหมดใน database นี้ได้ แสดงว่าใน Security Rules ของ real time database นี้ตั้งไว้ว่าทุกคนที่ authen สามารถอ่านได้ซึ่งมันก็มีโอกาศที่มันจะตั้งว่าทุกคนที่ authen จะสามารถเขียนได้เช่นกัน ซึ่งหลังจากดู user ของเราใน database
จะเห็น role เป็น citizen อยู่และจากการกดดู page source เพิ่มเติมของผมในหน้าหลังจาก login มาแล้ว
ได้ความว่าถ้าหากเราเขียน role ตัวเองจาก citizen เป็น admin เราจะสามารถทำอะไรบางอย่างได้ ผมเลยลองเปลี่ยน role ของตัวเองเป็น admin ซึ่ง syntax หรือ Param ต่างๆผมได้มาจาก ChatGPT ล้วนๆเลยครับ ว่าตรงไหนต้องใส่ Param หรือ Token อะไรยังไง โดยการที่เราจะเขียน role ใหม่ให้ตัวเองจะเป็นต้องมี LocalId และต้องใช้ medthod PUT ซึ่ง LocalId ผมก็ได้มาจากรูปก่อนหน้านี้แล้ว และ syntax จะเป็น
https://sth-water-control-default-rtdb.asia-southeast1.firebasedatabase.app/users/(LocalId)/role.json?auth=(idToken)
และมี data เป็น "admin"
จากรูปจะได้ว่าเราเป็น admin แล้วและผมทำการกลับเข้าไปดูที่หน้าเว็บแต่ก็ไม่เห็นมีอะไรเปลี่ยนแปลง🥲 ผมเลยลองไปดูรายละเอียดของ user เราอีกรอบเพื่อความชัวร์ ซึ่งมันจะมีตัวแปรอีกตัวนึงคือ controlUnlocked ที่เป็น boolean อยู่และของผมมันเป็น Flase ผมคิดว่าน่าจะต้องเปลี่ยนอันนี้เป็น True ด้วยมันจึงจะมีอะไรเกิดขึ้น ซึ่งเราก็ใช้ medthod PUT กับ url ที่มี syntax เป็น
https://sth-water-control-default-rtdb.asia-southeast1.firebasedatabase.app/users/(LocalId)/controlUnlocked.json?auth=(idToken)
และมี data เป็น true
ทีนี้ลองกลับไปดูที่หน้าเว็บ
ซึ่งก็จะมีปุ่มปิดระบบระบายนำ้ให้กดหลังจากกดแล้วก็จะได้ flag ออกมาดังรูปเลย
ก็จบไปแล้วนะครับสำหรับข้อนี้ ซึ่งจากการได้ทำข้อนี้ทำให้ได้รู้ว่าไม่ควรทิ้ง config ใดๆเอาไว้เด็ดขาดแม้ว่ามันอาจจะเป็นอะไรที่ดูไม่น่ามีปัญหาแต่ถ้ามันมีคนบางคนที่เขามีความประสงค์ร้ายกับระบบ สิ่งที่เราคิดว่ามันเล็กน้อยก็อาจจะเป็นปัญหาใหญ่ในอนาคตได้ ขอขอบคุณทุกท่านที่อ่านจนจบด้วยครับ และขอบคุณทาง Siam Thanat Hack ที่จัดกิจกรรมดีๆและสนุกแบบนี้นะครับ ถ้าหากผมเขียนอะไรผิดพลาดหรือเขียนงงๆผมต้องขออภัยมา ณ ที่นี้ด้วยครับ ไว้เจอกับ blog หน้าครับผมสวัสดีครับ