NWR04B: Still trying to get Linux booting

I'm finally working again on the NWR04B. Right now my focus is trying to get a kernel booting, but I'll be satisfied with any kind of response from the damn thing. Right now, this is as far as I get: Verifying product code......PASS
Boot Product Code!!!
And there it sits until I power cycle the thing. Crap. I've got a pretty steep learning curve here. First off, I haven't worked with the ARM architecture before. Second, I haven't ported Linux (or anything) to another architecture before. (I'm not really porting stuff here -- the hard work was already done by the HRI and Codeman. But the experience would definitely help.) Third, I know very little about assembly; I've got a copy of a really good ARM assembly guide, but I'm just not used to thinking at such a low level. Fourth, I still have not disassembled the bootloader that comes with the existing, vendor-supplied firmware, so I really don't know what state everything's in when the kernel comes up. Fifth, I don't have a JTAG adapter on this thing. As a result, things are going slowly. I started by assuming this sequence of events:

  1. The bootloader sets up the serial port, and decompresses application.bin.
  2. Application.bin is copied to RAM.
  3. The memory map is flipped. (This is in the datasheet. Before, flash memory starts at 0x00000000 and RAM starts at 0x20000000; afterward, it's the other way around.)
  4. The CPU jumps to 0x0, and execution continues from there; this is the Linux kernel initialization and decompression routine.

By disassembling the compressed Linux kernel, I can see that it should work -- ie, there's no need to (say) jump to some random address within the kernel to start working. (It's good to confirm these things...) But the lack of any response at boot time, even with verbose kernel debugging messages turned on, is disheartening. I had a look at the uClinux file arch/armnommu/boot/compressed/head.S, and realized that it might be missing some definitions for putc; this is architecture-dependent, and everything's wrapped in if 0. I tried putting in this:

#elif 1 /* my attempt at cx84200 serial debugging -- assuming that the address for mov is uart0*/
                .macro  loadsp, rb
                mov     \rb, #0x90000000
                .endm
                .macro  writeb, rb
                strb    \rb, [r3, #0]
                .endm

According to the datasheet, the byte at 0x90000000 is where "UARTDR, data read or written from the interface" goes. I'm assuming that means you put a byte there, then magic happens, then that byte is written to the UART. Still no response. I tried taking out the #if/#endif statements around debugging statements, to make it all as verbose as possible -- still nothing. However, with the judicious use of dd I've been able to cobble together a silly little "Hello, world!" in ARM assembly, and I'm able to get that to boot (well, print). This confirmed I had the basic sequence of events correct. What's more, I was able to insert this little bit into various places at the beginning of the kernel, and confirm how far along things were going. The answer is: not very. I've been following along in head.S, and I can see where the debugging information should be printed -- but it just doesn't. What's strange is that by mistake, I inserted helloworld at a non-four-byte boundary -- at byte 70, not 72 -- and then I got a response from a routine in head.S that prints out the first 256 bytes of the uncompressed kernel...and then nothing after that. So close!