Files
GaCy-GO/docs/scene-challenge-investigation.md
T

24 KiB

ตรวจ teleport และ Endgame — 17 ต.ค. 2026

ห้องรถไฟค้างโหลด — 19 ต.ค. 2026

  • ผู้ใช้รายงาน AA และห้องรถไฟเข้าไม่ได้ โดย log ที่ส่งระบุ Entry 100000352, Floor 10000003 และยังมี heartbeat หลังส่ง EnterScene response/notify แล้ว จึงไม่ถือว่าเข้า Client สำเร็จ
  • Client log รอบ 00:03 พบ AsyncLoad MapProp ล้มเหลวใน _EnterStep2 ขณะโหลด DesignerBackup/Test_Prop_Teleport.bytes, Test_Prop_PTBathSalt.bytes, Test_Prop_PTWeaponRack.bytes และ Test_Prop_PTLightOff.bytes ที่ไม่มีใน bundle index หลักฐานก่อนแก้เก็บใน ignored battle_diagnostics/train-loading-20261019/
  • พบว่า no-teleport adventure entrance เลือก checkpoint แรกของ Floor แม้ MapEntrance/Anchor ระบุจุดเริ่มเฉพาะห้อง แก้ให้ใช้ StartAnchorID ของ Entry บน Floor ที่ตรงกันก่อน checkpoint โดยไม่เปลี่ยน challenge loader หรือ checkpoint teleport ที่ระบุมาโดยตรง การไม่มี Anchor ยังใช้เส้นทางเดิม
  • Capture ก่อนหน้าไม่จบแม้แต่ Floor แรก จึงยังไม่ใช้ข้อมูลบางส่วนทับ metadata ปัจจุบัน เปลี่ยน capture เป็นเฉพาะ Floor ที่ล้มเหลวก่อน อ่านเฉพาะ RuntimeFloor/RuntimeGroup สูงสุด 4 กลุ่มต่อ heartbeat และเก็บ SavedValues ของ dimension เพื่อเทียบสถานะ debug กับ Client โดยไม่โหลดหรือรัน level graph
  • Unit test ของ entrance anchor ผ่านและ build game server ได้ การทดสอบ common ผ่าน แต่ integration TestGatewayHandshakeAndLogin ติด fixture monster event 30124011 ที่ไม่มี Client stage mapping ใน resource ปัจจุบัน จึงยังไม่ถือว่า suite ทั้งหมดผ่าน
  • AA ยังต้องเก็บ request/Client log ของการกดเข้าจริงแยกต่างหาก ไม่สรุปว่ามีสาเหตุเดียวกับห้องรถไฟ และยังรอยืนยันโหลดฉากหลังแก้จาก Client

Capture รอบใหม่ครบ Floor 10000003: กลุ่มไม่ซ้ำ 202 กลุ่ม, Server ที่ยังไม่ลบ 19 กลุ่ม และ SavedValues 34 ชื่อ พบ Client-managed groups 2/25/28/79 อ้างถึง DesignerBackup graph ทั้งสี่ชื่อที่ล้มเหลว โดยมีเงื่อนไข Utility_IsDebug == 1 (CompareType Equal=4 จาก enum ที่ capture ไว้) ขณะที่ native DefaultValue ของ flag นี้เป็น 0 ชุด MaxValue เดิมจึงเปิดกลุ่ม debug ที่ asset ไม่ได้ถูกแพ็กมา ใช้ native defaults ที่ capture สำหรับ Floor นี้และเก็บ min/max/default เป็น rules ไม่แก้แบบลบ PropID 100 ทั้งเกม

ไม่ได้ส่ง floor-wide start anchor ของรถไฟทับทุก Entry เพราะแต่ละห้องมี StartGroup/StartAnchor ของตัวเอง ใช้ --omit-start-anchor ใน exporter แล้วให้ no-teleport adventure path resolve Anchor ตาม Entry ข้อมูล Floor เดิมอีก 36 Floor เปรียบเทียบแล้วไม่เปลี่ยน และเก็บ source policy ของข้อมูลเดิมไว้ การ capture condition เป็นการอ่าน RuntimeGroup และ path ไม่ได้รัน graph ของ debug props หลัง capture นำ probe ของงานนี้ออกจาก scripts/ แล้ว

คำสั่งตรวจ exporter ครอบคลุม incomplete/missing/invalid SavedValues โดยยืนยันว่าไม่เขียนทับ output เดิม, การเก็บ provenance เมื่อ merge และการคง defaults แทน MaxValue ผ่านแล้ว ส่วน Client หลังแก้และ AA ยังรอทดสอบจริง

ผลทดสอบรอบแรกและการกรอง Dimension

ผู้ใช้ยืนยันว่ากดวาร์ปแล้วไม่มีอะไรเกิดขึ้นทั้งห้องและ AA หลังเปลี่ยน defaults รอบแรก Client ไม่แจ้ง DesignerBackup graph error เดิม แต่เกิด MapDef.InitServerGroups NRE เพราะ Group 251 ไม่มีใน MapDef นี่เป็นผลจากการเพิ่ม Server group ตาม RuntimeFloor ทั้งชุดโดยยังไม่กรอง Dimension ไม่ใช่หลักฐานว่าแค่ default ของ Floor แก้ครบแล้ว

การอ่าน RuntimeDimension ระบุว่า Dimension 0 มี GroupIndexList ของตัวเอง (199 GroupID ไม่ซ้ำจาก Floor รวม 202 กลุ่ม) และไม่มี 251 ขณะที่ Dimension อื่นมีข้อมูลกลุ่มนี้ เพิ่ม dimension_groups จาก GroupIndexList/GroupInstanceList ของ Client แล้วกรองทั้งกลุ่มเดิมและเส้นทางเพิ่ม prop จาก metadata ให้ตรง Dimension จริง ไม่ลบหมายเลขกลุ่มแบบเฉพาะ ID Unit test ตรวจว่ากลุ่มจาก Dimension อื่นไม่ถูกใส่กลับผ่าน props พร้อมรักษากลุ่มที่ถูกต้อง ผ่านแล้ว ผลวาร์ปหลังตัวกรองรอบนี้ยังรอ Client ยืนยัน

การตรวจต่อเพิ่ม TestTrainRoomScenePacketMatchesCapturedDimension: สร้าง SceneInfo ของ Entry ที่ผู้ใช้รายงานผ่าน loadScene ด้วย resource ปัจจุบัน แล้วตรวจ membership ของ EntityGroupList, DimensionID, SavedValues, XYZ/rotation ของ entrance และการคงจุดลงเมื่อระบุ checkpoint โดยตรง ผ่านแล้ว การทดสอบนี้สร้างข้อมูลใน session จำลองและไม่ส่งเข้า Client จึงไม่ใช่หลักฐานว่าภาพฉากโหลดได้ ส่วนการเฝ้า Game server และ Client process ที่ยังทำงานอยู่หลัง deploy ไม่พบคำขอ EnterScene ใหม่ในช่วงที่เฝ้า ยังต้องลองวาร์ปจาก Client หลังชุดกรอง Dimension ล่าสุด

ผลยืนยัน AA และจุดลง Party Car

ผู้ใช้ยืนยันหลังชุดกรอง Dimension ว่าวาร์ปเข้าหน้า AA และกดเข้าได้แล้ว แต่ยังไม่ได้ลองเล่น จึงยืนยันเฉพาะเส้นทางเข้า ไม่รวมการต่อสู้หรือ settlement ส่วนการวาร์ปห้องอีกจุดลงห้องนอน MC: log แยกได้ว่า Entry 1000003 (Party Car) ถูกกดก่อน 100000352 (ChallengePeakBattleEntry/AA) โดย 1000003 ไม่มี StartAnchorID และไม่มี Anchor เฉพาะ Entry จึงยังตกไปใช้ checkpoint แรก

เก็บ floor_default_anchor แยกจาก start_anchor ที่ทับทางเข้าทั้ง Floor และใช้เฉพาะ MapEntrance ที่ไม่ระบุ StartAnchorID เท่านั้น Native default ของ Floor นี้ที่ capture ไว้คือ XYZ (-5449,-15289,-12), RotY 180000 ส่วนทางเข้า AA เก็บ anchor เฉพาะเดิม เพิ่ม regression test ทั้ง default Town entrance และ explicit checkpoint ผ่านแล้ว ยังรอผู้ใช้ยืนยันจุดลง Party Car หลังแก้รอบนี้ และรอชื่อห้องเป้าหมายเพื่อยืนยันว่าตรงรายการที่ผู้ใช้ตั้งใจ

ยืนยันผลและปิดงาน — 19 ต.ค. 2026

ผู้ใช้ระบุชัดว่าข้อ 1 คือ Party Car และยืนยันว่า “ตอนนี้ถูกแล้ว” หลังใช้ floor default anchor ส่วน AA ผู้ใช้ยืนยันก่อนหน้านี้ว่าวาร์ปไปหน้า AA และกดเข้าได้แล้ว Log รอบล่าสุดของ Party Car เป็น Entry 1000003, Floor 10000003, XYZ (-5449,-15289,-12) และการเข้า Entry 100000304 สลับกลับ Party Car ใช้ anchor คนละจุดตาม resource โดยไม่ถูกทับเป็นจุดเดียวกัน จึงยืนยันการแก้อาการค้างโหลดและจุดลงผิดสำหรับ Party Car/ทางเข้า AA ที่รายงานได้ครบตามขอบเขตงานนี้

หลักฐานแยกกัน: Client ยืนยันการวาร์ปและเข้าฉากจากผู้ใช้; regression tests ตรวจ Dimension membership, SavedValues, anchor เฉพาะทางเข้า, floor default และ explicit checkpoint พร้อม build ผ่าน การเล่นต่อสู้และ settlement ของ AA ยังไม่ได้ทดสอบ และ integration suite ทั้งหมดยังไม่ถือว่าผ่านเพราะ fixture stage mapping ของ smoke test ที่บันทึกไว้ข้างต้น งานนี้ไม่ได้เปลี่ยนเส้นทาง Battle เพื่ออ้างผลจากการเข้าฉาก

หลักฐานจาก Client

  • Player.log แจ้ง [HoyoGroupManager] 尝试激活的Group不存在, FloorID=20571001 FloorName=Starfroster GroupID=216 ก่อน MapDef.InitServerGroups เกิด NullReferenceException
  • เริ่ม Endgame มี NullReferenceException ที่ ChallengeBossInstance._SyncExtraInfo ผ่าน _OnCmdStartChallengeScRsp
  • จึงมีปัญหาหลัง Client ได้รับแพ็กเก็ต แม้ server จะส่ง response/notify สำเร็จ

สิ่งที่แก้

เทียบซอร์ส PearlSR revision 005d2c12db4781071f4b5b68e8f364587886a710 ใน scene_mgr.zig และ challenge_mgr.zig:

  • Go ใช้ LevelOutputConfig.PlaneType เป็น protocol SceneInfo.GameModeType ทั้งที่เป็นคนละ enum; supplementary scene ยังมีค่าเริ่มต้นเป็น 0 แก้ adventure เป็น mode 1 และ challenge เป็น mode 4 ตามต้นฉบับ
  • เติม world metadata จาก MapEntrance/MazePlane แทน world 0 ของ supplementary scene และนำการแทน world ด้วย ID เฉพาะออกจากสองตัวโหลดนี้
  • โหลด FloorSavedValuesConfig.json ซึ่งมีใน repository แต่ไม่ได้ถูกอ่าน เติมค่าที่ขาดตาม floor โดยรักษาค่าที่ root config ระบุไว้ ส่งให้ทั้ง adventure และ challenge ต้นฉบับใช้ MaxValue เป็นสถานะปลดล็อกเช่นเดียวกัน
  • เพิ่ม CurChallenge.StageInfo.CurBossBuffs สำหรับ AS และ CurStoryBuffs สำหรับ PF พร้อม buff ที่เลือกและ maze buff จาก challenge data; ก่อนหน้านี้ไม่มี StageInfo ทั้งที่ Client ใช้สร้าง instance
  • เปิด state ของ prop/monster group ใน challenge ตามต้นฉบับ และเพิ่ม log scene metadata / challenge state ที่ server_debug.log

ขอบเขตและสิ่งที่ต้องยืนยัน

ยังไม่ได้ยืนยันผลใน Client หลังการแก้ เรายังไม่ทราบว่า Group 216 หายเพราะ scene initialization ที่ผิด หรือ resource/asset คนละ revision; resources/res.json ตรงกับ checkout PearlSR ข้างต้น จึงไม่ได้ลบหรือเปลี่ยนหมายเลขกลุ่มนี้เพื่อหลบ error

ต้องลองวาร์ป Starfroster และ Moment of Joy รวมทั้งเริ่ม Endgame แล้วอ่าน Player.log รอบใหม่ ถ้ายังมี missing group หลังแก้ metadata/saved values ต้องเทียบ floor asset ของ Client ต่อ การเปลี่ยนรอบนี้ไม่ได้รับรอง Peak/Tierce หรือการผ่านทุก node ของ Endgame และยังมี fallback arena/position เก่าใน handlers ที่ต้องตรวจแยก ไม่ได้อ้างว่าเอา hardcode ออกทั้ง repository

ไม่ได้แก้ battle converter, Calyx response, progression/EX หรือ inventory sync ในรอบนี้ จุดย้อนกลับที่ผู้ใช้ยืนยันก่อนเริ่มงานคือ tag stable-2026-10-17-battle-eidolon (commit a681aff)

ผลลองรอบ 19:44 และการแก้ต่อ

ผู้ใช้ยืนยัน AS/PF บางห้องเข้าได้แต่เกิดใต้แมพ, Tierce 30225 ค้าง, PF Starward เข้าห้องได้แต่หลังตีมอนค้าง Weakness และ teleport ของแมพใหม่ยังไม่สำเร็จ ผลนี้ยังไม่ใช่การยืนยันว่ารอบแก้ก่อนสำเร็จ

พบข้อมูลผิดที่ตรวจซอร์สได้:

  • root scene ของ entrance 3014003 ถูกตั้งชื่อ floor 30140001 แต่ MapEntrance ระบุ 30140003; 3012602 ก็ถูกตั้งเป็น 30126001 แทน 30126002 เปลี่ยนให้ single-floor scene ใช้ plane/floor จาก MapEntrance จริง
  • Tierce 30225 ใน challenge_data ระบุ entrance 3012602, monster 2034012, event 420554 แต่ตาราง resource ปัจจุบันระบุ 3012402 / 3024012 / 420584 ตัวโหลดจึงให้ ChallengeMazeConfig, ChallengeMazeTierceConfig และ StageConfig ปัจจุบันมีลำดับความสำคัญเหนือข้อมูล compiled เก่า
  • อ่าน PreChallengeMazeID ของ Tierce จากตาราง: node 0/1 ใช้ข้อมูลสองฝั่งของด่านก่อนหน้า ส่วน node 2 ใช้ด่าน Tierce ไม่เลือกด่าน Tierce ตั้งแต่ node 0 และไม่เดา remap ตามเลข season
  • เปลี่ยน response Tierce ให้ส่งเฉพาะ lineup ของ node ที่ active ตาม upstream
  • นำสูตรตำแหน่งเดิมที่ยก Y ไปหา prop สูงสุดและเลื่อนเข้าหาจุดกำเนิดโลกออก ใช้ Anchor เมื่อมี; ถ้าตารางไม่มี Anchor ใช้ตำแหน่งมอนในกลุ่มจริงแทน ไม่สร้างกลุ่มหรือพิกัดสมมติ หากไม่มีตำแหน่งจะตอบ error พร้อมบันทึกเหตุผล การเกิดตรงจุดมอนนี้ยังต้องตรวจ Client โดยเฉพาะห้องที่ไม่มี Anchor
  • เก็บ BattleConfig ของ AS/PF/MoC/Tierce ใน session; ทีม มอน และ buff มาจาก node/stage ที่เลือก ไม่เขียนทับ custom config ใน persistent และไม่ถูก Freesr reload เปลี่ยน wave ไปกลางห้อง จำนวนรอบใช้ ChallengeCountDown เมื่อระบุไว้ มิฉะนั้นใช้ค่าตั้ง rounds ของผู้ใช้เช่นต้นฉบับ AS/PF ไม่ระบุ countdown ในตาราง
  • log PF Starward รอบสุดท้ายมี SceneCastSkill สอง request ที่ไม่มีทั้ง hit/assist targets เซิร์ฟเวอร์จึงส่ง response ว่างและ ไม่ได้ส่ง BattleInfo ในสอง request นั้น ยังไม่สรุปว่าเป็น error โหลดมอนของ Battle; เพิ่ม request detail เมื่อเกิดใน Challenge เพื่อแยกจากปัญหา wave

ตอนตรวจรอบนี้ Player.log เป็น session หลังเปิดเกมใหม่แล้ว ไม่มี exception ของการกด teleport รอบก่อน จึงยังต้องอ่าน log หลังทำซ้ำโดยไม่ออกเกมก่อน ไม่ได้ลบ Group 216 หรืออ้างว่าการเปลี่ยน floor ของ Challenge แก้ teleport ของ Starfroster/Moment of Joy แล้ว

Build ผ่านและวางที่ root ไม่เท่ากับ Client ผ่าน ยังรอลองหลังการแก้ข้างต้น Peak ยังมีเส้นทาง legacy แยกจาก session config ที่แก้ใน AS/PF/Tierce รอบนี้

ยืนยันต้นเหตุจากตาราง Client หลังลองวาร์ปซ้ำ

หลังผู้ใช้กด Ferry Relay Station เก็บ exception MapDef.InitServerGroups ได้อีกครั้ง แม้ mode/world ถูกต้องแล้ว ตรวจแบบอ่านอย่างเดียวผ่าน GameCoreConfigLoader.LoadRtLevelFloorInfo(MapDef.GetRtFloorInfoPath(plane, floor)) และ GroupInstanceCommonMap พบ:

  • Starfroster floor 20571001 group 216 มี LoadSide=Server, IsHoyoGroup=true, IsDelete=true
  • floor 20572001 group 98 มี IsDelete=true เช่นกัน ทั้งสองกลุ่มยังถูกส่งใน resources/res.json จึงไม่ใช่หลักฐานว่า Client ขาด asset ทั้งแมพ
  • อ่าน StartGroupIndex/StartAnchorID และ AnchorList ของ runtime group ได้จุดเกิดจริงของห้อง Challenge ที่ Anchor.json เดิมไม่มี รวมทั้ง PF 30140003, Starward 30142001, AS 30141001/30132001 และ Tierce 30124002/30126002

เพิ่ม resources/SceneMetadata.json ครอบคลุม 8 floors ที่อ่านจริง พร้อม SHA-256 ของ GameAssembly และ log capture ไม่มี path เครื่องใน resource ตัวโหลดใช้ metadata เฉพาะ Client version ที่ตรง runtime config และจำนวน group ครบ แล้วกรองกลุ่มที่ถูกลบ, เป็น Client-owned หรือไม่มีในตาราง floor นั้น ใช้กฎเดียวกันทุก floor ที่มี metadata ไม่มีเงื่อนไขเจาะจง group 216/98 ใน Go

เติม start anchor และตำแหน่งมอนจาก runtime group โดยแปลง group transform เข้า world และ metres/degrees เป็นหน่วย protocol จุดเกิดของห้องที่ครอบคลุมจึงใช้ Anchor จริง ไม่ต้องยืนตรงมอนหรือเดาความสูง prop ส่วน floor อื่นยังใช้ข้อมูลเดิมและไม่อ้างว่าตรวจทุกแมพแล้ว ตัวแปลง log เป็น resource อยู่ที่ tools/export_scene_metadata.py; รับ log, assembly, client version และ output เป็น arguments และปฏิเสธ group capture ที่ไม่ครบ

Script อ่านข้อมูลชั่วคราวถูกนำออกจาก scripts/ หลังเก็บข้อมูลเสร็จ ไม่เปลี่ยน scene/actor, patch method หรือ save ใน Client ผลวาร์ป/สู้หลัง build ที่รวม metadata ยังรอผู้ใช้ยืนยัน

ผลยืนยันวาร์ปหลัง build ที่รวม metadata

ผู้ใช้ตอบคำถามลอง Ferry Relay Station และ Moment of Joy ว่า ได้แล้ว จึงยืนยันการวาร์ปสองปลายทางนี้ใน Client ได้จริง Log รอบเดียวกันมี entry 2057101 teleport 2057103/2057102 และ entry 2057201 teleport 2057202 โดย group list ไม่มีกลุ่มที่ถูกลบ 216/98 แล้ว ไม่พบ MapDef.InitServerGroups/missing-group error ใน Player.log รอบนี้ ผลนี้ยังไม่ยืนยัน PF/AS/Tierce หรือการตีมอนของ Endgame หลัง build ใหม่

MoC จากสมุด: ค้างท้ายหน้าโหลดในฉากรถไฟ

คำขอ EnterScene ระบุ entrance 100000104, floor 10000000 และ teleport 2206 Client ล้มที่ MapNpcDef.get_ConfigEntityPath ขณะโหลด MapNPC 227-400001 ตาราง RuntimeGroup ของ Client ระบุ NPCID=3001 (ปอมปอม) ในกลุ่มนี้

GetPamSkinData ของ Go เดิมตอบ cur_skin=0 และ unlock_skin_list=[0] แต่ Client PamSkinConfigRow lookup ยืนยันว่า ID0 คืน nil ขณะที่ ID252000 มี ConfigEntityPath จริง และตรงกับค่าปกติใน PearlSR services/scene.zig revision005d2c12

แก้ handler ให้อ่านค่าจาก ProfileConfig.pam_skins/current_pam_skin และตรวจทุก ID กับ PamSkinConfig.json ที่ export จาก Client พร้อม SHA-256 ของ GameAssembly ไม่แก้กลุ่ม227ทิ้ง ไม่เปลี่ยนเส้นทาง Battle ผลการวาร์ปหลังแก้นี้ยังรอ Client ยืนยัน