546 - bombShield(int a, int script)
Sets the bomb invulnerability flag (a=0 false, a=1 true), the caller's ANM script will change to script when a bomb is active.
611 - etEx(int etId, int async, int type, float a, float b)
Adds bullet transformation to bullet manager etId, Transformation of flag type determines the specific behaviour of the bullet. Documentation can be found here.
BulletEffectType-67108864 - etExDelay(string et, string isAsync, string time)
Hide the bullet for time frames. During this time, it will not move, will be invisible and won't have a hitbox. If used as a first transformation, can be used to delay when the bullet actually appears.
6 - isDelayedSpawn
While this flag is set, the bullet will be invisible and not have a hitbox. This flag is cleared once the delay timer ends.
4 - short_timer
Integer value between -1 and 15 inclusive (by default -1). If non-negative, shooters using short_timer shoot their bullets and timer increments by 1 per frame until 15 is reached. Once 15, timer reset to -1 or 0 depending on Z key state.
5 - long_timer
Integer value between -1 and 120 inclusive (by default -1). If non-negative, shooters using long_timer shoot their bullets and timer increments by 1 per frame until 120 is reached. Once 120, timer reset to -1 or 0 depending on Z key state.
91 - floatTime(int slot, float var, int time, int mode, float start, float final)
In time frames using mode mode, variable var changes from start to final. slot is used to set the slot to be used by this ins, every enemy has 8 slots.
-9980 - F1
Local float variable, inherited by spawned enemies.
-9984 - I1
Local integer variable, inherited by spawned enemies.
-9989 - ANGLE_PLAYER
Angle from the enemy to the player.
-9962 - BOSS_Y
Final Y position of the boss.
-9990 - PLAYER_Y
Player's Y position.
-9963 - BOSS_X
Final X position of the boss.
-9991 - PLAYER_X
Player's X position.
81 - circlePos(float varX, float varY, float angle, float radius)
Performs following operation: varX = cos(angle) * radius and varY = cos(angle) * radius
-9981 - F0
Local float variable, inherited by spawned enemies.
300 - enmCreate(string sub, float x, float y, int hp, int score, int item)
Creates an enemy using subroutine sub at coordinates (x, y) (relative to position of the parent), health of created enemy is hp, score bonus is score and item drop is item.
601 - etOn(int etId)
Shoots bullet(s) using properties from bullet manager etId.
23 - wait(int time)
Stops sub execution for time frames.
1 - delete()
Returns to the top of current call stack.
2 - GAME_SPEED
The value controls by how much faster the game speed is run. This variable is often set to a number between 0 and 1. This value is often changed when a (final) boss dies or when a photo is taken. Its default value is 1.
-9985 - I0
Local integer variable, inherited by spawned enemies.
-9983 - I2
Local integer variable, inherited by spawned enemies.
-9982 - I3
Local integer variable, inherited by spawned enemies.
-9954 - ENEMY_HP
Enemy's current HP.
3 - goheiExists
A flag that determines if a gohei exists on-screen or not. Flag is set to true by active gohei. Flag is set to false if gohei goes off-screen or is despawning.
-9926 - GI0
Global integer value. Value is initialised to 0 on stage load but not on stage reset.
-9925 - GI1
Global integer value. Value is initialised to 0 on stage load but not on stage reset.
-9924 - GI2
Global integer value. Value is initialised to 0 on stage load but not on stage reset.
-9923 - GI3
Global integer value. Value is initialised to 0 on stage load but not on stage reset.
Yoshika Revival Bug
Specifications
- Versions:
1.00a -
1.00b -
1.00c
- Difficulty:
Easy -
Normal -
Hard -
Lunatic -
Extra-Overdrive - Mode:
Main game -
Practice mode -
Spell practice - Shottype:
Reimu -
Marisa -
Sanae -
Youmu
What happens
Sometimes when Yoshika is dead, she will not be revived by Seiga: Seiga continues to shoot bullets as if Yoshika is still alive. This behaviour only happens on the first two spell cards of Seiga regardless of difficulty. Additionally, this behaviour is most commonly encountered in practice mode (especially using practice tools), but it is also possible to encounter this issue in a real run.

How it happens
While the cause of this bug is the same on both the first spell-card and second spell-card, the set-ups are slightly different:
Spell 1
- On this stage, reset while Yoshika is alive on any of the following sections:
- 240 frames after Seiga's first spell started.
- 160 frames after Seiga's second spell started.
- During Seiga's third non-spell started.
- 160 frames after Seiga's third spell started.
- Then reset the stage by doing Esc + R. DO NOT restart the stage from the main menu, but do it from the pause menu instead.
- Reach Seiga's first spell and kill Yoshika within the first 240 frames of this spell-card.
Note that this bug works with replays too. This means that if you have a functional Stage 4 replay that finishes Seiga's first spell within 240 frames, it's possible to encounter this bug when you restart the stage from the pause menu. By restarting, the replay desyncs on Seiga's first spell, but this can easily be fixed by going back to the main menu and replaying the replay.
Spell 2
- On Seiga's first spell, finish the spell-card while Yoshika is still alive.
- Within the first 160 frames of Seiga's second spell, kill Yoshika.
Unlike the bug with the first spell-card, this bug does not involve resetting the stage, meaning you can have a full game replay that encounters this issue.
Why it happens
Global variables
The game uses global variables (e.g. GI0, GI1, GI2, GI3) for certain patterns. When a stage is loaded, every global variable's value is set to 0. Here's an example of how the initialisation would look for every global integer variable:
GI0 = 0;
GI1 = 0;
GI2 = 0;
GI3 = 0;
This global variable initialisation is done every time a new stage is loaded into the memory, which is when you load a stage through either a stage transition or from the main menu. Note that this initialisation is not done when you reload the stage by e.g. Esc + R. For our interest, this issue is related to how global variable GI1 is accessed and written to by the game's code.
In the context of this bug, only the global variable GI1 is used. This global variable GI1 can have two values in this stage:
, which is the state when Yoshika is dead on attacks Spell 1, Spell 2, Non-spell 3, and Spell 3GI1= 0, which is the state when Yoshika is alive on attacks Spell 1, Spell 2, Non-spell 3, and Spell 3GI1= 1
This variable is used by Seiga, who will proceed to do a different action depending on the attack the value of GI1 was changed on. For example, when on the third non-spell, Seiga shoots more knives at the player, or when GI1 = 0 on the first spell, Seiga will resurrect Yoshika.GI1 = 0


Accessing the global variable GI1
GI1In this stage, only Yoshika is able to write to . On the other hand, Seiga reads GI1 and does certain actions depending on its value. The next section explains how GI1 is accessed on the second non-spell and second spell-card using ECL code.GI1
Below the following subroutines are denoted:
Boss2being Seiga's second non-spell.BossMiyako2being Yoshika, which is called right asBoss2is called.BossMiyako2Deadbeing Yoshika's death subroutine, i.e. this gets called when Yoshika dies on the second non-spellBossCard2being Seiga's second spell-cardBossMiyakoCard2initbeing Yoshika, which is called right asBoss2is called.BossMiyakoCard2also being Yoshika, but this is called 160 frames afterBossMiyakoCard2initis called. When called,is set toGI11.BossMiyakoCard2Deadbeing Yoshika's death subroutine afterBossMiyakoCard2is called. When called,is set toGI10.
To get more comfortable with these subroutines, some examples will be provided below with how the order of subroutines executed would look like in various scenarios.
Example 1 - Normal
Imagine you are fighting against Seiga and you are on her second non-spell and you do not kill Yoshika. Once the second spell starts, you stop shooting. The order of subroutines executed would be as follows:
Once BossMiyakoCard2 is called, the value of is set to GI11. Below is a table that summarises the value per subroutine.GI1
| Subroutine | value |
|---|---|
| Boss2 | 0 or 1 |
| BossMiyako2 | 0 or 1 |
| BossCard2 | 0 or 1 |
| BossMiyakoCard2init | 0 or 1 |
| BossMiyakoCard2 | 1 |
Example 2 - Normal
Imagine you are fighting against Seiga and you are on her second non-spell and you kill Yoshika. Once the second spell starts, you kill Yoshika two times. The order of subroutines executed would be as follows:
Once BossMiyakoCard2 is called, the value of is set to GI11. When Yoshika dies, BossMiyakoCard2Dead is called, and the new value of is GI10. Note that when Seiga revives Yoshika, Seiga calls for BossMiyakoCard2init. This subroutine then calls for BossMiyakoCard2, which continues the spell-card. In this example, reviving Yoshika is done twice.
Below is a table that summarises the value per subroutine.GI1
| Subroutine | value |
|---|---|
| Boss2 | 0 or 1 |
| BossMiyako2 | 0 or 1 |
| BossMiyako2Dead | 0 or 1 |
| BossCard2 | 0 or 1 |
| BossMiyakoCard2init | 0 or 1 |
| BossMiyakoCard2 | 1 |
| BossMiyakoCard2Dead | 0 |
| BossMiyakoCard2init | 0 |
| BossMiyakoCard2 | 1 |
| BossMiyakoCard2Dead | 0 |
| BossMiyakoCard2init | 0 |
| BossMiyakoCard2 | 1 |
Example 3 - Bugged
Imagine you are fighting against Seiga and you are on her second non-spell and you do not kill Yoshika. Once the second spell starts, you kill Yoshika within 160 frames of the spell starting. The order of subroutines executed would be as follows:
In this example, the subroutines BossMiyakoCard2 and BossMiyakoCard2Dead are never called because Yoshika was killed before they were able to be called. This means that Yoshika never writes to , meaning the behaviour of Seiga depends on an earlier subroutine that set GI1. GI1
Below is a table that summarises the value per subroutine.GI1
| Subroutine | value |
|---|---|
| Boss2 | 0 or 1 |
| BossMiyako2 | 0 or 1 |
| BossCard2 | 0 or 1 |
| BossMiyakoCard2init | 0 or 1 |
| BossMiyako2Dead | 0 or 1 |
For example, if the player ended spell-card 1 with Yoshika dead (so ), then Seiga will revive Yoshika in the earlier given example. However, if the player ended spell-card 1 with Yoshika alive (so GI1 = 0), then Seiga will not revive Yoshika.GI1 = 1

Why this issue cannot happen elsewhere
While it may seem that more of Seiga's patterns could be affected, this is not the case.
Non-spell 1 & Non-spell 2
This non-spell does not read or write to , so it never bugs out.GI1
Non-spell 3
This non-spell does read and write to . However, once the third non-spell GI1Boss3 is called, Yoshika's subroutines are immediately called and her death subroutine is immediately overwritten meaning there is no window of time provided in which it is possible to achieve this bug.
Spell-card 3
Similarly, this spell has the same logic as spell-cards 1 and 2. However, the bug cannot be triggered on this spell because of the death call back on non-spell 3 (BossMiyako3Dead) setting to GI10. This is unlike the death call backs of non-spell 1 and non-spell 2, which do not change the value of .GI1
Spell practice mode
This bug cannot happen on Spell practice mode. This is because when Yoshika is loaded first, she does not have a death call back. This behaviour means that she can have negative HP without her dying, meaning the spell-cards work as normal.
Conclusion
Links
Replays
- Replay
Nylilsaby "Nylilsa". Lunatic, Youmu, 1.00c. 「February 11, 2025」. Download link (Note: Glitch showcase on Spell 2)
Videos
- TRDario. 「February 20, 2025」. "Yoshika respawn bug on spell 1 and 2" https://www.youtube.com/watch?v=9apV8MBpaok
All Ten Desires pages: | |
|---|---|
| Incorrect boss position during spell practice · Misalignment of timer · Slowdown Item Duplication · Yoshika Revival Bug · Invincibility Desync · Marisa Desync | All Ecl-related pages: |