GP2X CPU-Clock

Previous topic - Next topic

D2O

Hallo,

gibt es eine Möglichkeit den CPU-Takt mit GLB zu beeinflussen, bzw. herunter zu takten?
Mein Gedanke geht eigendlich dahin das ich immer wieder gerne mit Musik einschlafe bzw. beim Musikhören  eindöse ;)
Nun kann man den kleinen ja software seitig nicht ausschalten.
Nun habe ich mir gedacht das man einen Timer einbaut der dann z.B. nach 60min. den Takt soweit herunter stellt (1mhz) das es
ein ausschalten fakt.
Sinn der sache ist ist eben das beim einschlafen der GP2X nicht unnötig strom(Akku) frist.

Ist sowas umsetzbar oder habe ich hier einen Gedankenfehler ?
I7 2600K; 8 GB RAM ; Win10 Pro x64 | NVidia GTX 750 TI 2048MB ; Realtec OnBoard Sound;
Lenovo ThinkPad T400: XP Pro
GLB Premium-immer Aktuell

Kitty Hello

Ja. Geht schon. Musst Du aber mit inline machen.
Schau mal hier:
http://wiki.gp2x.org/wiki/CPU_Frequency
Den mmregs32 und mmregs16 bekommst Du so:
Code (glbasic) Select
FUNCTION foo:

ENDFUNCTION


INLINE
extern "C"
{
typedef long off_t;
typedef long mode_t;
typedef long size_t;
int open(const char *path, int flags, ...);
void *mmap(void *addr, size_t LEN, int prot, int flags,     int fildes, off_t off);
}
#define MAP_SHARED 0x01
#define O_RDWR 0x02
#define PROT_READ 0x01
#define PROT_WRITE 0x02

  int memfd;
  unsigned long* memregs32;
  unsigned short* memregs16;

int InitGP2Xregs()
{  
  memfd = open("/dev/mem", O_RDWR);
  memregs32 = (unsigned long*) mmap(0, 0x10000, PROT_READ|PROT_WRITE, MAP_SHARED, memfd, 0xc0000000);
  memregs16 = (unsigned short *)memregs32;
}

ENDINLINE

D2O

Bin wohl etwas begriffstutzig :(

Wenn ich das mit deinem Code probiere (versteh denn eh nicht ganz), gibts immer das hier:
Quote from: Compiler"gpx_clock.gbas"(70) error : command not inside function or sub
genauso, wenn ich den Code von wiki benutze.



Code (glbasic) Select
// --------------------------------- //
// Project: gpx_clock
// Start: Friday, August 17, 2007
// IDE Version: 4.279


FUNCTION foo:

ENDFUNCTION

INLINE
extern "C"
{
//typedef long off_t;
//typedef long mode_t;
//typedef long size_t;
//int open(const char *path, int flags, ...);
//void *mmap(void *addr, size_t LEN, int prot, int flags,     int fildes, off_t off);
//}
//#define MAP_SHARED 0x01
//#define O_RDWR 0x02
//#define PROT_READ 0x01
//#define PROT_WRITE 0x02
//
//  int memfd;
//  unsigned long* memregs32;
//  unsigned short* memregs16;
//
//int InitGP2Xregs()
//{
//  memfd = open("/dev/mem", O_RDWR);
//  memregs32 = (unsigned long*) mmap(0, 0x10000, PROT_READ|PROT_WRITE, MAP_SHARED, memfd, 0xc0000000);
//  memregs16 = (unsigned short *)memregs32;


#define SYS_CLK_FREQ 7372800

void SetClock(unsigned int MHZ)
{
#ifdef GP2X
 unsigned int v;
 unsigned int mdiv,pdiv=3,scale=0;
 MHZ*=1000000;
 mdiv=(MHZ*pdiv)/SYS_CLK_FREQ;

 mdiv=((mdiv-8)<<8) & 0xff00;
 pdiv=((pdiv-2)<<2) & 0xfc;
 scale&=3;
 v = mdiv | pdiv | scale;
 
 unsigned int l = memregs32[0x808>>2];// Get interupt flags
 memregs32[0x808>>2] = 0xFF8FFFE7;   //Turn off interrupts
 memregs16[0x910>>1]=v;              //Set frequentie
 while(memregs16[0x0902>>1] & 1);    //Wait for the frequentie to be ajused
 memregs32[0x808>>2] = l;            //Turn on interrupts
#endif
}
}

ENDINLINE




GLOBAL a

WHILE TRUE


IF KEY(28) THEN bNOT(a)
IF a <> 0 THEN SetClock(50)


WEND
I7 2600K; 8 GB RAM ; Win10 Pro x64 | NVidia GTX 750 TI 2048MB ; Realtec OnBoard Sound;
Lenovo ThinkPad T400: XP Pro
GLB Premium-immer Aktuell

Schranz0r

Namespace schliessen und die While-schleife vor dem Inline machen, dann sollts schon gehn...
I <3 DGArray's :D

PC:
AMD Ryzen 7 3800X 16@4.5GHz, 16GB Corsair Vengeance LPX DDR4-3200 RAM, ASUS Dual GeForce RTX™ 3060 OC Edition 12GB GDDR6, Windows 11 Pro 64Bit, MSi Tomahawk B350 Mainboard

Kitty Hello

Code (glbasic) Select
GLOBAL a
WHILE TRUE
IF KEY(28) THEN bNOT(a)
IF a <> 0 THEN SetClock(50)
WEND
Das muss in eine andere Datei, oder in eine FUNCTION. Du darfst keinen Code ausserhalb einer FUNCTION/SUB nach der ersten haben. Und die erste ist hier "foo".

D2O

:wah: Ich stell mich glaub ich zu doof an :wah:

Ich hab mal schnell eine einfache, mit meinem restwissen über C, Summen function erstellt:
Kann mir daraus jemand bitte einen Lauffähigen Code mache :nw:
Denn auch ich verstehe, damit ich sehe wie ich die function summe() und wo ich sie aufrufen kann.

Code (glbasic) Select
FUNCTION foo:

ENDFUNCTION



INLINE
extern "C"
{

int summe(int, int); // Prototype, braucht man denn hier überhaupt?

int summe(int a , int b)
{
return (a+b);
}



}
ENDINLINE



PRINT summe(2,3),10,10
SHOWSCREEN
KEYWAIT
I7 2600K; 8 GB RAM ; Win10 Pro x64 | NVidia GTX 750 TI 2048MB ; Realtec OnBoard Sound;
Lenovo ThinkPad T400: XP Pro
GLB Premium-immer Aktuell

Kitty Hello

Hähähä! So nicht. GLBasic kennt die funktion "summe so nicht". Du musst einen Wrapper machen:
Code (glbasic) Select
INLINE
PRINT(summe(2,3), 10,10;
ENDINLINE

// oder
FUNCTTION gl_summe: a ,b
INLINE
   return summe(a,b);
ENDINLINE
ENDFUNCTION

D2O

Sorry, ich bin zu doof für die Inline sachen,
es sind ja wirklich nur ein paar zeilen Code und ich bekomme das nicht zu laufen.

Extremst Frustriert und am eigenen Wissen und gelernten zweifelnd :(

Das Inline zeugs kommt ab sofort bei mir in die unterste und letzte schublade des ToDo schrankes.
Trotzdem vielen Dank.
I7 2600K; 8 GB RAM ; Win10 Pro x64 | NVidia GTX 750 TI 2048MB ; Realtec OnBoard Sound;
Lenovo ThinkPad T400: XP Pro
GLB Premium-immer Aktuell

trucidare

hehe so habich auch angefangen und dann nach und nach wurds immer klarer. einfach dran bleiben dann gehts irgendwann.

@ gernot
danke für den code zum übertakten ;)
MacBook Pro 2,2 GHz Core 2 Duo, 4 GB RAM, 160 GB HDD, 8600M GT
Core i3 - 3,07 GHz, 8 GB Ram, 2.5 TB HDD, Geforce GTX 260+ OC

Kitty Hello

Hier nochmal der komplette Code (sollte laufen)
Code (glbasic) Select
FUNCTION foo:
ENDFUNCTION


INLINE
#ifdef GP2X
extern "C"
{
typedef long off_t;
typedef long mode_t;
typedef long size_t;
int open(const char *path, int flags, ...);
void *mmap(void *addr, size_t LEN, int prot, int flags,     int fildes, off_t off);
}
#define MAP_SHARED 0x01
#define O_RDWR 0x02
#define PROT_READ 0x01
#define PROT_WRITE 0x02

  int memfd;
  unsigned long* memregs32;
  unsigned short* memregs16;

int InitGP2Xregs()
{
  memfd = open("/dev/mem", O_RDWR);
  memregs32 = (unsigned long*) mmap(0, 0x10000, PROT_READ|PROT_WRITE, MAP_SHARED, memfd, 0xc0000000);
  memregs16 = (unsigned short *)memregs32;
}
#endif

#define SYS_CLK_FREQ 7372800

void SetClock(unsigned int MHZ)
{
#ifdef GP2X
  InitGP2Xregs();
 
  unsigned int v;
  unsigned int mdiv,pdiv=3,scale=0;
  MHZ*=1000000;
  mdiv=(MHZ*pdiv)/SYS_CLK_FREQ;

  mdiv=((mdiv-8)<<8) & 0xff00;
  pdiv=((pdiv-2)<<2) & 0xfc;
  scale&=3;
  v = mdiv | pdiv | scale;

  unsigned int l = memregs32[0x808>>2];// Get interupt flags
  memregs32[0x808>>2] = 0xFF8FFFE7;   //Turn off interrupts
  memregs16[0x910>>1]=v;              //Set frequentie
  while(memregs16[0x0902>>1] & 1);    //Wait for the frequentie to be ajused
  memregs32[0x808>>2] = l;            //Turn on interrupts
#endif
}


ENDINLINE



FUNCTION SetGP2XClock: mhz
INLINE
SetClock((unsigned int) mhz);
ENDINLINE

ENDFUNCTION

D2O

Danke Gernot,
jetzt habe ich meinen Fehler gefunden/verstanden.
Ich habe die "C" funktionen dann immer direkt aufgerufen, dabei mussten die dann auch mit Inline aufgerufen werden.

Werds demnächst mal testen.
I7 2600K; 8 GB RAM ; Win10 Pro x64 | NVidia GTX 750 TI 2048MB ; Realtec OnBoard Sound;
Lenovo ThinkPad T400: XP Pro
GLB Premium-immer Aktuell