xref: /netbsd-src/sys/arch/epoc32/stand/e32boot/exe/netbsd.cpp (revision 1cdab4cbb849e28449cca375660ea59d33603ea6)
1 /*	$NetBSD: netbsd.cpp,v 1.2 2013/06/20 13:36:48 kiyohara Exp $	*/
2 /*
3  * Copyright (c) 2012 KIYOHARA Takashi
4  * All rights reserved.
5  *
6  * Redistribution and use in source and binary forms, with or without
7  * modification, are permitted provided that the following conditions
8  * are met:
9  * 1. Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  * 2. Redistributions in binary form must reproduce the above copyright
12  *    notice, this list of conditions and the following disclaimer in the
13  *    documentation and/or other materials provided with the distribution.
14  *
15  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
16  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
18  * DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
19  * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
20  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
21  * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
23  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
24  * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25  * POSSIBILITY OF SUCH DAMAGE.
26  */
27 #include <e32cons.h>
28 #include <e32std.h>
29 #include <f32file.h>
30 
31 #include "e32boot.h"
32 #include "elf.h"
33 #include "netbsd.h"
34 
35 
36 NetBSD *
New(const TDesC & aFilename)37 NetBSD::New(const TDesC &aFilename)
38 {
39 	NetBSD *netbsd = NULL;
40 	RFs fsSession;
41 	RFile file;
42 	TInt size;
43 	union {
44 		Elf32_Ehdr elf;
45 	} hdr;
46 
47 	/* Connect to FileServer Session */
48 	User::LeaveIfError(fsSession.Connect());
49 
50 	User::LeaveIfError(file.Open(fsSession, aFilename, EFileRead));
51 	User::LeaveIfError(file.Size(size));
52 
53 	TPtr hdrBuf((TUint8 *)&hdr, sizeof(hdr));
54 	User::LeaveIfError(file.Read(hdrBuf));
55 	/* Currently support is ELF only. */
56 	if (Mem::Compare((TUint8 *)hdr.elf.e_ident, SELFMAG,
57 					(TUint8 *)ELFMAG, SELFMAG) == 0) {
58 		netbsd = new (ELeave) ELF(size);
59 	} else
60 		User::Leave(KErrNotSupported);
61 	TInt pos = 0;
62 	User::LeaveIfError(file.Seek(ESeekStart, pos));
63 
64 	TPtr fileBuf(netbsd->Buffer, size);
65 	User::LeaveIfError(file.Read(fileBuf));
66 	if (fileBuf.Length() != size)
67 		User::Leave(KErrNotFound);
68 	file.Close();
69 
70 	/* Close FileServer Session */
71 	fsSession.Close();
72 
73 	netbsd->LoadDescriptor =
74 	    (struct loaddesc *)PAGE_ALIGN(User::AllocL(ALIGN_SAFE_PAGE_SIZE));
75 
76 	return netbsd;
77 }
78 
79 NetBSD *
New(const TDesC & aFilename,const TDesC & aArgs)80 NetBSD::New(const TDesC &aFilename, const TDesC &aArgs)
81 {
82 	NetBSD *netbsd = New(aFilename);
83 
84 	netbsd->Args = &aArgs;
85 
86 	return netbsd;
87 }
88 
89 
90 void
ParseHeader(void)91 ELF::ParseHeader(void)
92 {
93 	struct loaddesc *loaddesc = LoadDescriptor;
94 	Elf32_Ehdr ehdr;
95 	Elf32_Phdr *phdr = NULL;
96 	int PhdrSize, i;
97 
98 	Mem::Copy(&ehdr, Buffer, sizeof(ehdr));
99 	PhdrSize = sizeof(Elf32_Phdr) * ehdr.e_phnum;
100 	phdr = (Elf32_Phdr *) new (ELeave) TUint8[PhdrSize];
101 	Mem::Copy(phdr, Buffer + ehdr.e_phoff, PhdrSize);
102 
103 	for (i = 0; i < ehdr.e_phnum; i++) {
104 		if (phdr[i].p_type != PT_LOAD ||
105 		    (phdr[i].p_flags & (PF_W | PF_X)) == 0)
106 			continue;
107 
108 		loaddesc->addr = VTOP(phdr[i].p_vaddr);
109 		loaddesc->offset = phdr[i].p_offset;
110 		loaddesc->size = phdr[i].p_filesz;
111 		loaddesc++;
112 	}
113 	/* Terminate loaddesc. */
114 	loaddesc->addr = 0xffffffff;
115 	loaddesc->offset = 0xffffffff;
116 	loaddesc->size = 0xffffffff;
117 
118 	EntryPoint = ehdr.e_entry;
119 }
120