aboutsummaryrefslogtreecommitdiff
path: root/backends/plugins/elf/elf-loader.cpp
diff options
context:
space:
mode:
authorBastien Bouclet2019-12-01 17:19:50 +0100
committerBastien Bouclet2019-12-01 17:19:50 +0100
commit34e835a20ca648b0fd2e67cefc84511c1dab6217 (patch)
tree97ba9b239a8fd9c9d8bba925b21262314de2f2c2 /backends/plugins/elf/elf-loader.cpp
parenta51c23abd3a667811b01e90b0c8c53505021950a (diff)
downloadscummvm-rg350-34e835a20ca648b0fd2e67cefc84511c1dab6217.tar.gz
scummvm-rg350-34e835a20ca648b0fd2e67cefc84511c1dab6217.tar.bz2
scummvm-rg350-34e835a20ca648b0fd2e67cefc84511c1dab6217.zip
3DS: Implement dynamic plugins
Allows a full build to run on old generation devices
Diffstat (limited to 'backends/plugins/elf/elf-loader.cpp')
-rw-r--r--backends/plugins/elf/elf-loader.cpp32
1 files changed, 24 insertions, 8 deletions
diff --git a/backends/plugins/elf/elf-loader.cpp b/backends/plugins/elf/elf-loader.cpp
index 5198fa8088..39f1f7dfa5 100644
--- a/backends/plugins/elf/elf-loader.cpp
+++ b/backends/plugins/elf/elf-loader.cpp
@@ -50,8 +50,7 @@ DLObject::DLObject() :
DLObject::~DLObject() {
discardSymtab();
- ELFMemMan.pluginDeallocate(_segment);
- _segment = 0;
+ discardSegment();
}
// Expel the symbol table from memory
@@ -65,11 +64,12 @@ void DLObject::discardSymtab() {
_symbol_cnt = 0;
}
-// Unload all objects from memory
-void DLObject::unload() {
- discardSymtab();
-
- ELFMemMan.pluginDeallocate(_segment);
+void DLObject::discardSegment() {
+ if (_segment) {
+ // Restore default protection before returning memory
+ protectMemory(_segment, _segmentSize, PF_R | PF_W);
+ deallocateMemory(_segment, _segmentSize);
+ }
_segment = 0;
_segmentSize = 0;
@@ -77,6 +77,12 @@ void DLObject::unload() {
_segmentVMA = 0;
}
+// Unload all objects from memory
+void DLObject::unload() {
+ discardSymtab();
+ discardSegment();
+}
+
bool DLObject::readElfHeader(Elf32_Ehdr *ehdr) {
assert(_file);
@@ -163,7 +169,7 @@ bool DLObject::readProgramHeaders(Elf32_Ehdr *ehdr, Elf32_Phdr *phdr, Elf32_Half
}
bool DLObject::loadSegment(Elf32_Phdr *phdr) {
- _segment = (byte *)ELFMemMan.pluginAllocate(phdr->p_align, phdr->p_memsz);
+ _segment = (byte *)allocateMemory(phdr->p_align, phdr->p_memsz);
if (!_segment) {
warning("elfloader: Out of memory.");
@@ -402,6 +408,8 @@ bool DLObject::load() {
return false;
}
+ protectMemory(_segment, _segmentSize, phdr.p_flags);
+
return true;
}
@@ -488,4 +496,12 @@ void *DLObject::symbol(const char *name) {
return 0;
}
+void *DLObject::allocateMemory(uint32 align, uint32 size) {
+ return ELFMemMan.pluginAllocate(align, size);
+}
+
+void DLObject::deallocateMemory(void *ptr, uint32 size) {
+ ELFMemMan.pluginDeallocate(ptr);
+}
+
#endif /* defined(DYNAMIC_MODULES) && defined(USE_ELF_LOADER) */