Data prior to the default UDG bank

The place for codemasters or beginners to talk about programming any language for the Spectrum.
Post Reply
User avatar
sludge
Drutt
Posts: 33
Joined: Sat Feb 24, 2024 4:38 pm

Data prior to the default UDG bank

Post by sludge »

From reset there is data just before 65368, 40 bytes to be exact.

What is it, and does it expand in size?

I have data stored just below this address and something is corrupting it.

Could it be responsible?
User avatar
ketmar
Manic Miner
Posts: 716
Joined: Tue Jun 16, 2020 5:25 pm
Location: Ukraine

Re: Data prior to the default UDG bank

Post by ketmar »

just look at SP in debugger. ;-)
User avatar
sludge
Drutt
Posts: 33
Joined: Sat Feb 24, 2024 4:38 pm

Re: Data prior to the default UDG bank

Post by sludge »

Stack - 65300, so theres the problem.

Any easy way of remedying the issue or will my data have to be shifted lower down?
User avatar
R-Tape
Site Admin
Posts: 6415
Joined: Thu Nov 09, 2017 11:46 am

Re: Data prior to the default UDG bank

Post by R-Tape »

sludge wrote: Thu Apr 11, 2024 7:22 am Any easy way of remedying the issue or will my data have to be shifted lower down?
Can't you put the stack below your own code? You can go as low as CLEAR 24000, but a bit higher is safer in case you have a large BASIC loader later.
User avatar
ketmar
Manic Miner
Posts: 716
Joined: Tue Jun 16, 2020 5:25 pm
Location: Ukraine

Re: Data prior to the default UDG bank

Post by ketmar »

Code: Select all

CLEAR 24575
now the stack is <$6000.

anyway, it depends of your code. if you're using BASIC, then "CLEAR" at the appropriate address. the BASIC will never use anything out of this range (well, it may corrupt a byte or two at $6000 due to ROM bugs on a very rare occasion. not something you should be afraid of). if you're doing everying in machine code, just set SP to where you want it to be.
User avatar
sludge
Drutt
Posts: 33
Joined: Sat Feb 24, 2024 4:38 pm

Re: Data prior to the default UDG bank

Post by sludge »

How do you set SP from machine code?

Code: Select all

ld sp,44000
User avatar
R-Tape
Site Admin
Posts: 6415
Joined: Thu Nov 09, 2017 11:46 am

Re: Data prior to the default UDG bank

Post by R-Tape »

sludge wrote: Thu Apr 11, 2024 7:48 am How do you set SP from machine code?

Code: Select all

ld sp,44000
Yep just like that Sludge. As long as you're not planning to return to BASIC, you can LOAD SP anywhere your own code will not encroach, and the stack will build down from there. Maybe allow 100 bytes space to be extra careful.

It's best done once at the start and not changed again, unless you're doing something unusual.
User avatar
Joefish
Rick Dangerous
Posts: 2060
Joined: Tue Nov 14, 2017 10:26 am

Re: Data prior to the default UDG bank

Post by Joefish »

R-Tape wrote: Thu Apr 11, 2024 9:08 amIt's best done once at the start and not changed again, unless you're doing something unusual.
That all depends on how tidy your code is, and if you RETurn from every CALL!!! :lol:

You can get away with a lot of mess in a game with, for example, a jump JP directly to your 'You Died' or finally 'Game Over' function, and have that reset the stack pointer, then jump again directly to your title screen, now assuming an empty stack. That way, however deep you might be in a chain of CALLs, you can just jump out the moment something kills you and not have to worry about trimming any spare RETurn addresses off the stack. It does mean any actual stack-related bugs and memory leaks in your game remain hidden for ages though, and maybe only show up when someone better than you plays the game continuously for loads longer!
User avatar
R-Tape
Site Admin
Posts: 6415
Joined: Thu Nov 09, 2017 11:46 am

Re: Data prior to the default UDG bank

Post by R-Tape »

Joefish wrote: Thu Apr 11, 2024 12:26 pm That all depends on how tidy your code is, and if you RETurn from every CALL!!! :lol:

You can get away with a lot of mess in a game with, for example, a jump JP directly to your 'You Died' or finally 'Game Over' function, and have that reset the stack pointer, then jump again directly to your title screen, now assuming an empty stack.
Absolutely! I used to do that, and set the stack pointer back to the top on every game restart. Not because I knew there were bugs, but just in case...

I meant best not to tinker too much until you're confident with how it works. Thinking about it, I don't think I've used the EX SP,(HL) or the ADD SP instructions in anger yet.
User avatar
ParadigmShifter
Manic Miner
Posts: 673
Joined: Sat Sep 09, 2023 4:55 am

Re: Data prior to the default UDG bank

Post by ParadigmShifter »

EX SP, (HL) is a (slow) way of having one extra "register"... push something to the stack, then you can get it back at any time (well, if you haven't pushed anything else in the meantime of course) using EX SP, (HL). It's also handy if you pass parameters to functions using the stack I think. You can also change the return address using it as well.

I'm using it in my scrolling routine where I keep the current draw list pointer on the top of the stack and HL is pointing at data I need for the scrolling... when I process that and want to then add something to the draw list I EX SP, (HL) to do that and when done do it again for the next iteration of the loop.

I probably could have used IX or IY instead though.

ADD HL, SP is obviously useful if you copy data using the stack (which is the quickest way to copy data).
User avatar
Joefish
Rick Dangerous
Posts: 2060
Joined: Tue Nov 14, 2017 10:26 am

Re: Data prior to the default UDG bank

Post by Joefish »

ADD HL,SP is particularly annoying, as far as I'm concerned, for being the wrong way round!

I've never used EX (SP),HL, and I can't imagine where I would, but if you Google it you I found a post I wrote nearly 7 years ago!!! :lol:
When used in the combination POP HL // EX (SP),HL it lets you get the 'top-but-one' value off the stack, and copies the top value of the stack down in its place. You can actually undermine the stack by one slot with these two instructions. It's for programming C-type function calls, where parameters are pushed onto the stack before calling the subroutine. You don't really want to leave them there, but you've got the problem that (from your subroutine's point of view) the RETurn address is at the top of the stack, not the parameters.
So POP HL first gets you the RETurn address off the stack (not much use on its own, but), then EX (SP),HL puts it back, but not before skimming one parameter off the stack from just behind the return address. Keep doing it and you can read off each of those stacked input parameters one-by-one, without wasting another register, and leaving the return address always ready to RET.

As me of many years ago hinted at, the trick is knowing that it's only really any use paired with another instruction, and exactly which instruction to pair it with. I wonder how many other such tricks I've forgotten in that time too? :mrgreen:
User avatar
sludge
Drutt
Posts: 33
Joined: Sat Feb 24, 2024 4:38 pm

Re: Data prior to the default UDG bank

Post by sludge »

Would popping the registers off the stack between levels help?
AndyC
Dynamite Dan
Posts: 1410
Joined: Mon Nov 13, 2017 5:12 am

Re: Data prior to the default UDG bank

Post by AndyC »

sludge wrote: Fri Apr 12, 2024 12:23 pm Would popping the registers off the stack between levels help?
If you're writing "clean" code, the number of things you PUSH and POP should always align (not that CALL is also a PUSH and RET is also a POP) in such circumstances. So you should be reasonably confident that your stack is in the same state when you reach the same point.

In the beginning, I'd definitely aim for that rather than abusing stack operations or just resetting the stack pointer to try and hide bugs. When you're much more confident about exactly the state of the entire system at any point in time, then you can start doing things that require more advanced reasoning.
User avatar
sludge
Drutt
Posts: 33
Joined: Sat Feb 24, 2024 4:38 pm

Re: Data prior to the default UDG bank

Post by sludge »

I seem to have remedied the situation by re-assembling the code from scratch.

No stack issues now, must have been something going on earlier in development.

Edit: The stack is now at 24758.

I'd done a clear 24799 then loaded the binary code dump in and everything now works fine.

Why was the stack under the UDG's before hand? Was it because I didnt CLEAR?
User avatar
Joefish
Rick Dangerous
Posts: 2060
Joined: Tue Nov 14, 2017 10:26 am

Re: Data prior to the default UDG bank

Post by Joefish »

The Spectrum ROM puts the stack wherever the system variable RAMTOP points, which indicates the memory that the ROM and the BASIC interpreter is free to use. When you do a CLEAR, you move that pointer down, to tell the ROM to leave the memory above it alone (you can still POKE the memory above that point, it's just the ROM will no longer use it for the stack, variables, BASIC program listing, etc.). When BASIC starts up, it effectively does exactly that, setting RAMTOP just below the UDGs to tell the BASIC interpreter to keep the UDGs safe from being overwritten.
User avatar
sludge
Drutt
Posts: 33
Joined: Sat Feb 24, 2024 4:38 pm

Re: Data prior to the default UDG bank

Post by sludge »

Not like me to do a CLEAR before I start proceedings but I clearly forgot this time.
Post Reply