GP2X Some F200 Fixes For Oldplay


Micket

Member
Joined
Jul 16, 2006
Messages
196
Age
41
Location
Sweden, Gothenburg
Website
www.micket.com
UPDATE: There might not even be anything wrong, so no need to bother reading anything here!!!

Appearantly Oldplay crashes when you try to turn off the screen on.
I haven't actually written this code myself, this was all from Sasq when i took over the project.
I guess the problem might be in hw_set_screen, but the code seems fine to me, unless the adresses have been changed.

CODE

#include <stdio.h>
#include <fcntl.h>
#include <sys/mman.h>
#include <unistd.h>
#include <stropts.h>

#define GPIOAPINLVL 0x1180
#define GPIOBPINLVL 0x1182
#define GPIOCPINLVL 0x1184
#define GPIODPINLVL 0x1186
#define GPIOEPINLVL 0x1188
#define GPIOFPINLVL 0x118A
#define GPIOGPINLVL 0x118C
#define GPIOHPINLVL 0x118E
#define GPIOIPINLVL 0x1190
#define GPIOJPINLVL 0x1192
#define GPIOKPINLVL 0x1194
#define GPIOLPINLVL 0x1196
#define GPIOMPINLVL 0x1198
#define GPIONPINLVL 0x119A
#define GPIOOPINLVL 0x119C

#define GPIOAOUT 0x1060
#define GPIOBOUT 0x1062
#define GPIOCOUT 0x1064
#define GPIODOUT 0x1066
#define GPIOEOUT 0x1068
#define GPIOFOUT 0x106A
#define GPIOGOUT 0x106C
#define GPIOHOUT 0x106E
#define GPIOIOUT 0x1060
#define GPIOJOUT 0x1062
#define GPIOKOUT 0x1064
#define GPIOLOUT 0x1066
#define GPIOMOUT 0x1068
#define GPIONOUT 0x106A
#define GPIOOOUT 0x106C

volatile unsigned int *memregs32;
volatile unsigned short *memregs16;

int batt_fd;

void hw_init()
{
int memfd = open("/dev/mem", O_RDWR);
if(memfd >= 0)
memregs16 = (unsigned short *)mmap(0, 0x10000, PROT_READ|PROT_WRITE, MAP_SHARED, memfd, 0xc0000000);

memregs32 = (volatile unsigned int *)memregs16;
fprintf(stderr, "hw_init - %p\n", memregs16);
fflush(stderr);

memregs16[0x0924>>1] = 0x8900;// + ((addclock)<<8);

batt_fd = open("/dev/batt", O_RDONLY);
}

void hw_set_led(bool on)
{
if(on)
memregs16[GPIOHOUT >> 1] |= 16;
else
memregs16[GPIOHOUT >> 1] &= ~16;
}

void hw_set_screen(bool on)
{
if(on)
memregs16[GPIOHOUT >> 1] |= 4;
else
memregs16[GPIOHOUT >> 1] &= ~4;
}


int hw_get_voltage()
{
int total = 0;
unsigned short v;
for(int i=0; i<10; i++)
if(read(batt_fd, &v, 2) == 2)
total += v;

int battval = total / 10;

if (battval > 1016) v = 37;
else if (battval > 974) v = 33;
else if (battval > 943) v = 32;
else if (battval > 915) v = 31;
else if (battval > 896) v = 30;
else if (battval > 837) v = 29;
else if (battval > 815) v = 28;
else if (battval > 788) v = 27;
else if (battval > 745) v = 26;
else if (battval > 708) v = 25;
else if (battval > 678) v = 24;
else if (battval > 649) v = 23;
else if (battval > 605) v = 22;
else if (battval > 573) v = 21;
else if (battval > 534) v = 20;
else if (battval > 496) v = 19;
else if (battval > 448) v = 18;
else v = 17;

return v;
}


#define MSP_INTMASK (0xC0000808)
//#define pMSP_INTMASK ((volatile unsigned int *)nMSP_INTMASK)
#define MSP_FPLLSETVREG (0xC0000910)
#define MSP_CLKCHGSTREG (0xC0000902)

#define SETW(x, n) (*((volatile unsigned short *)x) = n)
#define SETL(x, n) (*((volatile unsigned int *)x) = n)

#define GETW(x) (*((volatile unsigned short *)x))
#define GETL(x) (*((volatile unsigned int *)x))

unsigned int sdk2x_SetFPLL(unsigned short FpllSetReg)
{
int i;
unsigned int imask;

imask = GETL(MSP_INTMASK);

// hw_set_led(true);

// Mask ALL interrupts
SETL(MSP_INTMASK, 0xFF8FFFE7);

SETW(MSP_FPLLSETVREG, FpllSetReg);

while (GETW(MSP_CLKCHGSTREG) & 1);

SETL(MSP_INTMASK, imask);

//for (i=0;(i<10000000) && (GETW(MSP_FPLLVSETREG) != FpllSetReg); i++);
//return CalcPll (MSP_FPLLVSETREG);

return 0;
}

#define SYSTEM_CLOCK 2457600
void hw_set_cpu(int speed)
{
/*int m = 0;
switch(speed)
{
case 275: m = 0x6704; break;
case 250: m = 0x5D04; break;
case 225: m = 0x5304; break;
case 200: m = 0x4904; break;
case 175: m = 0x3F04; break;
case 150: m = 0x4901; break;
case 125: m = 0x3c01; break;
case 100: m = 0x6502; break;
case 75: m = 0x4902; break;
case 50: m = 0x6503; break;
}*/

int m = (((speed*1000000)/SYSTEM_CLOCK-8)<<8)|4;
printf("speed = %d, %X ***********************************\n",speed,m);

if(m)
{
// Get interupt flags
unsigned int l = memregs32[0x808>>2];

// Turn off interrupts
memregs32[0x808>>2] = 0xFF8FFFE7;

// Set new clock frequency
memregs16[0x910>>1]=m;

// Wait for it to take
while(memregs16[0x0902>>1] & 1);

// Turn on interrupts again
memregs32[0x808>>2] = l;
}

}
 
Micket said:
UPDATE: There might not even be anything wrong, so no need to bother reading anything here!!!

Appearantly Oldplay crashes when you try to turn off the screen on.
I haven't actually written this code myself, this was all from Sasq when i took over the project.
I guess the problem might be in hw_set_screen, but the code seems fine to me, unless the adresses have been changed.

Hey Micket, thought I'd dig this up to make a few comments and post a couple of finds. As you found out, there isn't a crash triggered by turning the f200 screen off, but you may or may not know that the current code doesn't work to actually turn the screen off on the f200. I did a little kernel digging and found where they moved the backlight bit to. So the following should get the backlight off on the f200...


...
#define GPIOGOUT 0x106C
#define GPIOHOUT 0x106E
#define GPIOIOUT 0x1070
#define GPIOJOUT 0x1072
#define GPIOKOUT 0x1074
#define GPIOLOUT 0x1076
#define GPIOMOUT 0x1078
#define GPIONOUT 0x107A
#define GPIOOOUT 0x107C




First notice the hex addresses in red, after 0x106E, they should move to 0x1070 and count up from there...



if(on)
memregs16[GPIOLOUT >> 1] |= 0x0800;
else
memregs16[GPIOLOUT >> 1] &= ~0x0800;


That's obviously f200 specific code, the f100 code stays the same.

The only other thing that bears mentioning, it that code and the similar f100 code only turn off the backlight. The below seems to work to actually cut power to the lcd display. Seems to work for me, I guess it's a "use at your own risk thing" <_<



if(on)
memregs16[GPIOHOUT >> 1] |= 0x0002;
else
memregs16[GPIOHOUT >> 1] &= ~0x0002;


Anyway, hope that proves useful for anyone who might want to turn the gp2x screen off for some reason...
 
Last edited by a moderator:
Micket said:
Hey, thanks for the information.
I don't like the idea to compile two different version so can i easily detect if the unit is a F200 or F100 somehow?
What I've seen, and what I'm doing is checking if the touchscreen device is present...

CODE

#include <sys/stat.h>

struct stat stFileInfo;
bool f200 = false;
if(stat("/dev/touchscreen/wm97xx",&stFileInfo) == 0)
f200 = true;
 
Last edited by a moderator:
Just wanted to report a bug. When I play a certain mp3 (fairly long podcast) with headphones, the internal speakers turn on as well. I can link you to the postcast if your interested in trying to duplicate it.
 
grahf said:
Just wanted to report a bug. When I play a certain mp3 (fairly long podcast) with headphones, the internal speakers turn on as well. I can link you to the postcast if your interested in trying to duplicate it.
This is out of my control. Firmware related if anything. I cannot even detect (or at least I don't) if headphones are connected and thus I don't write any code related to speakers/headphones, so It's impossible for this to be a bug in oldplay.
 
Last edited by a moderator:
FW 2.1.1, f100 gp2x.

Its pretty odd if you ask me, since I never experienced this before. And it only happened with one podcast (that works fine on the built in player/ craigamp). If you think its firmware related, then hopefully it will be fixed with open2x. Thanks for the reply!
 
grahf said:
FW 2.1.1, f100 gp2x.

Its pretty odd if you ask me, since I never experienced this before. And it only happened with one podcast (that works fine on the built in player/ craigamp). If you think its firmware related, then hopefully it will be fixed with open2x. Thanks for the reply!
Well, it would be interesting to to try it out, but since i dont have any code at all that cares weather or not you have plugged in your headphones i doubt i can fix it.
It would be some really far fetched bug in the mp3decoder that messes up something
gmail: micketeer
 
Last edited by a moderator:
Back
Top