Famicom Party: Making NES Games in Assembly
book.famicom.party
book.famicom.party
This is something that I find rather off-putting about NESdev. It's very Windows-centric. I'm not used to GNU/Linux being treated as a second-class dev citizen, so I've started a small contribution towards fixing this. I've got a NES tile viewer that I hope will soon be a tile editor, written in PyQt for cross-platform aspirations:
https://hg.sr.ht/~jordigh/Tilerswift/
Development has stalled, but I intend to get back to it.
Nobody seems to care about portability anymore.
https://github.com/jpwhiting/nestool
I made Mac and Windows builds, but I'm not sure yet how best to pre-compile a Linux version that works across distributions - any advice would be appreciated. I assume users can install Qt on their own, so I don't need to do static linking, but I'm not sure what needs to happen beyond that.
I'm in the process of updating the parts of the book that are already there to use it instead of NES Screen Tool. Looking at a few replacements for FamiTracker as well, so no one will need to use WINE to do NES development.
And if your software ever gets popular enough, I expect one day my distribution will just package it for me. I'm happy with this arrangement. Source for niche software, apt/rpm for well-established software.
For my own Qt project, I decided to use PyQt so I could leverage fbs for distribution for Windows where they're not used to source code (Mac can rely on homebrew, as far as I'm concerned):
I like AppImage. Self-contained portable application bundles that should work on most Linux distros.
Back in high school I started getting into Z80 programming on the TI-86 calculator. It was a great platform for learning. It wasn't too complicated to start making simple programs (you could even code directly on the calculator if you didn't mind inputting everything in Hex.) And it was an easy step to start doing graphics. This reminds me of that kind platform.
Sometimes I dream about getting back into ASM for fun. But I have so many other, more practical, things I'd like to learn (I'm not in software development). This is temping, though.
This was fairly annoying to do correctly, to be fair, so I mostly took it as a fun but not all-that-practical feature. It did make for a CTF challenge at iCTF one year, though :)
You're not! The whole thing is very easy to pick up, and there's a lot more documentation nowadays than it used to be.
It's also possible to write useful programs in C, rather than ASM, if you're into that. neslib ( https://github.com/clbr/neslib ) does pretty much everything you need. cc65 ( https://cc65.github.io/ ) is a little quirky but definitely usable.
Have you done much of this? I looked into it a while back and it seemed like the style of C required was very much its own flavor. I'd been wanting to get some experience with Assembly, so I've been (slowly) coming up to speed with that instead.
I'm about 30% through such a project right now, and I have written C code for 6502-family CPUs in the past, although not specifically for the NES. I wouldn't say it's a lot of it, the way I wrote "a lot" of C code for x86, PPC or ARM, but I did definitely did use it to write more than trivial/one-off programs.
> I looked into it a while back and it seemed like the style of C required was very much its own flavor.
As far as cc65 goes, I think it's (mostly?) ANSI-compliant. There are a couple of quirks that you need to be aware of due to the underlying processor, but that's true of any machine. For example, the 6502 lacks native arithmetic instructions for 16- and 32-bit operands, so the compiler won't generate the same kind of code for adding uint8_t operands and adding uint16_t operands.
Then, of course, each compiler has its own quirks :). cc65 doesn't do micro-optimizations, for example, so a lot of the things that we're taking for granted in gcc or clang don't happen automatically in cc65. But that's also true of pretty much any compiler, or, well, at least it used to be true back in the day.
But if you look at the code... it's pretty typical C, I've definitely seen worse. It's possible to write cleaner compilers targeting a much wider subset of C for 6502 than, say, for the 8051. I have absolutely no fond memories about programming that damn thing, in neither ASM, Pascal or C :). Some programmers are a little too inventive for their own good and hide a lot of stuff behind all sorts of macros and whatnot but you can definitely write the kind of C code that would be merged into the Linux kernel if it had a 6502 port.
I don't have any numbers but a lot, if not most of the current crop of indie/retro games aren't written in ASM anymore, at least not on platforms with decent C compilers (NES, SNES, Amiga...). Some games (platformers, side-scrollers) have a sufficiently regular structure that you can write them in Assembly without cursing the day you were born. But games that are less linear than that, or that require even the dumbest autonomous AI that's just a branching instruction smarter than "fire at every 3 seconds, use special ability if player_health < 10", are pretty painful to build without higher-level abstractions. It's definitely possible, it's just that debugging high-level problems ("why is this enemy not switching from offensive to defensive spells when its health drops below 50") in a low-level language is generally above the motivation threshold for things you do on your own time.
Either way, though, knowing your way around Assembly is a good idea. First, touching some assembly code every once in a while is unavoidable. If you're writing games for old enough consoles, NES included, you do occasionally have to touch bootstrap code, and that's all LDA, CRN, HCF and ACDC. Second, most (cross) compilers that you can run today, whether modern or vintage and ran in an emulator, are orders of magnitude worse than gcc, clang or MS C/C++. The fact that compilers orders of magnitude worse than those can still be used to write entire programs is testament to just how good modern compilers are. But useful though they may be, they will still occasionally spit out really bad code, and while knowing enough Assembly to outdo the compiler isn't necessarily required, knowing enough to figure out when the compiler does something dumb and speculate on how to change your code to set it straight is really useful.
FWIW, I learned 6502 assembly first and I am, or I used to be, pretty good at it. Back when I first became interested in this topic, around 2002 or so, there weren't any good compilers available for free (cc65 was around but, as far as I remember, its support for the C64, which is what I cared for back then, wasn't exactly stellar. But I may be wrong, it's been a long time). But the tooling we have today is good enough that I rarely need to write any.
I totally agree with you that just because you _can_ write complex games in Assembly, that doesn't mean you should. I wasn't knocking using C to write NES games at all and won't claim to even begin to know how to address that scenario you laid out.
Anyways, your answer was interesting, informative and full of what sounds like hard won wisdom. Thanks for taking the time to put it together. If you're up to sharing the details, I'd be interested in checking out your games.
The Commodore 64 had an advantage over the Famicom in that it could use cassettes and floppy disks to store the games on and could have them in BASIC or assembly.
Making software is not at all like making a hundred thousand of the same car. It’s more like custom-designing a hundred thousand distinct cars, all with slightly-to-drastically different body shapes, colors, interior features, purposes, and customers.
I'm telling you these are the people to emulate not the factory practices at the other Japanese company
Perhaps if building hardware it can be considered but the whole Toyota model is more about building a management structure around something that really doesn't need one
Stuff like better scanline interrupts and Japan only sound chips (Due to changes to the cartridge port in the west) which you'll probably know about if you decided to listen to Castlevania 2/3's soundtrack on Youtube and found it different to what you remembered. The most common feature was to turn the character rom into a pseudo or even proper RAM so you could use way more graphics and tons of nifty techniques that made stuff better.
Anyway, from a quick sift through this looks like a good site and far nicer than a lot of console development sites. (Sorry coranac, your site is a goldmine but the tiny font against that background gives me a headache)