FreeNOS
Runtime.cpp
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2009 Niek Linnenbank
3  *
4  * This program is free software: you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License as published by
6  * the Free Software Foundation, either version 3 of the License, or
7  * (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program. If not, see <http://www.gnu.org/licenses/>.
16  */
17 
18 #include <FreeNOS/System.h>
19 #include <Types.h>
20 #include <Macros.h>
21 #include <Array.h>
22 #include <FileSystemClient.h>
23 #include <PoolAllocator.h>
24 #include <FileSystemMount.h>
25 #include <FileDescriptor.h>
26 #include <MemoryMap.h>
27 #include <Memory.h>
28 #include <Randomizer.h>
29 #include "ProcessClient.h"
30 #include "PageAllocator.h"
31 #include "KernelLog.h"
32 #include "Runtime.h"
33 
35 extern void (*CTOR_LIST)();
36 
38 extern void (*DTOR_LIST)();
39 
40 void * __dso_handle = 0;
41 
43 {
44 }
45 
46 extern C int __cxa_guard_acquire(u32 *guard)
47 {
48  if (*guard)
49  return 0;
50  else
51  return 1;
52 }
53 
54 extern C void __cxa_guard_release(u32 *guard)
55 {
56  *guard = 1;
57 }
58 
62 extern C int __cxa_atexit(void (*func) (void *),
63  void * arg, void * dso_handle)
64 {
65  return (0);
66 }
67 
68 extern C int __aeabi_atexit()
69 {
70  return 0;
71 }
72 
73 extern C void __cxa_pure_virtual()
74 {
75 }
76 
77 extern C void __stack_chk_fail(void)
78 {
79 }
80 
81 extern C int raise(int sig)
82 {
83  return 0;
84 }
85 
87 {
88  for (void (**ctor)() = &CTOR_LIST; ctor && *ctor; ctor++)
89  {
90  (*ctor)();
91  }
92 }
93 
95 {
96  for (void (**dtor)() = &DTOR_LIST; dtor && *dtor; dtor++)
97  {
98  (*dtor)();
99  }
100 }
101 
102 void setupHeap()
103 {
104  Arch::MemoryMap map;
106  PageAllocator *pageAlloc;
107  PoolAllocator *poolAlloc;
108  const Allocator::Range pageRange = { heap.virt, heap.size, PAGESIZE };
109 
110  // Allocate one page to store the allocators themselves
111  Memory::Range range;
112  range.size = PAGESIZE;
114  range.virt = heap.virt;
115  range.phys = ZERO;
116  const API::Result result = VMCtl(SELF, MapContiguous, &range);
117  if (result != API::Success)
118  {
119  PrivExec(WriteConsole, (Address) ("failed to allocate pages for heap: terminating"));
121  }
122 
123  // Allocate instance copy on vm pages itself
124  pageAlloc = new (heap.virt) PageAllocator(pageRange);
125  poolAlloc = new (heap.virt + sizeof(PageAllocator)) PoolAllocator(pageAlloc);
126 
127  // Set default allocator
128  Allocator::setDefault(poolAlloc);
129 }
130 
132 {
133  FileSystemClient filesystem;
134 
135  // Map user program arguments
136  Arch::MemoryMap map;
137  Memory::Range argRange = map.range(MemoryMap::UserArgs);
138 
139  // First page is the argc+argv (skip here)
140  // Second page is the current working directory
141  filesystem.setCurrentDirectory(new String((char *) argRange.virt + PAGESIZE, false));
142 
143  // Third page and above contain the file descriptors table
145  (argRange.size - (PAGESIZE * 2)) / sizeof(FileDescriptor::Entry));
146 
147  // Inherit file descriptors table from parent (if any).
148  // Without a parent, just clear the file descriptors
149  if (ProcessCtl(SELF, GetParent) == 0)
150  {
151  Size count = 0;
153 
154  MemoryBlock::set(array, 0, count * sizeof(FileDescriptor::Entry));
155  filesystem.setCurrentDirectory(String("/"));
156  }
157 }
158 
160 {
161  const ProcessClient proc;
162  const ProcessID pid = proc.getProcessID();
163 
164  Timer::Info timer;
165  ProcessCtl(SELF, InfoTimer, (Address) &timer);
166 
167  Randomizer rand;
168  rand.seed(pid + timer.ticks);
169 }
170 
171 extern C void SECTION(".entry") _entry()
172 {
173  int ret, argc;
174  char *arguments;
175  char **argv;
176  SystemInformation info;
177  Arch::MemoryMap map;
178 
179  // Clear BSS
180  clearBSS();
181 
182  // Setup the heap, C++ constructors and default mounts
183  setupHeap();
184  runConstructors();
185  setupMappings();
186  setupRandomizer();
187 
188  // Allocate buffer for arguments
189  argc = 0;
190  argv = new char*[ARGV_COUNT];
191  arguments = (char *) map.range(MemoryMap::UserArgs).virt;
192 
193  // Fill in arguments list
194  while (argc < ARGV_COUNT && *arguments)
195  {
196  argv[argc] = arguments;
197  arguments += ARGV_SIZE;
198  argc++;
199  }
200 
201  // Pass control to the program
202  ret = main(argc, argv);
203 
204  // Terminate execution
205  runDestructors();
206  ProcessCtl(SELF, KillPID, ret);
207 }
FileDescriptor::setArray
void setArray(Entry *array, const Size count)
Assign entry table.
Definition: FileDescriptor.cpp:31
CTOR_LIST
void(* CTOR_LIST)()
List of constructors.
Runtime.h
Memory::Range
Memory range.
Definition: Memory.h:55
StrictSingleton< FileDescriptor >::instance
static FileDescriptor * instance()
Retrieve the instance.
Definition: Singleton.h:53
FileDescriptor::getArray
Entry * getArray(Size &count)
Get entry table.
Definition: FileDescriptor.cpp:25
API::Result
Result
Enumeration of generic kernel API result codes.
Definition: API.h:68
Macros.h
PageAllocator
Allocates virtual memory using the memory server.
Definition: PageAllocator.h:36
FileSystemMount.h
Types.h
ARGV_COUNT
#define ARGV_COUNT
Number of arguments at maximum.
Definition: Runtime.h:36
MemoryBlock::set
static void * set(void *dest, int ch, unsigned count)
Fill memory with a constant byte.
Definition: MemoryBlock.cpp:25
DTOR_LIST
void(* DTOR_LIST)()
List of destructors.
Memory::Writable
@ Writable
Definition: Memory.h:42
String
Abstraction of strings.
Definition: String.h:41
Memory::User
@ User
Definition: Memory.h:44
FileSystemClient
FileSystemClient provides a simple interface to a FileSystemServer.
Definition: FileSystemClient.h:42
PAGESIZE
#define PAGESIZE
ARM uses 4K pages.
Definition: ARMConstant.h:97
__cxa_guard_release
C void __cxa_guard_release(u32 *guard)
Definition: Runtime.cpp:54
ProcessClient
ProcessClient provides information about all processes on the local core.
Definition: ProcessClient.h:39
PrivExec
API::Result PrivExec(const PrivOperation op, const Address param=0)
Prototype for user applications.
Definition: PrivExec.h:52
ProcessID
u32 ProcessID
Process Identification Number.
Definition: Types.h:140
Address
unsigned long Address
A memory address.
Definition: Types.h:131
ProcessClient::getProcessID
ProcessID getProcessID() const
Get current process identifier.
Definition: ProcessClient.cpp:27
Array.h
Randomizer::seed
void seed(const ulong value)
Set a value as the current state.
Definition: Randomizer.cpp:22
VMCtl
API::Result VMCtl(const ProcessID procID, const MemoryOperation op, Memory::Range *range=ZERO)
Prototype for user applications.
Definition: VMCtl.h:61
FileDescriptor.h
ProcessCtl
API::Result ProcessCtl(const ProcessID proc, const ProcessOperation op, const Address addr=0, const Address output=0)
Prototype for user applications.
Definition: ProcessCtl.h:93
Timer::Info
Timer information structure.
Definition: Timer.h:42
Memory::Readable
@ Readable
Definition: Memory.h:41
main
int main(int argc, char **argv)
Program entry point.
Definition: Main.cpp:20
ARGV_SIZE
#define ARGV_SIZE
Maximum size of each argument.
Definition: Runtime.h:33
setupMappings
void setupMappings()
Definition: Runtime.cpp:131
ARMMap
Memory mapping for the kernel and user processes on the ARM architecture.
Definition: ARMMap.h:37
SECTION
C void SECTION(".entry") _entry()
Definition: Runtime.cpp:171
SELF
#define SELF
Definition: ProcessID.h:35
setupRandomizer
void setupRandomizer()
Definition: Runtime.cpp:159
PageAllocator.h
InfoTimer
@ InfoTimer
Definition: ProcessCtl.h:49
C
#define C
Used to define external C functions.
Definition: Macros.h:134
__aeabi_atexit
C int __aeabi_atexit()
Definition: Runtime.cpp:68
Memory::Range::phys
Address phys
Physical address.
Definition: Memory.h:58
FileDescriptor::Entry
Describes a single file opened by a user process.
Definition: FileDescriptor.h:46
FileSystemClient::setCurrentDirectory
void setCurrentDirectory(const String &directory)
Set new current directory.
Definition: FileSystemClient.cpp:151
Randomizer.h
MemoryMap::range
Memory::Range range(Region region) const
Get memory range for the given region.
Definition: MemoryMap.cpp:36
u32
unsigned int u32
Unsigned 32-bit number.
Definition: Types.h:53
Size
unsigned int Size
Any sane size indicator cannot go negative.
Definition: Types.h:128
setupHeap
void setupHeap()
Definition: Runtime.cpp:102
MemoryMap.h
__stack_chk_fail
C void __stack_chk_fail(void)
Definition: Runtime.cpp:77
__cxa_pure_virtual
C void __cxa_pure_virtual()
Unknown function, required by g++.
Definition: Runtime.cpp:73
__dso_handle
void * __dso_handle
Definition: Runtime.cpp:40
__cxa_atexit
C int __cxa_atexit(void(*func)(void *), void *arg, void *dso_handle)
Definition: Runtime.cpp:62
Randomizer
Produces random integers using the Linear congruential generator algorithm.
Definition: Randomizer.h:36
ProcessClient.h
Memory.h
runConstructors
void runConstructors()
Definition: Runtime.cpp:86
Allocator::Range
Describes a range of memory.
Definition: Allocator.h:65
__aeabi_unwind_cpp_pr0
C void __aeabi_unwind_cpp_pr0()
Definition: Runtime.cpp:42
Allocator::setDefault
static void setDefault(Allocator *alloc)
Makes the given Allocator the default.
Definition: Allocator.cpp:59
FileSystemClient.h
__cxa_guard_acquire
C int __cxa_guard_acquire(u32 *guard)
Definition: Runtime.cpp:46
PoolAllocator
Memory allocator which uses pools that each manage same-sized objects.
Definition: PoolAllocator.h:45
SystemInformation
System information structure.
Definition: SystemInfo.h:79
API::Success
@ Success
Definition: API.h:70
Memory::Range::virt
Address virt
Virtual address.
Definition: Memory.h:57
MemoryMap::UserArgs
@ UserArgs
< Used for copying program arguments and file descriptors
Definition: MemoryMap.h:61
MemoryMap::UserHeap
@ UserHeap
< User heap
Definition: MemoryMap.h:57
clearBSS
void clearBSS()
Generic function to clear the BSS memory section to zero.
Definition: Memory.cpp:21
Memory::Range::size
Size size
Size in number of bytes.
Definition: Memory.h:59
Memory::Range::access
Access access
Page access flags.
Definition: Memory.h:60
ZERO
#define ZERO
Zero value.
Definition: Macros.h:43
MapContiguous
@ MapContiguous
Definition: VMCtl.h:37
WriteConsole
@ WriteConsole
Definition: PrivExec.h:39
runDestructors
void runDestructors()
Definition: Runtime.cpp:94
KillPID
@ KillPID
Definition: ProcessCtl.h:40
GetParent
@ GetParent
Definition: ProcessCtl.h:42
KernelLog.h
PoolAllocator.h