forums.ps2dev.org Forum Index forums.ps2dev.org
Homebrew PS2, PSP & PS3 Development Discussions
 
 FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

SDK initialization

 
Post new topic   Reply to topic    forums.ps2dev.org Forum Index -> PSP Development
View previous topic :: View next topic  
Author Message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Thu Aug 06, 2009 5:24 pm    Post subject: SDK initialization Reply with quote

Hi again everybody!

I've managed to run non-signed ELFs from the MoHH exploit by kgsws.

But I ran into a problem: the ELF execute properly (at least very simple ones) if it doesn't include the SDK initialization (when I manually code module_start(), create a new thread running main(), specify PSP_NO_MAIN_THREAD() macro, and of course I include necessary linking flags on the Makefile), but it does absolutely nothing if the SDK initialization is present (the screen keeps blank). Any ideas?

I already sought some people's help, but they really had no clue xD If you need the code I'm using or any reference I'll post it, just ask me.

Thanks a lot!
_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Thu Aug 06, 2009 6:35 pm    Post subject: Reply with quote

What code are you using? You need to place all sections to the right addresses, resolve stubs, THEN jump to the start of text section (0x0890000).
Can you post your code?
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Thu Aug 06, 2009 8:25 pm    Post subject: Reply with quote

Yes, I do that, otherwise I wouldn't be able to run a thing, wouldn't I? :P

Quote:
You need to place all sections to the right addresses

Not ALL the sections. Only those marked as "must be allocated". And I think those are all in program section to make the loading faster (at least that's what the ELF standard paper I read said), so loading program section in the right address will suffice. Correct me if I'm wrong, but that way it works (partially as I said).

Quote:
resolve stubs

Done. I get the stubs resolved from MoHH in a table and then load the program section from the ELF, locate the .lib.stub section and resolve the stubs. Of course, I can only resolve imports included in MoHH because they don't use fixed addresses or fixed syscalls numbers. If someone knows how can I get around this without accessing kernel mode, I'm all ears :D

Quote:
THEN jump to the start of text section (0x0890000)

The entry point is specified by the ELF header, it's not a fixed address (although in PSP it's always the same, but just for safety I use the one specified in the ELF header). Btw, it's not 0x08900000 (you forgot a zero there :D), but 0x8900048 if I remember well (_start or module_start())

Here's the code; only the main function for brevity. If you need details about some function or data structure, just ask me I'll post it.

Code:
tNIDResolver nid_table[NID_TABLE_SIZE];

/* eloader entry point */
void start_eloader(char *eboot_path)
{
   unsigned int num_nids, stubs_size, stubs_resolved;   
   tStubEntry* pstub_entry;      
   SceUID elf_file;
   unsigned int elf_size;
   Elf32_Ehdr elf_header;

   #ifdef DEBUG
      dbglog = sceIoOpen(DEBUG_PATH, PSP_O_CREAT | PSP_O_WRONLY, 0777);
   #endif

   /* Extract resolved imports from game */
   if(num_nids = build_nid_table((tStubEntry *) MOHH_LIBSTUB_ADDRESS, nid_table))
   {      
      /* Open ELF */
      elf_file = sceIoOpen(eboot_path, PSP_O_RDONLY, 0777);

      /* Read ELF header */
      sceIoRead(elf_file, &elf_header, sizeof(Elf32_Ehdr));         
      
      /* Load ELF program section into memory */
      elf_size = elf_load_program(elf_file, &elf_header);

      /* Locate ELF's .lib.stubs section */
      stubs_size = elf_find_imports(elf_file, &elf_header, &pstub_entry);      
      
      /* Resolve ELF's stubs with game's stubs */
      stubs_resolved = resolve_imports(pstub_entry, stubs_size, nid_table);
      
      /* No need for ELF file anymore */
      sceIoClose(elf_file);

      /* Commit changes to RAM */
      sceKernelDcacheWritebackInvalidateAll();
      
      /* Go for ELF! */
      execute_elf((u32 *)elf_header.e_entry);
   }
   
   #ifdef DEBUG
      sceIoClose(dbglog);
   #endif
}


A few comments about the code:

  • I'm just considering static ELFs, not PRXs (by now). Just to simplify. If statics work, then relocation should be easy and would work without much problem (I hope xD)
  • I'm using fixed-size data structures because malloc() didn't work with the exploit's SDK. I didn't try to make it work neither. I'll check that later, it's just optimization.
  • Code is not optimized, just the first thought I got about it.
  • The aim is of course getting an EBOOT.PBP instead of an ELF. But I think that if I get the ELFs to work, extracting them from PBPs will be fairly easy.

_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Thu Aug 06, 2009 10:39 pm    Post subject: Reply with quote

Take a look at pspsdk/src/startup/crt0.c. That's the crt0 (initialization code) for ELF. try to use it in your application and check if it works. if it doesn't, try commenting out some things until it works. Then you'll know what prevent the ELF from loading.

EDIT: You said malloc doesn't work. Maybe it's a libc problem, in fact crt0 does some lib calls. have you tried the following in the Makefile of the elf?

Code:
USE_KERNEL_LIBC = 1
USE_KERNEL_LIBS = 1


also try PSP_NO_CREATE_MAIN_THREAD().
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Fri Aug 07, 2009 12:54 am    Post subject: Reply with quote

Quote:
also try PSP_NO_CREATE_MAIN_THREAD().

I already said that the ELF execute if I put this macro :)

Thanks for the ideas, I'll try and report any news.
_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Fri Aug 07, 2009 5:09 am    Post subject: Reply with quote

m0skit0 wrote:
Quote:
also try PSP_NO_CREATE_MAIN_THREAD().

I already said that the ELF execute if I put this macro :)

Thanks for the ideas, I'll try and report any news.


you said:

m0skit0 wrote:
when I manually code module_start(), create a new thread running main(), specify PSP_NO_MAIN_THREAD() macro, and of course I include necessary linking flags on the Makefile


i mean to use ONLY PSP_NO_MAIN_THREAD, without manually coding _start.
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Fri Aug 07, 2009 8:29 am    Post subject: Reply with quote

Then you got an error: "module_start" not found :P
_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Fri Aug 07, 2009 8:04 pm    Post subject: Reply with quote

m0skit0 wrote:
Then you got an error: "module_start" not found :P


ehhh??? but it's very strange!
from crt0.c:

Code:
/**
 * Startup thread
 *
 * Creates the main program thread based on variables defined by the program.
 *
 * @param args - Size (in bytes) of arguments passed to the program by the kernel.
 * @param argp - Pointer to arguments passed by the kernel.
 */
int _start(SceSize args, void *argp)
{
   void (*_main_func)(SceSize args, void *argp) = _main;
   void (*_init_func)(void) = _init;

   if ((&module_info != NULL) && (module_info.modattribute & 0x1000)) {
      /* If we're running in kernel mode, the addresses of our _main() thread
         and _init() function must also reside in kernel mode. */
      _main_func = (void *) ((u32) _main_func | 0x80000000);
      _init_func = (void *) ((u32) _init_func | 0x80000000);
   }

   /* Call _init() here, because an app may have code that needs to run in
      kernel mode, but want their main() thread to run in user mode.  If they
      define "constructors" they can do any kernel mode initialization here
      before their app is switched. */
   _init_func();

   if (&sce_newlib_nocreate_thread_in_start != NULL) {
      /* The program does not want main() to be run in a seperate thread. */
      _main_func(args, argp);
      return 1;
   }

   int priority = DEFAULT_THREAD_PRIORITY;
   unsigned int attribute = DEFAULT_THREAD_ATTRIBUTE;
   unsigned int stackSize = DEFAULT_THREAD_STACK_KB_SIZE * 1024;
   const char *threadName = DEFAULT_MAIN_THREAD_NAME;

   if (&sce_newlib_priority != NULL) {
      priority = sce_newlib_priority;
   }
   if (&sce_newlib_attribute != NULL) {
      attribute = sce_newlib_attribute;
   }
   if (&sce_newlib_stack_kb_size != NULL) {
      stackSize = sce_newlib_stack_kb_size * 1024;
   }
   if (&sce_newlib_main_thread_name != NULL) {
      threadName = sce_newlib_main_thread_name;
   }

   /* Does the _main() thread belong to the User, VSH, or USB/WLAN APIs? */
   if (attribute & (PSP_THREAD_ATTR_USER | PSP_THREAD_ATTR_USBWLAN | PSP_THREAD_ATTR_VSH)) {
      /* Remove the kernel mode addressing from the pointer to _main(). */
      _main_func = (void *) ((u32) _main_func & 0x7fffffff);
   }

   SceUID thid;
   thid = sceKernelCreateThread(threadName, (void *) _main_func, priority, stackSize, attribute, 0);
   sceKernelStartThread(thid, args, argp);

   return 0;
}


PSP_NO_CREATE_MAIN_THREAD is defined as:

Code:
  #define PSP_NO_CREATE_MAIN_THREAD     (           )         int sce_newlib_nocreate_thread_in_start = 1


so _start is still defined if PSP_NO_CREATE_MAIN_THREAD is used.
module_start is only an alias to _start, but it's defined ONLY when building prx (see crt0_prx.c). are you sure you aren't building with BUILD_PRX=1??? it seems strange to me...
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Fri Aug 07, 2009 8:32 pm    Post subject: Reply with quote

Ok, my mistake, I apologize! When I have some time I'll try playing with crt0.c to see what my ELF loader doesn't like from here. I'll answer as soon as I get some answers :)
_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Sat Aug 08, 2009 7:54 pm    Post subject: Reply with quote

Can you give me some advice about why the modifications in crt0.c doesn't affect at all? I mean, I modify that file but that seems not to affect the initialization code in my app. How can I do to test a modified crt0.c?

Sorry for the n00bishness :P
_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Sat Aug 08, 2009 8:15 pm    Post subject: Reply with quote

m0skit0 wrote:
Can you give me some advice about why the modifications in crt0.c doesn't affect at all? I mean, I modify that file but that seems not to affect the initialization code in my app. How can I do to test a modified crt0.c?

Sorry for the n00bishness :P


you'll have modify it from the pspsdk source, recompile pspsdk and try.
you can also include crt0.c in your application, then use -mno-crt0 in your makefile to tell the compiler to not include crt0.

EDIT: There's a third way. take pspsdk source, modfiy crt0, make (only startup directory). copy crt0.o in your pspsdk and try...
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Sun Aug 09, 2009 8:22 pm    Post subject: Reply with quote

BTW, take a look at this message: http://forums.ps2dev.org/viewtopic.php?p=26585#26585

to jump to text segment, don't use j/jr, use jal or when crt0 exits it'll return to $ra, but $ra doesn't point to the end of your loader code, and it'll crash!!! :)
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Mon Aug 10, 2009 6:24 pm    Post subject: Reply with quote

Thanks for pointing out that link, very useful. I don't know I've not visited it earlier :P

The fact is that it seems that default stack allocation by SDK initialization is the problem. If I down the 256 KB reserved by default, it do work. So I'm considering freeing the MoHH reserved memory, but sincerly I've never used dynamic allocation on PSP. Which functions should I use? sceKernelAllocPartitionMemory() and the like? Any useful info about how to use such functions?

Thanks!
_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Mon Aug 10, 2009 8:13 pm    Post subject: Reply with quote

m0skit0 wrote:
Thanks for pointing out that link, very useful. I don't know I've not visited it earlier :P

The fact is that it seems that default stack allocation by SDK initialization is the problem. If I down the 256 KB reserved by default, it do work. So I'm considering freeing the MoHH reserved memory, but sincerly I've never used dynamic allocation on PSP. Which functions should I use? sceKernelAllocPartitionMemory() and the like? Any useful info about how to use such functions?

Thanks!


I suggest you to dump all the UIDs for allocated memory blocks, so you'll see what's allocated by MoHH. But you can't do that in usermode, so we need to find another way. I suggest you to reverse MoHH, find the exitcallback registration function, reverse the exit callback and see what it does to free memory. That way you can free MoHH memory and get memory for your homebrew.
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
m0skit0



Joined: 02 Jun 2009
Posts: 226

PostPosted: Tue Aug 11, 2009 1:19 am    Post subject: Reply with quote

Yes, that's exactly what i'm doing right now :)
_________________
The Incredible Bill Gates wrote:
The obvious mathematical breakthrough would be development of an easy way to factor large prime numbers.
Back to top
View user's profile Send private message
ab5000



Joined: 06 May 2008
Posts: 74

PostPosted: Tue Aug 11, 2009 2:55 am    Post subject: Reply with quote

BTW, can you send me a PM with the source code of your loader? i'm very interested :)

Thanks!
_________________
Code:
%:include<stdio.h>
int _(int __,int ___,int ____,int _____)
<%for(;____<___;_____=_____*__,____++);
return _____;%>main()<%printf
("%d\n",_(2,5,0,1));%>
Back to top
View user's profile Send private message
Display posts from previous:   
Post new topic   Reply to topic    forums.ps2dev.org Forum Index -> PSP Development All times are GMT + 10 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group