Glitch City Laboratories Archives

Glitch City Laboratories closed on 1 September 2020 (announcement). This is an archived copy of a thread from Glitch City Laboratories Forums.

You can join Glitch City Research Institute to ask questions or discuss current developments.

You may also download the archive of this forum in .tar.gz, .sql.gz, or .sqlite.gz formats.

Generation I Glitch Discussion

The "(Enemy) learned " effect. - Page 1

The "(Enemy) learned " effect.

Posted by: Spoink
Date: 2016-06-25 19:17:12
What I want to know is why and how this occurs, as well as where the name comes from. I know the stack pointer decreases significantly for every textbox. Here is the video:
[youtube]https://www.youtube.com/watch?v=njs98Ulf7gc[/youtube]

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-10 08:13:08
In first place, where did you get that Pokemon in the very first of the game in the first place
Uhh, E6…
The back sprite of it is devastating, and have a very high chance of locking your game up.
But myself haven't seen this effect before.
My guess is it that, the back Sprite of E6 has corrupt everything (or buttons) with a certain value (which maybe is the Rattata learned <garbage>). Normally after learning a move, (if only that Pokemon learn the move and there's still move slot remaining) you would have exited to the overworld. But seemingly the game could not find a value to return back to the overworld, it would continue to scan through (which is keep learning the move) until it finds the value to go back to the overworld, but it can't, and maybe one of these happened:
The move learnt keep exceeding the limit and eventually crashed
It reached the end.
(I'm new to glitching so maybe all of those are wrong)
But why it's the ENEMY Pokemon learning the move?
Maybe it's jealous of you so it glitches itself too

Re: The "(Enemy) learned " effect.

Posted by: Spoink
Date: 2016-07-10 12:31:59
It actually takes the back sprite from 0xFAC9, which is in RAM. It reads this, and draws too many bytes, corrupting some stuff, and then… I don't know.

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-11 06:27:30
I suspect RNG glitching

Re: The "(Enemy) learned " effect.

Posted by: Torchickens
Date: 2016-07-11 10:08:24
I think this may be related to the sound bank addresses C0EF, C0F0 becoming corrupted (corrupted by the decompression of the glitch Pokémon's sprite). When experimenting with the "stable unstable" Missingno. trick (the first unstable Missingno. you encounter is believed to never freeze the game unless you encounter further), I noticed that a value of 01 would give a "learned"/"trying to learn" effect.

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-11 19:23:21

I think this may be related to the sound bank addresses C0EF, C0F0 becoming corrupted (corrupted by the decompression of the glitch Pokémon's sprite). When experimenting with the "stable unstable" Missingno. trick (the first unstable Missingno. you encounter is believed to never freeze the game unless you encounter further), I noticed that a value of 01 would give a "learned"/"trying to learn" effect.

So you mean it's corrupted to a infinite 01 loop?
It corrupted the enemy Pokemon value?

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-12 00:37:24

What I want to know is why and how this occurs, as well as where the name comes from. I know the stack pointer decreases significantly for every textbox. Here is the video:
[youtube]https://www.youtube.com/watch?v=njs98Ulf7gc[/youtube]

You used gameshark code for that?

Re: The "(Enemy) learned " effect.

Posted by: Torchickens
Date: 2016-07-12 08:59:11


I think this may be related to the sound bank addresses C0EF, C0F0 becoming corrupted (corrupted by the decompression of the glitch Pokémon's sprite). When experimenting with the "stable unstable" Missingno. trick (the first unstable Missingno. you encounter is believed to never freeze the game unless you encounter further), I noticed that a value of 01 would give a "learned"/"trying to learn" effect.

So you mean it's corrupted to a infinite 01 loop?
It corrupted the enemy Pokemon value?


It can get changed to 01 but I don't know if it is an infinite loop, and if you put a halt to the message you may be able to return the sound banks to normal. The sprite decompression causes corruption of the memory, so one of the C0EF/C0F0 (sound bank) addresses may have been corrupted to 01.

All tunes in the game use sound banks: 02 (overworld music), 08 (battle music) 1F (dungeon music) and 20 in English Yellow/28 in Japanese Yellow (special music). But bank 01 is invalid and can lead to the game executing the "learned"/"trying to learn" message for unknown reasons. When some people try the 0120EFC0 0120F0C0 019F5AD3 code to play the Pokémon Yellow unused track, the nurse in the Pokémon Center can disappear and it seems the cause is related to the sound bank being forced to 20 where there are limited valid sounds.

I don't know if invalid sprites can corrupt the enemy Pokémon, except possibly Missingno. in Japanese Yellow who can turn the battle into a Trainer battle if I remember correctly (but I may be wrong).

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-12 09:23:03



I think this may be related to the sound bank addresses C0EF, C0F0 becoming corrupted (corrupted by the decompression of the glitch Pokémon's sprite). When experimenting with the "stable unstable" Missingno. trick (the first unstable Missingno. you encounter is believed to never freeze the game unless you encounter further), I noticed that a value of 01 would give a "learned"/"trying to learn" effect.

So you mean it's corrupted to a infinite 01 loop?
It corrupted the enemy Pokemon value?


It can get changed to 01 but I don't know if it is an infinite loop, and if you put a halt to the message you may be able to return the sound banks to normal. The sprite decompression causes corruption of the memory, so one of the C0EF/C0F0 (sound bank) addresses may have been corrupted to 01.

All tunes in the game use sound banks: 02 (overworld music), 08 (battle music) 1F (dungeon music) and 20 in English Yellow/28 in Japanese Yellow (special music). But bank 01 is invalid and can lead to the game executing the "learned"/"trying to learn" message for unknown reasons. When some people try the 0120EFC0 0120F0C0 019F5AD3 code to play the Pokémon Yellow unused track, the nurse in the Pokémon Center can disappear and it seems the cause is related to the sound bank being forced to 20 where there are limited valid sounds.

I don't know if invalid sprites can corrupt the enemy Pokémon, except possibly Missingno. in Japanese Yellow who can turn the battle into a Trainer battle if I remember correctly (but I may be wrong).

Just asking, is there's more invalid sound banks?

Re: The "(Enemy) learned " effect.

Posted by: Torchickens
Date: 2016-07-12 12:43:34
That's right. You can access 256 with the code 01xxEFC0, 01xxF0C0. I don't know if any are effectively duplicates, however.

Sometimes these invalid sound banks will cause the game to freeze.

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-12 19:33:13

That's right. You can access 256 with the code 01xxEFC0, 01xxF0C0. I don't know if any are effectively duplicates, however.

Sometimes these invalid sound banks will cause the game to freeze.

So in drc's case, most of the value, I think it's just a 01 loop and a crash…
Hmm

It actually takes the back sprite from 0xFAC9, which is in RAM. It reads this, and draws too many bytes, corrupting some stuff, and then… I don't know.

I think there's something missing
What comes after 0xFAC9?

Re: The "(Enemy) learned " effect.

Posted by: TheZZAZZGlitch
Date: 2016-07-15 13:04:12
I accidentally found the answer while investigating the behavior of glitch sound banks.

It is known that encountering unstable Missingno. on Yellow will corrupt sound-related RAM. The "(Enemy) learned"/"(Enemy) is trying to learn" effect occurs if the current sound bank at $C0EF gets corrupted to the value 0x01. Being more exact, the effect activates when the game tries to play any sound from this invalid sound bank.

Sound banks are essentially ROM banks. Before playing a sound, the game switches to the appropriate ROM bank to play the sound from there. Every sound bank has its own handler - a piece of code which tells the game how to actually play the sounds. The game runs through a long list of comparisons to see which bank is currently loaded and execute the correct handler.

Because the programmers never accounted for sound banks other than 0x02, 0x08, 0x0F or 0x20, the game will jump to $6BD4 every time a sound is played from a bank other than 0x02, 0x08 or 0x0F:

[tt]; check if current bank is 02
    cp $2
    jr nz, .checkForBank08
    (…)
.checkForBank08
; check if current bank is 08
    cp $8
    jr nz, .checkForBank1F
    (…)
.checkForBank1F
; check if current bank is 1F
    cp $1F
    jr nz, .bank20
    (…)
; if we got here, the current bank must be 20… right?
.bank20

    ld a, b
    call Handler_6BD4
[/tt]

This causes the game to execute code at $6BD4 every time a sound from an invalid sound bank is played.
What is at this address? It depends on the loaded ROM bank, which depends on the loaded sound bank. It just so happens $6BD4 at ROM bank 0x01 will land in the middle of the LearnMove subroutine:

[tt]LearnMove:
    call SaveScreenTilesToBuffer1
    ld a, [wWhichPokemon]
    ld hl, wPartyMonNicks
    call GetPartyMonName
; 6BD4 is here
    ld hl, wcd6d
    ld de, wLearnMoveMonName
    ld bc, NAME_LENGTH
    call CopyData
    (…)[/tt]

And suddenly, the game will attempt to teach a move!

The move name will depend on the last string loaded into memory, which can be an item (MISSINGNO. learned POTION), a move (MISSINGNO. learned HYPER BEAM), a Pokemon (MISSINGNO. learned CHARIZARD), player's name or rival's name (MISSINGNO. learned ASSFART).

The Pokemon that the move is taught to depends on the wWhichPokemon address ($CF91). The subroutine which calculates poison damage in the overworld (which runs every 4 steps) changes this address, and sets it to the last Pokemon it considered. So, most likely, if you don't go out of your way to manipulate this value, the game will actually attempt to teach a move to the last Pokemon in the player's party.

Which textbox is displayed depends on whether the player's last party Pokemon already has 4 moves ("trying to learn" text) or has less than 4 moves ("learned" text).

Trying to click through the textbox will play a sound, which will trigger another textbox, since the invalid sound bank is still loaded. This causes the game to fall into an infinite loop. After clicking through a lot of textboxes, the stack will eventually overflow, and the game will crash.

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-15 18:49:08

I accidentally found the answer while investigating the behavior of glitch sound banks.

It is known that encountering unstable Missingno. on Yellow will corrupt sound-related RAM. The "(Enemy) learned"/"(Enemy) is trying to learn" effect occurs if the current sound bank at $C0EF gets corrupted to the value 0x01. Being more exact, the effect activates when the game tries to play any sound from this invalid sound bank.

Sound banks are essentially ROM banks. Before playing a sound, the game switches to the appropriate ROM bank to play the sound from there. Every sound bank has its own handler - a piece of code which tells the game how to actually play the sounds. The game runs through a long list of comparisons to see which bank is currently loaded and execute the correct handler.

Because the programmers never accounted for sound banks other than 0x02, 0x08, 0x0F or 0x20, the game will jump to $6BD4 every time a sound is played from a bank other than 0x02, 0x08 or 0x0F:

[tt]; check if current bank is 02
    cp $2
    jr nz, .checkForBank08
    (…)
.checkForBank08
; check if current bank is 08
    cp $8
    jr nz, .checkForBank1F
    (…)
.checkForBank1F
; check if current bank is 1F
    cp $1F
    jr nz, .bank20
    (…)
; if we got here, the current bank must be 20… right?
.bank20

    ld a, b
    call Handler_6BD4
[/tt]

This causes the game to execute code at $6BD4 every time a sound from an invalid sound bank is played.
What is at this address? It depends on the loaded ROM bank, which depends on the loaded sound bank. It just so happens $6BD4 at ROM bank 0x01 will land in the middle of the LearnMove subroutine:

[tt]LearnMove:
    call SaveScreenTilesToBuffer1
    ld a, [wWhichPokemon]
    ld hl, wPartyMonNicks
    call GetPartyMonName
; 6BD4 is here
    ld hl, wcd6d
    ld de, wLearnMoveMonName
    ld bc, NAME_LENGTH
    call CopyData
    (…)[/tt]

And suddenly, the game will attempt to teach a move!

The move name will depend on the last string loaded into memory, which can be an item (MISSINGNO. learned POTION), a move (MISSINGNO. learned HYPER BEAM), a Pokemon (MISSINGNO. learned CHARIZARD), player's name or rival's name (MISSINGNO. learned ASSFART).

The Pokemon that the move is taught to depends on the wWhichPokemon address ($CF91). The subroutine which calculates poison damage in the overworld (which runs every 4 steps) changes this address, and sets it to the last Pokemon it considered. So, most likely, if you don't go out of your way to manipulate this value, the game will actually attempt to teach a move to the last Pokemon in the player's party.

Which textbox is displayed depends on whether the player's last party Pokemon already has 4 moves ("trying to learn" text) or has less than 4 moves ("learned" text).

Trying to click through the textbox will play a sound, which will trigger another textbox, since the invalid sound bank is still loaded. This causes the game to fall into an infinite loop. After clicking through a lot of textboxes, the stack will eventually overflow, and the game will crash.
Nice~

Re: The "(Enemy) learned " effect.

Posted by: ISSOtm
Date: 2016-07-15 18:55:44
TheZZAZZGlitch, did you investigate what code other banks yield ? Otherwise, it might be cool to write a tool that looks through ROM to find whether or not we get cool instructions… and, hopefully, a jp / call somewhere in RAM ?

Re: The "(Enemy) learned " effect.

Posted by: TheUnReturned
Date: 2016-07-15 19:05:37

TheZZAZZGlitch, did you investigate what code other banks yield ? Otherwise, it might be cool to write a tool that looks through ROM to find whether or not we get cool instructions… and, hopefully, a jp / call somewhere in RAM ?

Sadly, most invalid banks tend to crash, so don't expect too much from it. :P