Author Topic: PocketSNES based on Snes9x 1.43-dev [2014-08-24 update]  (Read 120608 times)

iames85

  • Posts: 65
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #40 on: January 03, 2014, 10:51:04 pm »
This is fantastic guys. Thanks you so much for all your hard work. Its so great to have these games playable again after so many years.

Nebuleon

  • Guest
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #41 on: January 03, 2014, 11:14:15 pm »
Really awesome update, I'll be much more likely to play SNES stuff on the Zero thanks to this  :)

Being nitpicky here, but would it be possible to bring over the bilinear scaler from ReGBA? It should look more "even" compared to the one from SNES9x4D (lifebars from Mega Man games seem to be an easy way to compare):





I can understand if there's not enough CPU power left over for that type of scaling in this case (until the IPU driver is done anyways).
ReGBA can scale evenly, but PocketSNES cannot.

GBA: 320x213.33333 <-- 240x160, so the bilinear interpolants are 0.75x, 0.75y (*3/4 in integer math)
SNES: 320x240 <-- 256x224, so the bilinear interpolants are 0.8x, 0.9333333y (*4/5 and *14/15 in integer math)

Because integer divisions by powers of 2 are much faster than integer divisions by arbitrary integers -- 1 cycle instead of up to 31, according to the MIPS XBurst manual --, one cannot scale in real-time using the software bilinear scaler from ReGBA if the linear interpolants cannot be represented as fractions with a power-of-2 denominator.

Currently the scaling is done by a Bresenham half-pixel algorithm vertically and quarter-pixel horizontally. It can run in 63 cycles per group of 8 output pixels, or 604800 cycles per frame (3.62% CPU time).

A software bilinear scaler would have to spend time doing a division by 15 and a division by 5 per color component per input pixel, and it would have to look at the 4 neighbors of all output pixels amongst the input image, so it would run in 744 cycles per single output pixel, or 57139200 cycles per frame (342% CPU time). As happened in ReGBA before I noticed the interpolants were optimisable, the frameskipper decision algorithm would decide that it can only render 1 frame every 3 or 4, so every game starts at 20 or 15 FPS.

tl;dr: I'll wait for the IPU.

Awakened

  • Posts: 96
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #42 on: January 04, 2014, 12:00:46 am »
ReGBA can scale evenly, but PocketSNES cannot.

GBA: 320x213.33333 <-- 240x160, so the bilinear interpolants are 0.75x, 0.75y (*3/4 in integer math)
SNES: 320x240 <-- 256x224, so the bilinear interpolants are 0.8x, 0.9333333y (*4/5 and *14/15 in integer math)

Because integer divisions by powers of 2 are much faster than integer divisions by arbitrary integers -- 1 cycle instead of up to 31, according to the MIPS XBurst manual --, one cannot scale in real-time using the software bilinear scaler from ReGBA if the linear interpolants cannot be represented as fractions with a power-of-2 denominator.

Currently the scaling is done by a Bresenham half-pixel algorithm vertically and quarter-pixel horizontally. It can run in 63 cycles per group of 8 output pixels, or 604800 cycles per frame (3.62% CPU time).

A software bilinear scaler would have to spend time doing a division by 15 and a division by 5 per color component per input pixel, and it would have to look at the 4 neighbors of all output pixels amongst the input image, so it would run in 744 cycles per single output pixel, or 57139200 cycles per frame (342% CPU time). As happened in ReGBA before I noticed the interpolants were optimisable, the frameskipper decision algorithm would decide that it can only render 1 frame every 3 or 4, so every game starts at 20 or 15 FPS.

tl;dr: I'll wait for the IPU.
Gotcha. I'm glad to have the current scaler until that is available.

gustavolatil

  • Posts: 131
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #43 on: January 04, 2014, 03:46:10 am »
act raiser intro sounds weird :/

Nebuleon

  • Guest
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #44 on: January 04, 2014, 06:10:22 am »
act raiser intro sounds weird :/
Yes, it does. Feel free to find the code that fixes this in Snes9x 1.5x and backport it without the performance spiralling out of control. :)

kuwanger

  • Posts: 29
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #45 on: January 04, 2014, 11:15:03 am »
Despite Nebuleon's rather discouraging words, I took a crack at bilinear interpolantion.  Well, I think it's that, anyways.  The results are slightly better than the current version for MMX[123], although there's definitely a noticeably performance hit.  The former makes me think my math is wrong.  And that latter, I'm not sure if optimizing well ever be enough to really make a difference.

In any case, here it is.  I've included just the executable and the one file I changed in the source (menu/scaler.cpp), so it's really for those willing to fiddle with creating a link in GMenu2x and accepting this is really just a test case.  In any case, enjoy. :)

PocketSNES with a (hopefully) bilinear upscale, although still way too slow for actual use

patrick81

  • Posts: 30
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #46 on: January 04, 2014, 12:33:53 pm »
Thanks Nebuleon!!  I didn't realize it won't load old SRAM yet.  I already deleted PocketSNES-1.39 and I'm not sure where I can find that.   ???   The new update looks really good!!   ;)

I updated this but it cannot read my load states anymore.   :o  Am i missing something?  Did it move to somewhere?
As the saved state format is very much tied to the core, later versions of Snes9x -- the core PocketSNES uses --, lose saved state backwards compatibility with every new version.

In the meanwhile, please hold on to your PocketSNES-1.39 build from August, load one saved state from 1.39 and let it save SRAM. 1.43 will then be able to load SRAM along with your game and you can save a new state with it.

Surkow

  • * Administrator
  • Posts: 670
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #47 on: January 04, 2014, 01:09:39 pm »
Thanks Nebuleon!!  I didn't realize it won't load old SRAM yet.  I already deleted PocketSNES-1.39 and I'm not sure where I can find that.   ???   The new update looks really good!!   ;)

I updated this but it cannot read my load states anymore.   :o  Am i missing something?  Did it move to somewhere?
As the saved state format is very much tied to the core, later versions of Snes9x -- the core PocketSNES uses --, lose saved state backwards compatibility with every new version.

In the meanwhile, please hold on to your PocketSNES-1.39 build from August, load one saved state from 1.39 and let it save SRAM. 1.43 will then be able to load SRAM along with your game and you can save a new state with it.
It can be found on the downloads page.

patrick81

  • Posts: 30
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #48 on: January 04, 2014, 01:18:24 pm »
Thanks!!   ;D  Ahh it's so nice to know my old save states are working again.  whew!   8)

Thanks Nebuleon!!  I didn't realize it won't load old SRAM yet.  I already deleted PocketSNES-1.39 and I'm not sure where I can find that.   ???   The new update looks really good!!   ;)

I updated this but it cannot read my load states anymore.   :o  Am i missing something?  Did it move to somewhere?
As the saved state format is very much tied to the core, later versions of Snes9x -- the core PocketSNES uses --, lose saved state backwards compatibility with every new version.

In the meanwhile, please hold on to your PocketSNES-1.39 build from August, load one saved state from 1.39 and let it save SRAM. 1.43 will then be able to load SRAM along with your game and you can save a new state with it.
It can be found on the downloads page.

patrick81

  • Posts: 30
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #49 on: January 04, 2014, 03:35:00 pm »
@Nebuleon

Is it possible to add Favorite List?  This way we can go back and forth between 2 or more favorite games instead of having to search for them.  It's a pain to search one game I want to play more often.  Is it possible to add some kind of short cuts (saved paths) to favorite list.  Also it would be nice to see that in GBA emulator as well.   

PureWicked.AU

  • Posts: 240
    • Australian GCW reseller
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #50 on: January 04, 2014, 09:50:37 pm »
Hi, silly question, I tried to re-organize my SD card and formatted it, as well as renamed it and the SNES rom folder too, is there a way to reset the default rom folder I selected earlier? as I now can't get to my new one

Nebuleon

  • Guest
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #51 on: January 04, 2014, 10:39:10 pm »
Thanks Nebuleon!!  I didn't realize it won't load old SRAM yet.  I already deleted PocketSNES-1.39 and I'm not sure where I can find that.   ???   The new update looks really good!!   ;)
[2 nesting quote levels removed]

SRAM is not old or new. Saved states are. They are very tied to the core version. Load your states in 1.39, and then let the game save itself to SRAM. SRAM will then transfer automatically to 1.43 due to being at the same place on your internal card. The format is obviously the same for the raw data, so it will load "old SRAM".

Nebuleon

  • Guest
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #52 on: January 04, 2014, 10:40:51 pm »
@Nebuleon

Is it possible to add Favorite List?  This way we can go back and forth between 2 or more favorite games instead of having to search for them.  It's a pain to search one game I want to play more often.  Is it possible to add some kind of short cuts (saved paths) to favorite list.  Also it would be nice to see that in GBA emulator as well.   
I don't implement GUIs so well. This is why I rely on gmenu2x's file browser saving your last directory with ReGBA. It acts as an implicit favo(u)rite list.

This is open-source. You can get someone else to implement things, or implement them yourself if you have the skills.

Nebuleon

  • Guest
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #53 on: January 04, 2014, 10:41:32 pm »
Hi, silly question, I tried to re-organize my SD card and formatted it, as well as renamed it and the SNES rom folder too, is there a way to reset the default rom folder I selected earlier? as I now can't get to my new one
Delete ~/.snes96_snapshots/romdir.opt.

patrick81

  • Posts: 30
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #54 on: January 05, 2014, 02:28:30 am »
aw okay.  I don't know anyone who can do this but it's not a big deal.  It's just a suggestion.   ;D

Thanks for your fantastic work!! 


@Nebuleon

Is it possible to add Favorite List?  This way we can go back and forth between 2 or more favorite games instead of having to search for them.  It's a pain to search one game I want to play more often.  Is it possible to add some kind of short cuts (saved paths) to favorite list.  Also it would be nice to see that in GBA emulator as well.   
I don't implement GUIs so well. This is why I rely on gmenu2x's file browser saving your last directory with ReGBA. It acts as an implicit favo(u)rite list.

This is open-source. You can get someone else to implement things, or implement them yourself if you have the skills.

patrick81

  • Posts: 30
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #55 on: January 05, 2014, 02:38:55 am »
I think  i know what you mean.  I never done this before.  I loaded the old saved state on PocketSnes 1.39 and just save it the normal way in the game?  I opened PocketSnes 1.43 and I don't see anything saved in the game (not the saved state).  I see no "continue" in the game.  I must have done something wrong. 

EDIT: never mind!  I got it to work!  It's quite easy to fix!  Thanks for the help!   ;D

Thanks Nebuleon!!  I didn't realize it won't load old SRAM yet.  I already deleted PocketSNES-1.39 and I'm not sure where I can find that.   ???   The new update looks really good!!   ;)
[2 nesting quote levels removed]

SRAM is not old or new. Saved states are. They are very tied to the core version. Load your states in 1.39, and then let the game save itself to SRAM. SRAM will then transfer automatically to 1.43 due to being at the same place on your internal card. The format is obviously the same for the raw data, so it will load "old SRAM".
« Last Edit: January 05, 2014, 02:55:20 am by patrick81 »

Nebuleon

  • Guest
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #56 on: January 05, 2014, 03:42:43 am »
Alright, I just made a little revision. Now the GUI returns to $HOME if your ROM directory cannot be read.

Download: https://dl.dropboxusercontent.com/u/106475413/gcw-zero/PocketSNES-20140105-1.opk

Nebuleon

  • Guest
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #57 on: January 05, 2014, 04:09:33 am »
Despite Nebuleon's rather discouraging words, I took a crack at bilinear interpolantion.  Well, I think it's that, anyways.  The results are slightly better than the current version for MMX[123], although there's definitely a noticeably performance hit.  The former makes me think my math is wrong.  And that latter, I'm not sure if optimizing well ever be enough to really make a difference. [...]

PocketSNES with a (hopefully) bilinear upscale, although still way too slow for actual use
a) There's some very noticeable colour banding in your Mega Man X with bilinear scaling screenshot.

b) This code:
Code: [Select]
red[x] = divide_by_fifteen_table[a >> 11][14] + divide_by_fifteen_table[a>> 11][1];
green[x] = divide_by_fifteen_table[(a >> 5) & 0x3f][14] + divide_by_fifteen_table[(a >> 5) & 0x3f][1];
blue[x] = divide_by_fifteen_table[a & 0x1f][14] + divide_by_fifteen_table[a & 0x1f][1];
I'm not sure why you go through divide_by_fifteen_table for this, because the result is going to be 'a' itself, but clamped to colour values up to RGB565 30,62,30.

c) Rendering the Super Mario World title screen at 30 FPS is rather jarring. With that number of operations, perhaps avoiding colour blending altogether if two neighbouring pixels have the same colour would give some speedup (except in games which have such complex rendering that no two neighbouring pixels are alike).
Code: [Select]
if (a == b) {
  red[x] = a >> 11;
  green[x] = (a >> 5) & 0x3F;
  blue[x] = a & 0x1F;
} else ...

d) Did you try /15 and /5 and see how bad it was before implementing your lookup table?

PureWicked.AU

  • Posts: 240
    • Australian GCW reseller
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-03 update]
« Reply #58 on: January 05, 2014, 05:45:19 am »
Alright, I just made a little revision. Now the GUI returns to $HOME if your ROM directory cannot be read.

Download: https://dl.dropboxusercontent.com/u/106475413/gcw-zero/PocketSNES-20140105-1.opk

thank you so much, was going to try and find the file to delete that you mentioned earlier but this is a much safer fix

kuwanger

  • Posts: 29
Re: PocketSNES based on Snes9x 1.43-dev [2014-01-05 update]
« Reply #59 on: January 05, 2014, 05:33:52 pm »
[...]
a) There's some very noticeable colour banding in your Mega Man X with bilinear scaling screenshot.

Yea, that's from rounding error.  I've fixed that.

Quote
b) This code:
Code: [Select]
...I'm not sure why you go through divide_by_fifteen_table for this, because the result is going to be 'a' itself, but clamped to colour values up to RGB565 30,62,30.

Yea, that was a quick hack to avoid yet another color banding effect.

Quote
c) Rendering the Super Mario World title screen at 30 FPS is rather jarring. ...

Sorry.  Like I was saying, it was a just a quick hack to see if I could get you 352% CPU usage figure down to a sub-100% value.

Quote
d) Did you try /15 and /5 and see how bad it was before implementing your lookup table?

Nah.  Like I said, you gave rather discouraging words. :)

Having said that, I've decided to fix the color banding effect and generally avoid 99% of the problems with a massive (okay, really only ~0.044% of the GCW0's memory) lookup tables to avoid most the hassle.  I don't see the 30FPS issue with SMW, but I haven't really looked too much into how much actual CPU usage is being done and such.  Anyways, here it is (same as the old link):

Not quite as much of a hack PocketSNES with bilinear filtering (Note this is based on the older source code (and includes the 3 source files I changed), so if you do end up wanting to merge parts of this, you'll have to be careful obviously)

Technically there's a pause at startup to generate said lookup tables, but it's (if I calculated it right) on the order of 1-2 seconds.  Anyways, here's again the older screenshot and the newer bilinear filtering.  I'll later look into the actual CPU usage and play some more games to see just how badly this performs.

 

Post a new topic
Post a new topic