Skip to content

[Vengeance] Fix Vengeance Metamorphosis refresh assertion crash#10954

Merged
ToppleTheNun merged 1 commit intosimulationcraft:midnightfrom
taherbert:fix/meta-chaining-assertion
Feb 15, 2026
Merged

[Vengeance] Fix Vengeance Metamorphosis refresh assertion crash#10954
ToppleTheNun merged 1 commit intosimulationcraft:midnightfrom
taherbert:fix/meta-chaining-assertion

Conversation

@taherbert
Copy link
Contributor

@taherbert taherbert commented Feb 15, 2026

Summary

Fixes an assertion crash when Vengeance Metamorphosis is refreshed (e.g. hardcasting Meta during an active Untethered Rage-procced Meta).

Root Cause

Vengeance Metamorphosis (spell 187827) has a Periodic Dummy effect that set_period() picks up during buff_t::init():

Name             : Metamorphosis (id=187827) [Spell Family (107)]
Class            : Vengeance Demon Hunter
Duration         : 15 seconds
Effects          :
#1 (id=273949)   : Apply Aura (6) | Change Model (56)
#2 (id=273950)   : Apply Aura (6) | Increase Health% (133)
#3 (id=283617)   : Apply Aura (6) | Modify Leech% (443)
#4 (id=307168)   : Apply Aura (6) | Add Flat Modifier (107): Spell Effect 4 (32)
#5 (id=314452)   : Apply Aura (6) | Modify Versatility% (471)
#6 (id=329389)   : Apply Aura (6) | Replace Animation (Set) (312)
#7 (id=356685)   : Apply Aura (6) | Periodic Dummy (226): every 2 seconds    <-- this one
#8 (id=775930)   : Apply Aura (6) | Modify Base Resistance (142)
...

Effect 7 is a Periodic Dummy (visual/server logic, not modeled by SimC). During buff_t::init(), set_period() detects this A_PERIODIC_DUMMY subtype and sets refresh_behavior=TICK. However, metamorphosis_buff_t explicitly sets tick_behavior=NONE — so no tick_event is ever created.

When Meta is refreshed, refresh_duration() enters the TICK case and asserts tick_event is non-null → crash.

Chain of events

  1. metamorphosis_buff_t constructor sets buff_period = 0, tick_behavior = NONE
  2. buff_t::init()set_period(min()) scans spell data, finds effect 7 (A_PERIODIC_DUMMY, 2s period)
  3. Overrides buff_period = 2s and sets refresh_behavior = TICK (since !refresh_behavior_overridden)
  4. tick_behavior = NONE prevents tick_event creation in start()
  5. UR grants temporary Meta charge → player hardcasts Meta while UR-Meta active → trigger()refresh()refresh_duration()assert(tick_event) at buff.cpp:1637crash

Fix

Explicitly call set_refresh_behavior(buff_refresh_behavior::DURATION) in the metamorphosis_buff_t constructor. This sets refresh_behavior_overridden=true, so init() → set_period() respects the override and skips the TICK assignment.

Reproduction

A VDH profile with Untethered Rage that casts metamorphosis on cooldown crashes within ~100 iterations:

# BEFORE (crashes):
Assertion failed: (tick_event), function refresh_duration, file buff.cpp, line 1637.
Test profile (click to expand)
ptr=1
demonhunter="MetaChainTest"
spec=vengeance
level=90
race=night_elf
role=tank
position=front
# Any VDH build with Untethered Rage
talents=CUkAAAAAAAAAAAAAAAAAAAAAAAAYMzMjhZkZmBWMDDmZMzYmZmxYGzsNzYbMzyYMDAAAAzyMYYsswEGmZGLAAAAYgBAAzMADAAAgB
head=,id=153840,ilevel=289
neck=,id=153861,ilevel=289
shoulder=,id=153842,ilevel=289
back=,id=153865,ilevel=289
chest=,id=153837,ilevel=289
wrist=,id=153844,ilevel=289
hands=,id=153839,ilevel=289
waist=,id=153843,ilevel=289
legs=,id=153841,ilevel=289
feet=,id=153838,ilevel=289
finger1=,id=153863,ilevel=289
finger2=,id=153862,ilevel=289
trinket1=,id=153860,ilevel=289
trinket2=,id=153864,ilevel=289
main_hand=,id=248072,ilevel=289
off_hand=,id=248062,ilevel=289

actions.precombat=snapshot_stats
actions=auto_attack
actions+=/metamorphosis
actions+=/immolation_aura
actions+=/spirit_bomb,if=soul_fragments>=4
actions+=/fracture
actions+=/soul_cleave

max_time=120
iterations=100
# AFTER (completes successfully):
Simulating... ( iterations=111, threads=12, ... )

@taherbert taherbert changed the title [DH] Fix Metamorphosis refresh assertion crash (buff.cpp:1637) [DH] Fix Vengeance Metamorphosis refresh assertion crash Feb 15, 2026
Spell 187827 (VDH Metamorphosis) has a Periodic Dummy effect (simulationcraft#7, 2s
period) used for visual/server logic not modeled by SimC. During
buff_t::init(), set_period() detects this periodic effect and sets
refresh_behavior=TICK. However, the metamorphosis_buff_t constructor
sets tick_behavior=NONE, so no tick_event is ever created. When Meta
is refreshed (e.g. hardcasting during active Untethered Rage-procced
Meta), refresh_duration() hits the TICK case and asserts tick_event
is non-null, crashing the sim.

Fix: Explicitly set refresh_behavior=DURATION in the constructor so
init() -> set_period() respects the override flag and skips the TICK
assignment.
@taherbert taherbert force-pushed the fix/meta-chaining-assertion branch from c349cd0 to 2333bf6 Compare February 15, 2026 21:21
@taherbert taherbert changed the title [DH] Fix Vengeance Metamorphosis refresh assertion crash [Vengeance] Fix Vengeance Metamorphosis refresh assertion crash Feb 15, 2026
@ToppleTheNun ToppleTheNun merged commit a70b298 into simulationcraft:midnight Feb 15, 2026
120 of 226 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants