[C64] How does a linker work?
category: code [glöplog]
Hi. Can someone please explain (or link URL to help) to me how a linker (also what a IFFL-Linker is) works on the C64-computer?
That is, info that for example the linker most often puts its decrunch-code in the address ~$0400 and so on.
Thanks.
That is, info that for example the linker most often puts its decrunch-code in the address ~$0400 and so on.
Thanks.
you are mixing two things here...
first, normally "linker" in c64 world refers to a tool that merges a bunch of binaries into one binary, often with (at least) some kind of RLE compression added. typically the result will be a new (one) binary that then can be started and which will unpack/relocate the parts and then runs the whole thing.
an "iffl linker" is something entirely different. basically IFFL is a tool that appends a bunch of binaries to each other in order to save space on disk (where each binary would be saved to 256 byte block boundaries - so this mostly makes sense when you have a whole lot of small files). you could think of it like a tar-file.
first, normally "linker" in c64 world refers to a tool that merges a bunch of binaries into one binary, often with (at least) some kind of RLE compression added. typically the result will be a new (one) binary that then can be started and which will unpack/relocate the parts and then runs the whole thing.
an "iffl linker" is something entirely different. basically IFFL is a tool that appends a bunch of binaries to each other in order to save space on disk (where each binary would be saved to 256 byte block boundaries - so this mostly makes sense when you have a whole lot of small files). you could think of it like a tar-file.
The third option is that a linker does what a linker does on any other platform, i.e. combining relocatable object files into an executable binary, which is what for example ld65 in the cc65 suite is doing.
A fourth option is that a "linker" is the person who "links" a demo together, which is a manual (and often tedious if the person/-s who wrote the part code were not disciplined enough to adhere to a set of hard restrictions on memory usage) process involving writing glue code (generic or custom for every two parts), and maybe using an IRQ loader etc.
A fourth option is that a "linker" is the person who "links" a demo together, which is a manual (and often tedious if the person/-s who wrote the part code were not disciplined enough to adhere to a set of hard restrictions on memory usage) process involving writing glue code (generic or custom for every two parts), and maybe using an IRQ loader etc.
Can someone please elaborate, with like an example of 2 files?
If both of those files are on address $080B-$5000.
If both of those files are on address $080B-$5000.
Although I can just stop being lazy, and just test c64-linkers myself, and use WinVice Action-Replay cartridge to save files at certain addresses :)
But with all those disc-magazines released by the scene, I thought that one of those magazines would have some info about linkers. Maybe there is one though, but it's not worth finding it, it's faster to try testing linkers myself.
But with all those disc-magazines released by the scene, I thought that one of those magazines would have some info about linkers. Maybe there is one though, but it's not worth finding it, it's faster to try testing linkers myself.
this sounds like xy-problem
what is it that you really want to do?
what is it that you really want to do?
groepaz, I want to try to make a "mega-demo" with multiple parts, and each part exits to the other part of the demo when the user pushes spacebar.
reread what groepaz and radiant said before and you´ve got your answer (again!) !
you´ve got to code your parts cleverly, meaning arranging memory, so it doesn´t interfere with memory you need for the part that is currently running, then link it after eachother. ;)
example:
part1 starts at $1000, has data from $2000-$3000
part2 cant be located from $1000 to $3000 as this memory is used by part1 already, so code it starting from $3001 and has data from $4000-$5000
the linker just loads stuff where you give it location! one-filing! putting it all in one file!
all of my memory-adresses here are pure nonsense btw! ;) just pointing out the obvious! i got this concept at age of 6 and linked my demomaker-parts one after another until i reached 220 blocks or whatever the limit was/is with 39k ram left! ;) (linking parts from different demomakers was my next step and adding own basic-code the next then, then i lost it, bought an amiga and started assembly!)
its not that hard, learn about hexadecimal(16) after you learned about binary(2), get the connection to decimal, our number system(10)!
when you are done with that you should get it! ;) ask youtube, has many vids about that matter!
you´ve got to code your parts cleverly, meaning arranging memory, so it doesn´t interfere with memory you need for the part that is currently running, then link it after eachother. ;)
example:
part1 starts at $1000, has data from $2000-$3000
part2 cant be located from $1000 to $3000 as this memory is used by part1 already, so code it starting from $3001 and has data from $4000-$5000
the linker just loads stuff where you give it location! one-filing! putting it all in one file!
all of my memory-adresses here are pure nonsense btw! ;) just pointing out the obvious! i got this concept at age of 6 and linked my demomaker-parts one after another until i reached 220 blocks or whatever the limit was/is with 39k ram left! ;) (linking parts from different demomakers was my next step and adding own basic-code the next then, then i lost it, bought an amiga and started assembly!)
its not that hard, learn about hexadecimal(16) after you learned about binary(2), get the connection to decimal, our number system(10)!
when you are done with that you should get it! ;) ask youtube, has many vids about that matter!
and before you ask, yes, there are c-64-linkers that can relocate starting-adresses. you still have to rely on the code using relative-offsets then (for data used), which most-likely ain´t the case! maybe there are linkers out there that even relocate these adresses, i cant remember, its 30+ years ago i did that stuff the last time! ;) but even then, read the freaking manual and fill out those few hexadecimal numbers, have your megademo! :p
if you cant even link i wonder where your parts are coming from, most likely some demomakers! :p
again: read up on number-systems, then learn about how RAM works!
if you cant even link i wonder where your parts are coming from, most likely some demomakers! :p
again: read up on number-systems, then learn about how RAM works!
I've learned how to convert the decimal-hexadecimal-binary number--systems decades ago, but I don't see what that really has got to do with this.
I think about another type of linker than the one you refer to at your first post, because that type of stupid job the linker you speak of can just be done in a machine-code monitor like the one in Action Replay cartridge.
I'm not doing this "mega-demo" (which isn't 100% what I want to do, but I only want to know how that linker I think of works) to be released anywhere, it's just for pure nostalgia for myself, so you don't need to be a jerk about it.
Never mind about this thread, as said, I just better try it myself.
I think about another type of linker than the one you refer to at your first post, because that type of stupid job the linker you speak of can just be done in a machine-code monitor like the one in Action Replay cartridge.
I'm not doing this "mega-demo" (which isn't 100% what I want to do, but I only want to know how that linker I think of works) to be released anywhere, it's just for pure nostalgia for myself, so you don't need to be a jerk about it.
Never mind about this thread, as said, I just better try it myself.
Lol
Quote:
read the freaking manual
"read the freaking manual".
Reading a generic ML-book will NOT help me understand how ECA-Linker works!
I must test that program to see what it does.
Although maybe ECA-Linker is one of those linkers that I thought were stupid (and that it was better to use ActionReplay-monitor instead).
Reading a generic ML-book will NOT help me understand how ECA-Linker works!
I must test that program to see what it does.
Although maybe ECA-Linker is one of those linkers that I thought were stupid (and that it was better to use ActionReplay-monitor instead).
Relax. Just kidding.
If you want a megademo where each part loads after a space press and you don't mind nothing happening while the loading is done (like the old demos did except for maybe border flashing) then you can easelly achieve that with spindle. Spindle takes $c00-$eff for itself, but that's not too much and if you were making separate prgs then you probably start at $800, just move it to $f00.
Now let's say you have 5 parts and all of them start at $F00, then your spin script will look like this
(empty spaces between the files means there's a loader call)
in your code, after you read the keyboard do this
The loader will load your next part and jump into the address you pushed, $f00. That's the start of your next part.. it will just work ;)
Now let's say you have 5 parts and all of them start at $F00, then your spin script will look like this
Code:
part1.prg
part2.prg
part3.prg
part4.prg
part5.prg
(empty spaces between the files means there's a loader call)
in your code, after you read the keyboard do this
Code:
sei ; turn off interrupts
lda #$00
sta $d011 ; turn off the screen to load faster
lda #$0e
pha
lda #$ff
pha
; ^ pushes $F00 - 1 to the stack, the return address
jmp $c90 ; starts loading.
The loader will load your next part and jump into the address you pushed, $f00. That's the start of your next part.. it will just work ;)
there are, as always, multiple ways to achive this. the "modern" way to do it is having a IRQ loader, load stuff in the background, yadda yadda. this is not trivial, especially if you want all the seemless transitions etc that modern demos have.
the 80s way is to simply link parts together until memory is full. basically you first pack a part and make it executable. then the part that runs before that contains a memcopy that move the next part down in memory and jumps to the depacker. just the same way as a crack intro would work. then you pack both and make it executable. and repeat until the memory is full. this is a bit easier, the only thing you need to do is make parts not use the memory where the next parts are in memory.
yaddayadda... that said - none of this is related to using "linkers". those create a single executable, not multipart demos. for example using ECA linker is equal to loading several binary files into memory, saving entire memory, and then RLE pack it.
the easiest solution is likely what golara suggested - although in reality its like shooting a fly with a cannon ball.
the 80s way is to simply link parts together until memory is full. basically you first pack a part and make it executable. then the part that runs before that contains a memcopy that move the next part down in memory and jumps to the depacker. just the same way as a crack intro would work. then you pack both and make it executable. and repeat until the memory is full. this is a bit easier, the only thing you need to do is make parts not use the memory where the next parts are in memory.
yaddayadda... that said - none of this is related to using "linkers". those create a single executable, not multipart demos. for example using ECA linker is equal to loading several binary files into memory, saving entire memory, and then RLE pack it.
the easiest solution is likely what golara suggested - although in reality its like shooting a fly with a cannon ball.
I did a trackmo in a similar to Golara's with Spindle, but for each "part" I'd keep the partswitching / preparing / loading code in a known spot of memory that none of the demo code would otherwise overlap so I could safely load a bunch of stuff into memory over the previous part code & data without worrying about overwriting the code for switching parts.
Quote:
I did a trackmo in a similar to Golara's with Spindle, but for each "part" I'd keep the partswitching / preparing / loading code in a known spot of memory that none of the demo code would otherwise overlap so I could safely load a bunch of stuff into memory over the previous part code & data without worrying about overwriting the code for switching parts.
I started like I described above and now I'm linking the parts proper with music still playing and transitions. It's a lot of work, but spindle still makes it much easier than old loaders.
I did it similar to what has been described above - started with a minimal "loader" part (basically logo/scroller) that loaded the next executable, copied it where it belonged and then launched it, and added that loader to the part before in the same way. Then it gradually got more sophisticated until we planned each part's memory layout so that they would fit together in mem, and the IRQ loader could split what's loaded into chunks (like "$2000-$4000, then $c000-$d000") and un-RLEd on the fly. We sometimes had a few frames of black screen (but with music still running) due to memcpys and codegens, but in general it worked well.
Yeah, the main upside for using Spindle is that you can orchestrate all the memory AND IO writes with the loading script and then just using a single line of code load the next assortment of blobs into anywhere in memory: your code, bitmaps, lookup tables, whatever. it makes orchestrating around the holes in memory very speed efficient and simultaneously you can keep running the music to smooth out the experience.
You will also, for cramming it all in's sake want to order your parts by memory print. So if your smallest demo part uses only $0800-$2000 and your biggest part uses $0800-$a000, then (if they crunch reasonably) you will show the biggest demo part last, so the in-size-decreasing blob of crunched payload (getting smaller with every part that you decrunch) melts while the available space for operation in ram increases. I hope this makes sense.
Thanks for the help!