This is a bit of a work in progress, but I have created some documentation for the enhanced text mode of the MEGA65. It is still missing the 256-colour mode information, but does explain the core of the memory layout when using 2 bytes per char instead of one.
https://github.com/MEGA65/mega65-core/blob/px100mhz/doc/viciv-modes.md
Hopefully I will be able to expand on this over the coming week, however, this post also marks the end of my annual leave, and thus, sadly, progress will almost certainly slow down again for a while. That said, I am very happy with the progress made over the past six weeks or so. I tried to keep a bit of a progress log for my own personal satisfaction, and while I know I missed a bunch of stuff, it is still quite a list of things that have been dealt with:
24DEC17 - 800x600 video modes work
24DEC17 - Joystick input not working
24DEC17 - CPU bug fixed (Boulder Mark etc runs fine)
24DEC17 - b0 command in UART monitor stops CPU on BRK instruction
25DEC17 - $DC00 always reads as zeros
26DEC17 - Fix sprite fine horizontal placement problem
26DEC17 - PDM/Sigma-Delta audio output working
26DEC17 - Kickstart looks for file "NTSC", if not present, switches to PAL
26DEC17 - CIA clock speed is always 1MHz, except in C128 2MHz mode.
26DEC17 - Fix CIA clock halving bug
26DEC17 - $D016 smooth scroll in 320H mode fixed
26DEC17 - CIA is 1MHz even in 2MHz mode
26DEC17 - NumLock on PS/2 / USB keyboard is now "joystick lock" (WASD+shift, cursors+space)
27DEC17 - Got rid of single stray pixel by right border
27DEC17 - Make On-screen-keyboard X position variable via $D619
27DEC17 - C= + <- key to toggle matrix mode on C64 keyboards
27DEC17 - On-screen-keyboard again shows key events
28DEC17 - Stop kickstart screen format getting clobbered when setting PAL/NTSC
28DEC17 - Fix doubled first row of pixels in chargen/bitmap
28DEC17 - Joystick input on MEGA65 r1 PCB
28DEC17 - Stereo channel swap/merge on $D6F9
29DEC17 - Speed up PCB synthesis via map command line option
29DEC17 - Find bug stopping IEC serial working (was driving lines high)
29DEC17 - Find hardware errata; No SRQ line on IEC serial port
29DEC17 - Make joystick controlled quick-synthesising debug rig
29DEC17 - Right SID is now on right channel
29DEC17 - $D612 bits 6-7 allow rotation of joystick inputs by 180 degrees
30DEC17 - $D03x can no longer be written over in VIC-II mode
30DEC17 - IEC serial port works, at least partially
30DEC17 - Digital audio outputs reduced volume to prevent amplifier complaining
30DEC17 - Find and fix timer b and ISR reading bugs in CIAs
31DEC17 - Investigate and fix lack of shift register in CIAs for C65 DOS fast mode
31DEC17 - C65 disk drive check succeeds without shift-register status kludge
01JAN18 - VIC-II Bitmap mode displays last pixel row as though from next char row
01JAN18 - Fix trimming of sprite pixels vertically and when expanded horizontally
01JAN18 - Cartridge port accesses now work
01JAN18 - Cartridge ROMs now map to memory
02JAN18 - International Soccer cartridge works
03JAN18 - Ultimax-Mode cartridges work
04JAN18 - 1351/POT interface proof-of-concept
04JAN18 - 3.5" floppy drive proof-of-concept
05JAN18 - dotclock on cartridge port sped up from 4MHz to ~6.5MHz
06JAN18 - dotclock on cartridge port correctly at 8MHz
06JAN18 - 1351 mouse/POT inputs work correctly, and are in MEGA65 VHDL
07JAN18 - 16-colour sprite mode
07JAN18 - Sprite rendering bugs fixed
08JAN18 - Top row of pixels in sprite can now collide
08JAN18 - Sprite:sprite collision detection much more accurate (one Impossible Mission bug remains)
08JAN18 - Sprite Y position corrected
09JAN18 - Ethernet can received (but frames lack CRC!)
09JAN18 - 1581 repaired, and 3.5" test disks prepared
09JAN18 - Ethernet TX phase correction for r1 PCB (but CRC received by nexys still wrong)
09JAN18 - Ethernet TX and RX fully working on both r1 PCB and Nexys4DDR
10JAN18 - Resistor pull-up pack for floppy interface
10JAN18 - Floppy drive reads from real disk
10JAN18 - Worked out how to decode floppy data
10JAN18 - Real drive tracks F011 activity
10JAN18 - Step and spin-up delays set for real floppy drive
11JAN18 - MFM gap finder
11JAN18 - MFM gap quantiser
11JAN18 - MFM byte decoder
11JAN18 - 1581 sector decoder
11JAN18 - CRC16
11JAN18 - Real floppy mode for F011
12JAN18 - MFM decoder decodes real disks (but MEGA65 doesn't get the data for some reason)
13JAN18 - Amiga/1351 mouse / joystick auto detection
13JAN18 - Copy 1351 mouse status to Amiga mouse status to avoid mouse cursor jumping
14JAN18 - Fix problems with buffer writing when reading from FDC
14JAN18 - $14 F011 command waits instead of steps, as expedted
15JAN18 - Can load sector from FDC into sector buffer (but job doesn't complete properly)
15JAN18 - Ethernet MIIM now working
15JAN18 - FDC sector rotation bug fixed
15JAN18 - sector buffer collapsed to one physical copy (saves 2 BRAMs)
15JAN18 - FDC sector reading now works with C65 ROM (can DIR a real disk)
20JAN18 - Pull in Daniel England's diskmenu improvements
19JAN18 - Fix FDISK bugs for system partition creation
20JAN18 - Implement basic system partition reading
20JAN18 - Use CTRL,ALT and SHIFT to control boot process instead of FPGA switches
21JAN18 - Enhanced DMA list mode (and update FDISK, Kickstart to use it)
21JAN18 - Multiplier in CPU
21JAN18 - Hold RESTORE for HyperTrap, instead of double-tap (no stray NMI caused)
26JAN18 - Config program loads config from SD card
26JAN18 - Psygnosis owl sprite demo
26JAN18 - Fix logo display bug with new enhanced DMA
28JAN18 - Config utility works and saves and loads
28JAN18 - V400 character rendering bugs fixed
28JAN18 - V400 border position bugs fixed
29JAN18 - Virtual D81 F011 reading works again
29JAN18 - VD81 (buffered) writing seems to work
The main thing is that the hardware has been tested well enough to allow for the second revision of the motherboard to be designed and assembled over the next couple of months.
Wednesday, 31 January 2018
Raster splits in BASIC
I have started trying to generate some documentation on the advanced character modes of the MEGA65's VIC-IV video controller, and in the process decided to write some simple example programs, so that people can more easily see what each feature does, and experiment with them themselves. To make the tests more accessible, I figured that I would write them in BASIC, rather than assembly language.
The trick was, if I am changing the character mode, and yet want to have some kind of useful information on the display, then I would need a raster split, so that part of the screen could be in the special mode, but the information in ordinary text mode. But hang on, I am programming in BASIC, not assembly, so how can possibly have a raster split? The answer is with 50MHz! What used to take a second on a C64 can be done in a single frame on the MEGA65, and what used to take a frame, can be done in just a few rasters. Thus I figured that if I used the rather under rated WAIT command in C64 BASIC, I could probably get a stable enough raster split for this purpose. It wont be perfect, but it will still be pretty good.
Wait is a bit of a strange beast. It takes three arguments: The address to wait for certain values on, a value to AND with the contents of the location, and a value to XOR before doing the AND. So:
WAIT 53265,128,0
Will wait while (PEEK(53265) XOR 0) AND 128) = 0
That is, it will wait until the VIC-II(or III or IV) is near the bottom of the screen, and:
WAIT 53265,64,0
will wait while (PEEK(53266) XOR 0) AND 64) = 0
That is, until the VIC-II/III/IV has just about finished drawing the top two lines of text. If I only want to put text in the top line, that's close enough for my little test program.
So, lets put this together into a little loop that changes the border colour based on where we are on the screen:
2000 R = 53248 + 17: R2 = R + 1
2010 REM WAIT FOR BOTTOM OF SCREEN
2020 WAIT R,128,0: POKE 53280,0
2050 REM WAIT UNTIL AFTER A COUPLE OF ROWS OF TEXT
2060 WAIT R,128,128: POKE 53280,2
2070 WAIT R1,64,0: POKE 53280, 1
2090 GET A$: IF A$="" GOTO 2010
Line 2000 works out $D011 and $D012, the two raster indicator registers on the VIC-II in decimal, so that we can easily use them in the routine.
Line 2020 waits until bit 7 of $D011 = 1, i.e., for the bottom part of the screen to start being drawn, and then sets the border colour to black.
Line 2060 waits until we are out of the vertical fly back with $D011=0 again, and then sets the border colour to red.
Line 2070 waits for raster #64, i.e., almost the end of the second row of text, and then makes the border white.
So, if this works, we should see white border for most of the screen, but red at the top, and black at the bottom, and indeed we do:
So now you don't need to learn assembly language to do a raster split any more ;)
The trick was, if I am changing the character mode, and yet want to have some kind of useful information on the display, then I would need a raster split, so that part of the screen could be in the special mode, but the information in ordinary text mode. But hang on, I am programming in BASIC, not assembly, so how can possibly have a raster split? The answer is with 50MHz! What used to take a second on a C64 can be done in a single frame on the MEGA65, and what used to take a frame, can be done in just a few rasters. Thus I figured that if I used the rather under rated WAIT command in C64 BASIC, I could probably get a stable enough raster split for this purpose. It wont be perfect, but it will still be pretty good.
Wait is a bit of a strange beast. It takes three arguments: The address to wait for certain values on, a value to AND with the contents of the location, and a value to XOR before doing the AND. So:
WAIT 53265,128,0
Will wait while (PEEK(53265) XOR 0) AND 128) = 0
That is, it will wait until the VIC-II(or III or IV) is near the bottom of the screen, and:
WAIT 53265,64,0
will wait while (PEEK(53266) XOR 0) AND 64) = 0
That is, until the VIC-II/III/IV has just about finished drawing the top two lines of text. If I only want to put text in the top line, that's close enough for my little test program.
So, lets put this together into a little loop that changes the border colour based on where we are on the screen:
2000 R = 53248 + 17: R2 = R + 1
2010 REM WAIT FOR BOTTOM OF SCREEN
2020 WAIT R,128,0: POKE 53280,0
2050 REM WAIT UNTIL AFTER A COUPLE OF ROWS OF TEXT
2060 WAIT R,128,128: POKE 53280,2
2070 WAIT R1,64,0: POKE 53280, 1
2090 GET A$: IF A$="" GOTO 2010
Line 2000 works out $D011 and $D012, the two raster indicator registers on the VIC-II in decimal, so that we can easily use them in the routine.
Line 2020 waits until bit 7 of $D011 = 1, i.e., for the bottom part of the screen to start being drawn, and then sets the border colour to black.
Line 2060 waits until we are out of the vertical fly back with $D011=0 again, and then sets the border colour to red.
Line 2070 waits for raster #64, i.e., almost the end of the second row of text, and then makes the border white.
So, if this works, we should see white border for most of the screen, but red at the top, and black at the bottom, and indeed we do:
So now you don't need to learn assembly language to do a raster split any more ;)
Displaying 256 colour images and 16 colour sprites
The material in this post is from Daniel, who has been working hard on tools for preparing and displaying 256-colour images on the MEGA65, using the full-colour text mode, where each pixel is represented by a byte, and where characters can be re-used to save space when drawing a low-entropy image. But over to Daniel...
As you all might know, I've been working on a few demos getting a few things tested and working... At first, I needed a nice sprite pointer and there were some problems I couldn't solve so I handed the tests over to Paul and he sent me back an awesome demo. After implementing my pointer, I was quite inspired and wanted to try to improve on what he had started. So I upped-the-ante and released a three sprite animation with a few more frames. I had to generate all of the data myself, including extracting each frame of the animation. I wrote a GUI tool to handle the data conversion because I couldn't find Paul's for looking. I had tried to do a five sprite version but I couldn't figure out the memory utilisation at the time but I'll will be revisiting it in the future.
Next, I wanted to get some 320x200x256 images on the screen. Quite some time ago (gosh, is it two years already?) I built a tool to convert images into a format that I could use with the 16bit tile feature on the Mega65. I dragged it out and tried to get it working. I found out that it was well out-of-date and didn't work. In fact, when I built the tool, the feature was still in the design stage and it was never actually used to produce an image on the M65 (at the time the C64GS).
After some consultation with Paul I started to rework the tool. I also had to build a loader program for the M65 side. After quite a bit of trial-and-error and annoying Paul with some silly questions, I finally got an image on the screen. I didn't actually release that demo because it was too simple and seemed to have a few problems. And... The image was a very basic outline of something that I might want to reuse later...
I needed to test the colour use so I made the very pretty spectrum example. I just used a gradient brush in GIMP to paint out the gradient and converted it to 256 colours using dithering which I don't normally do because I thought it might be nice for this example. However, when I tried to convert it, my tool came back with some 800 tiles. That was impossible for my loader to handle at the time because it required that the tiles be stored in a contiguous block. So, I reworked the image, copying sections such that it is actually comprised of only two unique sections (one of them repeated three times). I was worried it would look terrible but I think its okay.
[Ed: each 8x8 tile in this mode requires 64 bytes, one byte for each pixel, so 800 tiles requires 51,200 bytes, so some would need to go under IO or under ROMs to fit in the C64 memory map].
So the general principle was now sound but I needed to be sure that the tile reuse by foreground colour replacement was actually working. I came up with the idea of making a little Andy Warhol tribute using the breadbox image which I had made some time ago. For something that seems so simple, I had to struggle with GIMP to get it to do what I wanted. I had to munge the images a few times before I got what I was looking for. In the end, I think its rather pretty and the colour substitution was working. I did have a problem with the flip bits initially but I checked some information Paul gave me and corrected the problem in my tool.
Now onto the big stuff... In staring the process I had wanted to put a 1000 tile image on the screen. That's a unique tile for every location, a real 320x200x256 image and I wanted to have sprites, too. I had already made the image I wanted to use (a very long process in Photoshop, let me tell you! I recoloured the whole image - every single detail and that was just the start!). It was actually for a little animation demo I did a long time ago...
I wanted to replicate some of that demo but my tool and loader were not up to the task in any shape or form. Firstly, I was having to modify my loader for each individual image and secondly, my tool could only output to a contiguous block of RAM. If you look at the memory map for the M65, you'll see that there just isn't a contiguous 64kB block of RAM that you can use when you need screen RAM and so on, too.
When I was asking Paul about it he quite casually said, "just don't make it contiguous and use whatever memory you can." Hmm... I don't know if he knew the complexity of what he was suggesting but I knew what I had to do. I had to rework my tool to and image format to allow for segment based mapping. I also wanted it to be able to be processed by a generic loader because I was really over all of the complicated calculations I had to do to get the data loading loops to work and it just wasn't something that could be sold as a solution.
I built a test application that would allow me to specify free, reserved and system segments in the memory range that I could use. It actually came together rather quickly. Next, I planned how to change my data format and make it loadable by a generic loader. I then incorporated my changes into my conversion tool. That wasn't quite so easy... I found some issues with the GUI messaging that were preventing me from knowing when the user had actually done the mapping, of all things that could go wrong. Other than a few minor bugs, the tool side was completed more quickly than I had anticipated.
Next I had to write the loader. Oh boy. My loaders up to that point where horribly hacked so I pretty much had to start from scratch. That was okay because the data format had changed quite significantly. After a few calculation problems, complete and utter system failures (I'm sure it was my fault), copy-and-paste bugs and a weird, you have to do this, in this order thing, I got the loader working. It took me a few more hours to do than I'd planned for though but it didn't stop me being ecstatic at my success!
While I was waiting for something, I'd written the small sprite test that I wanted to use in the final demo. I quickly incorporated it into my image program (and bothered Paul with silly questions again which I figured out before he got back to me) and voila! A true 320x200x256 image with 16 colour sprites! 1000 unique tiles and 256 colours!
There is still a bug though... In the middle of the screen, offset a little to the right, a tile is incorrect. I have no idea why. I'll need to consult Paul. Also, as the sprite approaches the bottom border, it gets a strange warping effect on it. Something Paul will need to fix.
My tool allows for arbitrary sizes of images (up to 255x255 cells). You may be able to guess what's comming next...
I'll release the updated version of my tool and loader in a day or two. I promised someone I would be available tomorrow and have a day away from coding.
ARGH! I was supposed to sleep but I just had to add the music I wanted, too... Please enjoy "Beachparty" by Zyron. It sounds a little off pitch, though. My humble apologies!
Edit: I got up first thing in the morning to look at why that tile was broken. I finally figured it out and with some direction from Paul was able to fix it. [Ed: The sprite pointer list that normally lives directly after the screen memory was in the middle of one of the tiles. Fortunately, this list can be moved around easily on the MEGA65 by writing to $D06C/D/E, so that was easily solved.]
And the following video shows all three loading and being run on the MEGA65. Apologies for the effectively silent audio level in the video, as I don't have my decent camera here, and the microphone on my phone is half dead.
As you all might know, I've been working on a few demos getting a few things tested and working... At first, I needed a nice sprite pointer and there were some problems I couldn't solve so I handed the tests over to Paul and he sent me back an awesome demo. After implementing my pointer, I was quite inspired and wanted to try to improve on what he had started. So I upped-the-ante and released a three sprite animation with a few more frames. I had to generate all of the data myself, including extracting each frame of the animation. I wrote a GUI tool to handle the data conversion because I couldn't find Paul's for looking. I had tried to do a five sprite version but I couldn't figure out the memory utilisation at the time but I'll will be revisiting it in the future.
Next, I wanted to get some 320x200x256 images on the screen. Quite some time ago (gosh, is it two years already?) I built a tool to convert images into a format that I could use with the 16bit tile feature on the Mega65. I dragged it out and tried to get it working. I found out that it was well out-of-date and didn't work. In fact, when I built the tool, the feature was still in the design stage and it was never actually used to produce an image on the M65 (at the time the C64GS).
After some consultation with Paul I started to rework the tool. I also had to build a loader program for the M65 side. After quite a bit of trial-and-error and annoying Paul with some silly questions, I finally got an image on the screen. I didn't actually release that demo because it was too simple and seemed to have a few problems. And... The image was a very basic outline of something that I might want to reuse later...
I needed to test the colour use so I made the very pretty spectrum example. I just used a gradient brush in GIMP to paint out the gradient and converted it to 256 colours using dithering which I don't normally do because I thought it might be nice for this example. However, when I tried to convert it, my tool came back with some 800 tiles. That was impossible for my loader to handle at the time because it required that the tiles be stored in a contiguous block. So, I reworked the image, copying sections such that it is actually comprised of only two unique sections (one of them repeated three times). I was worried it would look terrible but I think its okay.
[Ed: each 8x8 tile in this mode requires 64 bytes, one byte for each pixel, so 800 tiles requires 51,200 bytes, so some would need to go under IO or under ROMs to fit in the C64 memory map].
So the general principle was now sound but I needed to be sure that the tile reuse by foreground colour replacement was actually working. I came up with the idea of making a little Andy Warhol tribute using the breadbox image which I had made some time ago. For something that seems so simple, I had to struggle with GIMP to get it to do what I wanted. I had to munge the images a few times before I got what I was looking for. In the end, I think its rather pretty and the colour substitution was working. I did have a problem with the flip bits initially but I checked some information Paul gave me and corrected the problem in my tool.
Now onto the big stuff... In staring the process I had wanted to put a 1000 tile image on the screen. That's a unique tile for every location, a real 320x200x256 image and I wanted to have sprites, too. I had already made the image I wanted to use (a very long process in Photoshop, let me tell you! I recoloured the whole image - every single detail and that was just the start!). It was actually for a little animation demo I did a long time ago...
I wanted to replicate some of that demo but my tool and loader were not up to the task in any shape or form. Firstly, I was having to modify my loader for each individual image and secondly, my tool could only output to a contiguous block of RAM. If you look at the memory map for the M65, you'll see that there just isn't a contiguous 64kB block of RAM that you can use when you need screen RAM and so on, too.
When I was asking Paul about it he quite casually said, "just don't make it contiguous and use whatever memory you can." Hmm... I don't know if he knew the complexity of what he was suggesting but I knew what I had to do. I had to rework my tool to and image format to allow for segment based mapping. I also wanted it to be able to be processed by a generic loader because I was really over all of the complicated calculations I had to do to get the data loading loops to work and it just wasn't something that could be sold as a solution.
I built a test application that would allow me to specify free, reserved and system segments in the memory range that I could use. It actually came together rather quickly. Next, I planned how to change my data format and make it loadable by a generic loader. I then incorporated my changes into my conversion tool. That wasn't quite so easy... I found some issues with the GUI messaging that were preventing me from knowing when the user had actually done the mapping, of all things that could go wrong. Other than a few minor bugs, the tool side was completed more quickly than I had anticipated.
Next I had to write the loader. Oh boy. My loaders up to that point where horribly hacked so I pretty much had to start from scratch. That was okay because the data format had changed quite significantly. After a few calculation problems, complete and utter system failures (I'm sure it was my fault), copy-and-paste bugs and a weird, you have to do this, in this order thing, I got the loader working. It took me a few more hours to do than I'd planned for though but it didn't stop me being ecstatic at my success!
While I was waiting for something, I'd written the small sprite test that I wanted to use in the final demo. I quickly incorporated it into my image program (and bothered Paul with silly questions again which I figured out before he got back to me) and voila! A true 320x200x256 image with 16 colour sprites! 1000 unique tiles and 256 colours!
There is still a bug though... In the middle of the screen, offset a little to the right, a tile is incorrect. I have no idea why. I'll need to consult Paul. Also, as the sprite approaches the bottom border, it gets a strange warping effect on it. Something Paul will need to fix.
My tool allows for arbitrary sizes of images (up to 255x255 cells). You may be able to guess what's comming next...
I'll release the updated version of my tool and loader in a day or two. I promised someone I would be available tomorrow and have a day away from coding.
ARGH! I was supposed to sleep but I just had to add the music I wanted, too... Please enjoy "Beachparty" by Zyron. It sounds a little off pitch, though. My humble apologies!
Edit: I got up first thing in the morning to look at why that tile was broken. I finally figured it out and with some direction from Paul was able to fix it. [Ed: The sprite pointer list that normally lives directly after the screen memory was in the middle of one of the tiles. Fortunately, this list can be moved around easily on the MEGA65 by writing to $D06C/D/E, so that was easily solved.]
And the following video shows all three loading and being run on the MEGA65. Apologies for the effectively silent audio level in the video, as I don't have my decent camera here, and the microphone on my phone is half dead.
Tuesday, 30 January 2018
MEGA65 configuration utility / Konfigurations Programme
After lots of posts full of words, here is one mostly full of pictures. Daniel has been beavering away on a configuration utility for the MEGA65, so that you can set all the important settings, without having to load anything. Daniel has done a great job, and freed me up to work on various other things, mostly bug fixing various little things, in the meantime.
Die letzten Posten haben alle viele Wörter gemacht, hier ist mal einer mit vielerr Bildern. Daniel ist bis zum Umfallen geschuftet und ein "Konfigurations-Utility" für den MEGA65 geschrieben. Jetzt kann man alle wichtigen Eingstellungen vornehmen, ohne irgendwas dafür laden zu müssen. Daniel hat das richtig gut gemacht und mir damit Gelegenheit gegeben, verschiedene Dinge voranzubringen, meist nötige Bug-Fixes.
So first, we start by holding C= and resetting the MEGA65, and then pressing ALT while still holding C= after kickstart says "release control to continue booting". This makes the Utility Menu appear. Think of it like Batman's utility belt, only 8-bit, and generally lacking in the shark repellant department:
Als Erstes: Wenn wir beim Starten oder Resetten C= drücken, meldet das Kickstart "Release control to continue booting". Wenn stattdessen die ALT-Taste dazu gedrückt wird, erscheint das Utility-Menü. Das muss man wie Batmans Ausrüstungsgürtel vorstellen, nur in 8-bit, und natürlich ohne die Haiabwehr-Sachen:
When we press 1 to load the new configuration utility, it quickly appears, and can be controlled by mouse or keyboard to check and set various configuration options. The following few photos show the current contents of the screens (which is likely to change over time).
Wenn wir die 1 drücken, kommt ziemlich schnell das Konfigurations-Utility. Es wird entweder mit der Maus oder per Tastatur bedient, um damit alle möglichen Konfigurationsoptionen einzustellen. Die nächsten Bilder zeigen den gegenwärtigen Inhalt dieses Bildschirms (was sich in Zukunft sehr wahrscheinlich noch ändern wird).
Then when you are finished checking and setting everything, you can save and exit as you wish. There is a confirmation prompt for added comfort.
Nach der Anschluss der Einstellungen kann man (wenn man möchte) speichern und die Konfigurationen verlassen. Es gibt eine Abfrage, die einen an die verschiedenen Speichermöglichkeiten erinnert.
Friday, 26 January 2018
Testing 16-colour sprite mode
What originally started out as debuging the 16-colour sprite mode to allow for a more colourful mouse pointer in the MEGA65 configuration program ended up going a bit further.
Daniel wrote a test program for 16 colour sprites to reproduce some strange behaviour that he was seeing. The mistake in the VHDL was simple, and quickly fixed. In the process, we also tweaked the transparent colour selection, so that it is now the foreground colour of the sprite.
Having fixed that and a few other little problems, I wanted to make a more interesting test of the 16-colour sprites. So I decided it would be fun to animate a well-known 16-colour sprite assembly from the Amiga.
The first step was to produce the sprite data in the correct format. To do this, I added a new mode to the pngprepare program in the MEGA65 source tree, that takes a PNG with 16 or less colours, and produces a nice binary format that can be used natively on the MEGA65, including the palette entries, and information about how tall the sprites are, so that extended height mode can be used.
Then I modified Daniel's program to use that binary format, and to animate the resulting sprites. The result is quite nice:
This uses just two of the eight sprites, side-by-side to get the 32 pixel horizontal resolution. The sprite itself is at 320x200.
So then I started thinking about using some multiplexing to get more owls on the screen. I can easily use 3 pairs of sprites to get three owls on without multiplexing (the 4th pair could be used, but I would have to do a bit more palette fiddling, and it is already late). As the owl is $57 pixels tall, and I can have three overlapping owls, this means one every 29 (decimal) rasters. I could also trim the sprites vertically (at the moment the blank space above and below the own as it moves is part of the sprite, wasting about 50% of the height in any one frame), so it would be quite easy to get more than double this number of owls on the screen. But, let's have a few more owls anyway, for good measure:
I gave in and did the palette fiddling I mentioned, so there are four pairs of sprites, which are then multiplex 3x over (parts are concealed by the top and bottom borders). So there are probably 8 or 9 whole 32x86 pixel 16-colour owls worth -- all using the 8 hardware sprites, not Amiga-style BOBs. It would also be possible to horizontally multiplex the sprites (this is easier on the MEGA65 than on the C64, in part because the CPU is 50x faster, and there is DMA to splat the sprite X positions during a raster line), and the blank space above/below the owls could also be trimmed out to optimise things, allowing fairly easily to have about 4x more owls on the screen if we wanted to. But I'll leave that fun to someone else...
Daniel wrote a test program for 16 colour sprites to reproduce some strange behaviour that he was seeing. The mistake in the VHDL was simple, and quickly fixed. In the process, we also tweaked the transparent colour selection, so that it is now the foreground colour of the sprite.
Having fixed that and a few other little problems, I wanted to make a more interesting test of the 16-colour sprites. So I decided it would be fun to animate a well-known 16-colour sprite assembly from the Amiga.
The first step was to produce the sprite data in the correct format. To do this, I added a new mode to the pngprepare program in the MEGA65 source tree, that takes a PNG with 16 or less colours, and produces a nice binary format that can be used natively on the MEGA65, including the palette entries, and information about how tall the sprites are, so that extended height mode can be used.
Then I modified Daniel's program to use that binary format, and to animate the resulting sprites. The result is quite nice:
This uses just two of the eight sprites, side-by-side to get the 32 pixel horizontal resolution. The sprite itself is at 320x200.
So then I started thinking about using some multiplexing to get more owls on the screen. I can easily use 3 pairs of sprites to get three owls on without multiplexing (the 4th pair could be used, but I would have to do a bit more palette fiddling, and it is already late). As the owl is $57 pixels tall, and I can have three overlapping owls, this means one every 29 (decimal) rasters. I could also trim the sprites vertically (at the moment the blank space above and below the own as it moves is part of the sprite, wasting about 50% of the height in any one frame), so it would be quite easy to get more than double this number of owls on the screen. But, let's have a few more owls anyway, for good measure:
I gave in and did the palette fiddling I mentioned, so there are four pairs of sprites, which are then multiplex 3x over (parts are concealed by the top and bottom borders). So there are probably 8 or 9 whole 32x86 pixel 16-colour owls worth -- all using the 8 hardware sprites, not Amiga-style BOBs. It would also be possible to horizontally multiplex the sprites (this is easier on the MEGA65 than on the C64, in part because the CPU is 50x faster, and there is DMA to splat the sprite X positions during a raster line), and the blank space above/below the owls could also be trimmed out to optimise things, allowing fairly easily to have about 4x more owls on the screen if we wanted to. But I'll leave that fun to someone else...
Improving the ethernet adapter
I have made a couple of improvements to the ethernet interface in the MEGA65:
1. The Ethernet PHY MIIM registers now work, so you can find out if the ethernet port is connected, and at what speed, for example. This was not too tricky, except that I had the bus running at 2x the correct speed, because I read the 400ns edge-to-edge time, i.e., half-clock time, as being the clock cycle time. After that, it was all peachy.
2. MAC address filtering, including recognising broadcast and multi-cast ethernet frames.
This is basically an extension of the "allow bad-CRC" flag, together with adding registers to store the MAC address of the machine, so that ethernet frames can be filtered if the CRC is bad, if the frame is not broadcast, not multicast, and not addressed to the MEGA65. The broadcast and multicast checks can be independently disabled, if you really want to cut down on processing load, by only listening for packets addressed to the machine itself.
After chasing down the bugs introduced in the process, it now all works. LGB wrote a nice little ethernet test utility, that responds to ARP requests and PING. This now works very nicely, and I can ping the MEGA65 from my linux laptop:
$ ping 192.168.1.65
PING 192.168.1.65 (192.168.1.65) 56(84) bytes of data.
64 bytes from 192.168.1.65: icmp_seq=1 ttl=64 time=0.316 ms
64 bytes from 192.168.1.65: icmp_seq=2 ttl=64 time=0.304 ms
64 bytes from 192.168.1.65: icmp_seq=3 ttl=64 time=0.304 ms
64 bytes from 192.168.1.65: icmp_seq=4 ttl=64 time=0.336 ms
64 bytes from 192.168.1.65: icmp_seq=5 ttl=64 time=0.306 ms
^C
--- 192.168.1.65 ping statistics ---
5 packets transmitted, 5 received, 0% packet loss, time 4085ms
rtt min/avg/max/mdev = 0.304/0.313/0.336/0.016 ms
$ arp -na? (192.168.178.1) auf 38:10:d5:29:66:ef [ether] auf wlp1s0
? (192.168.1.65) auf 02:47:53:65:65:65 [ether] auf enp0s31f6
$
Here we can see the program running on the MEGA65, with counters on the top line for the number of packets received (RX), transmitted (TX), ARP packets replied to (ARP), PING packets replied to (PING) and UDP packets seen (UDP).
Below that is the MAC address of the MEGA65 displayed three times over:
1. The Ethernet PHY MIIM registers now work, so you can find out if the ethernet port is connected, and at what speed, for example. This was not too tricky, except that I had the bus running at 2x the correct speed, because I read the 400ns edge-to-edge time, i.e., half-clock time, as being the clock cycle time. After that, it was all peachy.
2. MAC address filtering, including recognising broadcast and multi-cast ethernet frames.
This is basically an extension of the "allow bad-CRC" flag, together with adding registers to store the MAC address of the machine, so that ethernet frames can be filtered if the CRC is bad, if the frame is not broadcast, not multicast, and not addressed to the MEGA65. The broadcast and multicast checks can be independently disabled, if you really want to cut down on processing load, by only listening for packets addressed to the machine itself.
After chasing down the bugs introduced in the process, it now all works. LGB wrote a nice little ethernet test utility, that responds to ARP requests and PING. This now works very nicely, and I can ping the MEGA65 from my linux laptop:
$ ping 192.168.1.65
PING 192.168.1.65 (192.168.1.65) 56(84) bytes of data.
64 bytes from 192.168.1.65: icmp_seq=1 ttl=64 time=0.316 ms
64 bytes from 192.168.1.65: icmp_seq=2 ttl=64 time=0.304 ms
64 bytes from 192.168.1.65: icmp_seq=3 ttl=64 time=0.304 ms
64 bytes from 192.168.1.65: icmp_seq=4 ttl=64 time=0.336 ms
64 bytes from 192.168.1.65: icmp_seq=5 ttl=64 time=0.306 ms
^C
--- 192.168.1.65 ping statistics ---
5 packets transmitted, 5 received, 0% packet loss, time 4085ms
rtt min/avg/max/mdev = 0.304/0.313/0.336/0.016 ms
$ arp -na? (192.168.178.1) auf 38:10:d5:29:66:ef [ether] auf wlp1s0
? (192.168.1.65) auf 02:47:53:65:65:65 [ether] auf enp0s31f6
$
Here we can see the program running on the MEGA65, with counters on the top line for the number of packets received (RX), transmitted (TX), ARP packets replied to (ARP), PING packets replied to (PING) and UDP packets seen (UDP).
Below that is the MAC address of the MEGA65 displayed three times over:
Thursday, 25 January 2018
Upgrading the SD card controller: SDHC cards now work!
This little job has been a LONG time coming. We knew several years ago that we wanted at least SDHC support (and ideally, SDXC, as well) for the MEGA65.
The limitation was in the open-source VHDL SD card controller that we were using. Fortunately, some nice people have improved that controller, so that it now supports SDHC cards, i.e., SD cards between 4GB and 32GB in size. SDXC begins from 64GB and goes up to 2TB, which seems to be rather larger than one might need for the MEGA65, however, SDHC cards will start to be harder to get in due course, so we want to add support for SDXC. For now, the job is about SDHC cards, however.
The first step was to pull in the new version of the SD controller in VHDL. This proved to be not too hard, as it really is a re-vamp of the old one we were already using. There were some changes to the handshaking, which took a little work to get right, and it also assumed you knew at compile time whether you had an SD or SDHC card -- whereas we want to be able to work out what is plugged in when you turn on the computer.
With all that working, it was then time to fix FDISK/FORMAT, and Kickstart itself. With a little effort, both of these now reliably detect whether you have an SD or SDHC card, and can prepare and boot from either. Of course, the SDHC cards are quite a bit faster as well, which is nice. I am using only a class 4 card, and it is very noticeably faster than the old 2GB SD card I was using.
Also, preliminary testing suggests that the unrealiability issues I was seeing with the SD card interface have also been resolved with the use of this new interface, which is very welcome, since they were stopping me from making a functional freeze function. So, finally, I can get back to doing exactly that.
The limitation was in the open-source VHDL SD card controller that we were using. Fortunately, some nice people have improved that controller, so that it now supports SDHC cards, i.e., SD cards between 4GB and 32GB in size. SDXC begins from 64GB and goes up to 2TB, which seems to be rather larger than one might need for the MEGA65, however, SDHC cards will start to be harder to get in due course, so we want to add support for SDXC. For now, the job is about SDHC cards, however.
The first step was to pull in the new version of the SD controller in VHDL. This proved to be not too hard, as it really is a re-vamp of the old one we were already using. There were some changes to the handshaking, which took a little work to get right, and it also assumed you knew at compile time whether you had an SD or SDHC card -- whereas we want to be able to work out what is plugged in when you turn on the computer.
With all that working, it was then time to fix FDISK/FORMAT, and Kickstart itself. With a little effort, both of these now reliably detect whether you have an SD or SDHC card, and can prepare and boot from either. Of course, the SDHC cards are quite a bit faster as well, which is nice. I am using only a class 4 card, and it is very noticeably faster than the old 2GB SD card I was using.
Also, preliminary testing suggests that the unrealiability issues I was seeing with the SD card interface have also been resolved with the use of this new interface, which is very welcome, since they were stopping me from making a functional freeze function. So, finally, I can get back to doing exactly that.
Subscribe to:
Posts (Atom)












