High color bitmap on the SNES

Discussion of hardware and software development for Super NES and Super Famicom.

Moderator: Moderators

Forum rules
  • For making cartridges of your Super NES games, see Reproduction.
93143
Posts: 1194
Joined: Fri Jul 04, 2014 9:31 pm

Re: High color bitmap on the SNES

Post by 93143 » Sun Feb 07, 2016 7:05 pm

I've never had it not work on my SNES, reset or cold boot, reload or rerun. It's rock-solid every time. Maybe it's the rev.1 PPU2 causing the problem? Or maybe the Super Everdrive is shielding me from the failure mode somehow?
Sik wrote:What are you using as an anchor point on the SNES?
I'm kinda cheating, actually. This is IRQ-driven with no special measures; hence the jitter byuu found.

There's one DMA transfer per scanline, which means the data is exactly what fits on the screen (28KB) in a linear bitmap format. Originally I was going to trigger the DMA with timed code, which would have required me to use an IRQ at the top of the screen followed by a cycle-counted stagger-stepping technique based on an H-counter read to align to a particular dot (I've done this before). And once I found out that DMA always targets the main screen (on my SNES) I started thinking about exploiting that to align the CPU to half-dot precision. Unfortunately, if I've correctly understood the way DMA aligns itself, just writing straight to the active layer would inevitably result in a one-dot offset between scanlines, and the offset pattern would change every two frames.

So I set up a loading pattern on the main screen and a display pattern on the subscreen, turned on colour addition, and set it to clip the main screen to black before math (which results in the subscreen being displayed by itself). So the DMA now writes to the CGRAM index pointed to by the (invisible) main screen, and a bit later the subscreen displays the colour. This allows DMA writes to happen with up to three dots worth of jitter with no visible artifacting, and it also allows me to start the DMA before the beginning of the active scanline and buffer enough colours to get through the DRAM refresh (I could have done that with the live-write technique, but it would have required a less straightforward data format).

What it looks like to me is that the failure cases seem to involve the DMA targeting the subscreen instead of the main screen. This would actually be trivial to detect without checking the version number. If the alignment is consistent within a single runtime (ie: only a reset or power cycle can change it), it may be possible to fix this...
byuu wrote:DRAM refresh moving around between hardware revisions.
How much? fullsnes doesn't mention this...
Espozo wrote:I forgot, why can't using color math work the way you have it 93143?
Because I need an uninterrupted loading pattern on the main screen, and it has to be invisible.

Using timed code to write directly to a display layer would probably allow colour math, but because of the DMA alignment issue (8 master clocks since reset, and a scanline isn't a multiple of that; neither is every other frame) I wouldn't get nice static vertical columns like you see here. This might not matter as much for a video mode, but it'd probably look goofy for a still.
You know, what's the technical explanation as to why this goes by every 4 pixels instead of every 2 like on the Genesis?
DMA on the Mega Drive goes at two pixels per word, just like on the SNES, but the word size is 16-bit. VRAM only accepts half a word, which is why screen coverage per VBlank is almost identical to the SNES (a touch lower, actually, but you can keep going into active display at a much slower rate if you don't mind the CPU hit). But CRAM and VSRAM take 16-bit words, meaning you can DMA a 9-bit value to CRAM in one shot.

The SNES has an 8-bit data bus, and the DMA unit is on the CPU, so it's 8-bit no matter what. This means you need two writes to update a colour, and at two pixels per byte that's four pixels.

User avatar
Drew Sebastino
Formerly Espozo
Posts: 3503
Joined: Mon Sep 15, 2014 4:35 pm
Location: Richmond, Virginia

Re: High color bitmap on the SNES

Post by Drew Sebastino » Sun Feb 07, 2016 7:30 pm

93143 wrote: VRAM only accepts half a word
You mean if it could accept a whole word, you could upload twice as much tile data? What happens to the unused 8 bits?
93143 wrote:I wouldn't get nice static vertical columns like you see here.
You mean like some lines would be shifted over a pixel or something like that?

tepples
Posts: 22017
Joined: Sun Sep 19, 2004 11:12 pm
Location: NE Indiana, USA (NTSC)
Contact:

Re: High color bitmap on the SNES

Post by tepples » Sun Feb 07, 2016 8:03 pm

I tried it again on my 1/1/1 and it loaded just fine, nice and stable. Reset and it's glitchy as ass. Reset again and "No Signal!" Reset again and it's fine. But I can see some banding, especially on the brown table at top center and on Leah's black shirt (at left). In 256-color, one could use dithering to make this banding less visible, but not so much luck when pixels are that wide (PAR: 32:7).

Now as for the reason I chose to try it in the first place: I can't see a brown line at top, but it might be blending with the black of the border. (My TV shows 226 lines, including one line of border at top and bottom.)

Sik
Posts: 1589
Joined: Thu Aug 12, 2010 3:43 am

Re: High color bitmap on the SNES

Post by Sik » Sun Feb 07, 2016 8:28 pm

Espozo wrote:
93143 wrote: VRAM only accepts half a word
You mean if it could accept a whole word, you could upload twice as much tile data? What happens to the unused 8 bits?
I thinl that one refers to the MD case... the VRAM bus is 8-bit, so words take twice as long to be transferred. So yeah, nothing is lost, it's just wasteful.

You can configure it to use 16-bit VRAM and indeed that'll double the transfer bandwidth (oh boy). This setup also supports twice as much VRAM. The only reason this wasn't used is because it probably was too expensive (Sega engineers thought it wasn't much of a gain...)

EDIT: also wait what, "no signal"?

93143
Posts: 1194
Joined: Fri Jul 04, 2014 9:31 pm

Re: High color bitmap on the SNES

Post by 93143 » Sun Feb 07, 2016 8:31 pm

tepples wrote:I tried it again on my 1/1/1 and it loaded just fine, nice and stable. Reset and it's glitchy as ass. Reset again and "No Signal!" Reset again and it's fine.
I've tried various combinations of boot/reset and load/reload with my SNES+Super Everdrive, and I still can't get it to not work. It could be the Everdrive, or it could be the system revision...

No signal? That doesn't sound like a software bug on my end... the PPU should be outputting a signal of some description no matter what, right?
But I can see some banding, especially on the brown table at top center and on Leah's black shirt (at left).
That's just what 15-bit colour looks like. Only way out is dither, and it'd have to be done with reference to the original true-colour image (and, as you note, probably with the assistance of a higher-resolution luminance mask, which I can't use with this version of the technique).
I can't see a brown line at top
Neither can I, and I can see the top line of the image just fine. Especially in Revenant's stable image, but on your glitchy ones too. Not that that matters, since this ROM isn't the one that cuts off the top line... More importantly, I can see the bottom line on Revenant's image, which should rule out a downshift. If you can see it too, then either the rev.3 PPU2 (which I understand is the standard byuu is targeting) is causing a problem with the top line, or higan is doing it wrong.

This is what higan's output looks like when the emulator is fudged to make the timing work (thank you byuu):
Untitled.png
And here's the raw image (take Wii_kids_truecolor.png, linearly interpolate to 128x224, linearly interpolate to 64x224, posterize to 32 levels, nearest-neighbour back to 256x224 (for display purposes), and save):
dmacolour.png
dmacolour.png (22.86 KiB) Viewed 2750 times
Espozo wrote:
93143 wrote:I wouldn't get nice static vertical columns like you see here.
You mean like some lines would be shifted over a pixel or something like that?
Every other line.

According to the documentation, DMA always aligns itself to a multiple of 8 master clocks since the last reset, and since a line is 1324 master clocks long, DMA would inevitably be offset by 4 master clocks (one pixel) every line. And since frames alternate between being divisible by 8 master clocks and not being divisible by 8 master clocks, the pattern would change at 30 fps.

It might be possible to exploit this to produce a zigzag pattern, or to treat it as chroma dither in that pseudo-4:1:1 video mode tepples was talking about. But straight columns are impossible that way.

Sik
Posts: 1589
Joined: Thu Aug 12, 2010 3:43 am

Re: High color bitmap on the SNES

Post by Sik » Sun Feb 07, 2016 10:20 pm

I guess No Signal could happen if you mess with the video output, e.g. on the Mega Drive you could be constantly changing resolution mid-screen to mess with the timings of the scanlines (also I think there's a bit that outright removes the sync signals, period). I don't know if there's anything on the SNES that could be used to do that... or that could be being used here.

Maybe some really badly timed transfer messed with outputting the hblank sync?

93143
Posts: 1194
Joined: Fri Jul 04, 2014 9:31 pm

Re: High color bitmap on the SNES

Post by 93143 » Sun Feb 07, 2016 10:50 pm

Sik wrote:Maybe some really badly timed transfer messed with outputting the hblank sync?
I really don't see how. The DMA unit is on the CPU, not the PPU, and during the main loop I'm not touching anything on the PPU bus except CGADD and CGDATA, plus the H/V counter registers in a loop in VBlank, plus one write to INIDISP (controls brightness, turns rendering on and off) at the end of VBlank. And before that there's nothing unusual; just standard VRAM and display setup. This is all supposed to be more or less isolated from the actual picture generation, which is on the far side of the PPU. Even if nothing is being shown on screen, it should still send a black picture...

Unless it can be replicated on multiple setups, I'm going to assume it was a hardware issue.

...

In other news, I've managed to get a stable picture in bsnes v072, by switching the roles of the main screen and subscreen based on an alignment test. Unfortunately I think I screwed up the alignment test, because it now breaks on my real SNES. Lemme see if I can't fix it...
Attachments
dmacolour_alignment_test.png
dmacolour_alignment_test.png (35.23 KiB) Viewed 2722 times

93143
Posts: 1194
Joined: Fri Jul 04, 2014 9:31 pm

Re: High color bitmap on the SNES

Post by 93143 » Sun Feb 07, 2016 11:45 pm

Got it. I stupidly forgot that you have to mask off the top 7 bits of the H/V counter values, so the test DMA was happening outside active display...

This ROM works both in bsnes v072 (except for the brown line) and on my real SNES (as far as I can tell), and thus might work reliably on earlier-rev consoles.
Attachments
dmac_align.sfc
(64 KiB) Downloaded 115 times

Near
Founder of higan project
Posts: 1550
Joined: Mon Mar 27, 2006 5:23 pm

Re: High color bitmap on the SNES

Post by Near » Mon Feb 08, 2016 5:09 am

> Well, couldn't the program see what console version it is and adjust accordingly?

You could run heuristics (like a test ROM) to detect the version and then run different programs, but that's getting a bit nuts.

> If it is possible to overlay a BG layer on top of this, then it won't.

If there is a BG layer or sprites, then the PPU will be fetching different color indexes, and the DMA writes to CGRAM won't go to the correct locations.

The way this trick works ... during active display, the CGRAM address is asserted by the PPU, overriding the user-specified address. It points at the pixel color being fetched in, and apparently it manages to write the new color before the PPU loads in the value through abuse of main/sub screen fetching patterns.

It's really very impressive 93143 made this work at all, but there's not really any more room to push things more.

> You know, what's the technical explanation as to why this goes by every 4 pixels instead of every 2 like on the Genesis?

It's the length of time it takes to write via DMA to the palette register twice for each color (8 cycles per write, 4 cycles per pixel). You can't get away with only one write to CGRAM registers.

> it also allows me to start the DMA before the beginning of the active scanline and buffer enough colours to get through the DRAM refresh

I still don't entirely get this because DRAM refresh is smack in the middle of the screen for 40 clocks. But obviously you made it work :D

> How much? fullsnes doesn't mention this...

It's always at 534 on CPUr2; whereas it toggles between 530 and 538 each scanline on CPUr1 (and the toggle doesn't happen on NTSC non-interlaced frame 1 scanline 240 due to the missing dot.) The way the latter one works is actually a clock divider by 8 triggering it, and 1364 not being evenly divisible by 8 is why the position shifts each scanline. So CPUr1 probably piggy-backed on the DMA clock divider. I have no idea why Nintendo felt the need to change the DRAM refresh timing for CPUr2. It wasn't related to the DMA/HDMA CPU crashing bug.

> EDIT: also wait what, "no signal"?

It's tepples. He apparently lives inside of a black hole (or something else that causes huge amounts of electronic interference) with decade-old hardware, so his computing equipment always experiences weird failures that nobody else ever sees :P

tepples
Posts: 22017
Joined: Sun Sep 19, 2004 11:12 pm
Location: NE Indiana, USA (NTSC)
Contact:

Re: High color bitmap on the SNES

Post by tepples » Mon Feb 08, 2016 8:03 am

byuu wrote:You could run heuristics (like a test ROM) to detect the version and then run different programs, but that's getting a bit nuts.
Uniracers is nuts.
byuu wrote:> EDIT: also wait what, "no signal"?

It's tepples. He apparently lives inside of a black hole (or something else that causes huge amounts of electronic interference) with decade-old hardware, so his computing equipment always experiences weird failures that nobody else ever sees :P
My Super NES is from launch in 1991, but my TV isn't quite a decade old (a Vizio from 2007, shortly before Circuit City went under). I imagine a lot of people use TVs even older than that so that the Super Scope will still work.

Sik
Posts: 1589
Joined: Thu Aug 12, 2010 3:43 am

Re: High color bitmap on the SNES

Post by Sik » Mon Feb 08, 2016 10:21 am

Newer TVs are the most prone to barf to the video signals from old consoles =P

I was wondering if something caused the SPPU to output a tiny burst of color or something like that during hblank that could cause such a TV to outright treat it as invalid.

Revenant
Posts: 442
Joined: Sat Apr 25, 2015 1:47 pm
Location: FL

Re: High color bitmap on the SNES

Post by Revenant » Mon Feb 08, 2016 10:45 am

dmac_align.sfc now seems to work flawlessly on the 2/1/1. Nice work!

User avatar
Ramsis
Posts: 341
Joined: Sun Jul 01, 2012 6:44 am
Location: Lion's den :3
Contact:

Re: High color bitmap on the SNES

Post by Ramsis » Mon Feb 08, 2016 11:27 am

Tested this on my 1/1/1 Super Famicom (PowerPak/MUFASA build #11331): No errors at all with dmacolor.sfc (downloaded Jan 09, 2016), but immediate glitches with dmac_align.sfc (no glitches after tapping Reset though).

Then again, with that poor resolution, I don't see the point of all this. If it's just about displaying an image, why not just use Mode 3, with a decent 256-color indexed palette? :?:
Some of my projects:
Furry RPG!
Unofficial SNES PowerPak firmware
(See my GitHub profile for more)

tepples
Posts: 22017
Joined: Sun Sep 19, 2004 11:12 pm
Location: NE Indiana, USA (NTSC)
Contact:

Re: High color bitmap on the SNES

Post by tepples » Mon Feb 08, 2016 11:47 am

Though this demo is of a still image as a proof of concept, a subsequent demo could use MSU1 video. This 64-pixel-wide mode can be updated at 60 fps, unlike DMA which is limited to about 6K/frame without letterboxing. This would take ten frames to load a new 256x224 pixel frame, with visible tearing due to not enough RAM for a double buffer.

User avatar
Ramsis
Posts: 341
Joined: Sun Jul 01, 2012 6:44 am
Location: Lion's den :3
Contact:

Re: High color bitmap on the SNES

Post by Ramsis » Mon Feb 08, 2016 12:30 pm

tepples wrote:This 64-pixel-wide mode can be updated at 60 fps
Once again, the sheer resolution is scaring me off. :|
tepples wrote:unlike DMA which is limited to about 6K/frame without letterboxing.
What's so bad about letterboxing though? :?:
Some of my projects:
Furry RPG!
Unofficial SNES PowerPak firmware
(See my GitHub profile for more)

Post Reply