linker: restore prelink support

Prelink support is required to load old vendor binary blobs
on many devices properly

This commit partially reverts 4688279db5dcc4004941e7f133c4a1c3617d842c

Change-Id: Ibc835095579c0bbd18aff61f37bd420de353e94d
diff --git a/linker/linker_phdr.c b/linker/linker_phdr.c
index 250ca20..36f848b 100644
--- a/linker/linker_phdr.c
+++ b/linker/linker_phdr.c
@@ -218,6 +218,8 @@
  * Input:
  *   phdr_table    -> program header table
  *   phdr_count    -> number of entries in the tables
+ *   required_base -> for prelinked libraries, mandatory load address
+ *                    of the first loadable segment. 0 otherwise.
  * Output:
  *   load_start    -> first page of reserved address space range
  *   load_size     -> size in bytes of reserved address space range
@@ -229,18 +231,22 @@
 int
 phdr_table_reserve_memory(const Elf32_Phdr* phdr_table,
                           size_t phdr_count,
+                          Elf32_Addr required_base,
                           void** load_start,
                           Elf32_Addr* load_size,
                           Elf32_Addr* load_bias)
 {
     Elf32_Addr size = phdr_table_get_load_size(phdr_table, phdr_count);
+
     if (size == 0) {
         errno = EINVAL;
         return -1;
     }
 
     int mmap_flags = MAP_PRIVATE | MAP_ANONYMOUS;
-    void* start = mmap(NULL, size, PROT_NONE, mmap_flags, -1, 0);
+    if (required_base != 0)
+        mmap_flags |= MAP_FIXED;
+    void* start = mmap((void*)required_base, size, PROT_NONE, mmap_flags, -1, 0);
     if (start == MAP_FAILED) {
         return -1;
     }