After some consideration, I decided to use the SRAM loading method, rather than move all the level loading functions to a seperate bank. While I never finished the other method, it was ugly as sin and would have proabably introduced countless bugs that'd taken ages to track down and fix.
Basically, how it works is pretty simple. All the level pointers and whatnot are still in the main banks, just like the normal game. The actual object and enemy data has been moved into bank one. Also in bank one is a small function that copies the data into SRAM. From that point on, everything runs just like normal.
The total level data for worlds one through eight totals 8319 bytes. Of this, 269 bytes are headers and are stored in the main banks. The other 8050 bytes are the level data and are stored in a dedicated bank to be loaded into SRAM. This basically means that the level data (not including headers) could grow another 142 bytes before we have space issues. Hopefully that won't happen.
I've incorporated worlds 1 - 8, the changes to TerrainRenderBits for the latest patchs, and all the other changes so far. You can get the patch here
While I agree that intensive testing is needed before we release a final patch, I wouldn't consider this patch final. There are still a lot of things to be done. Honestly, despite all the hard work done so far, I think we've really only done the easy bits so far. There are several enemies and powerups yet to be added. Additionally, there are several engine limiations that compromize the accuracy of the port.
Now that the levels are pretty much done. I intend to go straight into gameplay hacking. I'm interested in compiling a list of outstanding differences between the games so that we have a checklist of things that need to be done.
I'm going to clean up my source code and will be making it availible to those who wish to help out with ASM hacking.