Merge "Add PT_ARM_EXIDX."
diff --git a/android-changes-for-ndk-developers.md b/android-changes-for-ndk-developers.md
index 5279118..c301857 100644
--- a/android-changes-for-ndk-developers.md
+++ b/android-changes-for-ndk-developers.md
@@ -316,6 +316,16 @@
the -soname linker option).
+## DT_RUNPATH support (Available in API level >= 24)
+
+If an ELF file contains a DT_RUNPATH entry, the directories listed there
+will be searched to resolve DT_NEEDED entries. The string `${ORIGIN}` will
+be rewritten at runtime to the directory containing the ELF file. This
+allows the use of relative paths. The `${LIB}` and `${PLATFORM}`
+substitutions supported on some systems are not currently implemented on
+Android.
+
+
## Writable and Executable Segments (Enforced for API level >= 26)
Each segment in an ELF file has associated flags that tell the
diff --git a/libc/arch-arm/include/machine/elf_machdep.h b/libc/arch-arm/include/machine/elf_machdep.h
index 3496b28..f7ee43f 100644
--- a/libc/arch-arm/include/machine/elf_machdep.h
+++ b/libc/arch-arm/include/machine/elf_machdep.h
@@ -3,12 +3,6 @@
#ifndef _ARM_ELF_MACHDEP_H_
#define _ARM_ELF_MACHDEP_H_
-#define ELF32_MACHDEP_ENDIANNESS ELFDATA2LSB
-
-#define ELF64_MACHDEP_ENDIANNESS XXX /* break compilation */
-#define ELF64_MACHDEP_ID_CASES \
- /* no 64-bit ELF machine types supported */
-
/* Processor specific flags for the ELF header e_flags field. */
#define EF_ARM_RELEXEC 0x00000001
#define EF_ARM_HASENTRY 0x00000002
@@ -30,14 +24,6 @@
#define EF_ARM_EABI_VER4 0x04000000
#define EF_ARM_EABI_VER5 0x05000000
-#define ELF32_MACHDEP_ID_CASES \
- case EM_ARM: \
- break;
-
-#define ELF32_MACHDEP_ID EM_ARM
-
-#define ARCH_ELFSIZE 32 /* MD native binary size */
-
/* Processor specific relocation types */
#define R_ARM_NONE 0
diff --git a/libc/arch-arm64/include/machine/elf_machdep.h b/libc/arch-arm64/include/machine/elf_machdep.h
index 6eab313..9f10b99 100644
--- a/libc/arch-arm64/include/machine/elf_machdep.h
+++ b/libc/arch-arm64/include/machine/elf_machdep.h
@@ -29,20 +29,6 @@
#ifndef _AARCH64_ELF_MACHDEP_H_
#define _AARCH64_ELF_MACHDEP_H_
-#if defined(__AARCH64EB__)
-#define ELF64_MACHDEP_ENDIANNESS ELFDATA2MSB
-#else
-#define ELF64_MACHDEP_ENDIANNESS ELFDATA2LSB
-#endif
-
-#define ELF64_MACHDEP_ID_CASES \
- case EM_AARCH64: \
- break;
-
-#define ELF64_MACHDEP_ID EM_AARCH64
-
-#define ARCH_ELFSIZE 64 /* MD native binary size */
-
/* Null relocations */
#define R_ARM_NONE 0
#define R_AARCH64_NONE 256
diff --git a/libc/arch-mips/include/machine/elf_machdep.h b/libc/arch-mips/include/machine/elf_machdep.h
index b6117f2..59e0974 100644
--- a/libc/arch-mips/include/machine/elf_machdep.h
+++ b/libc/arch-mips/include/machine/elf_machdep.h
@@ -3,26 +3,6 @@
#ifndef _MIPS_ELF_MACHDEP_H_
#define _MIPS_ELF_MACHDEP_H_
-#ifdef _LP64
-#define ARCH_ELFSIZE 64 /* MD native binary size */
-#else
-#define ARCH_ELFSIZE 32 /* MD native binary size */
-#endif
-
-#if ELFSIZE == 32
-#define ELF32_MACHDEP_ID_CASES \
- case EM_MIPS: \
- break;
-
-#define ELF32_MACHDEP_ID EM_MIPS
-#elif ELFSIZE == 64
-#define ELF64_MACHDEP_ID_CASES \
- case EM_MIPS: \
- break;
-
-#define ELF64_MACHDEP_ID EM_MIPS
-#endif
-
/* mips relocs. */
#define R_MIPS_NONE 0
@@ -151,7 +131,4 @@
#define EF_MIPS_ABI_EABI32 0x00003000
#define EF_MIPS_ABI_EABI64 0x00004000
-#define ELF32_MACHDEP_ENDIANNESS ELFDATA2LSB
-#define ELF64_MACHDEP_ENDIANNESS ELFDATA2LSB
-
#endif /* _MIPS_ELF_MACHDEP_H_ */
diff --git a/libc/arch-x86/include/machine/elf_machdep.h b/libc/arch-x86/include/machine/elf_machdep.h
index 4bce933..5324ebc 100644
--- a/libc/arch-x86/include/machine/elf_machdep.h
+++ b/libc/arch-x86/include/machine/elf_machdep.h
@@ -1,18 +1,7 @@
/* $NetBSD: elf_machdep.h,v 1.10 2009/05/30 05:56:52 skrll Exp $ */
-#define ELF32_MACHDEP_ENDIANNESS ELFDATA2LSB
-#define ELF32_MACHDEP_ID_CASES \
- case EM_386: \
- case EM_486: \
- break;
-
-#define ELF64_MACHDEP_ENDIANNESS XXX /* break compilation */
-#define ELF64_MACHDEP_ID_CASES \
- /* no 64-bit ELF machine types supported */
-
-#define ELF32_MACHDEP_ID EM_386
-
-#define ARCH_ELFSIZE 32 /* MD native binary size */
+#ifndef _X86_ELF_MACHDEP_H_
+#define _X86_ELF_MACHDEP_H_
/* i386 relocations */
#define R_386_NONE 0
@@ -62,3 +51,5 @@
#define R_386_IRELATIVE 42
#define R_TYPE(name) __CONCAT(R_386_,name)
+
+#endif
diff --git a/libc/arch-x86_64/include/machine/elf_machdep.h b/libc/arch-x86_64/include/machine/elf_machdep.h
index bf1f273..dedbd41 100644
--- a/libc/arch-x86_64/include/machine/elf_machdep.h
+++ b/libc/arch-x86_64/include/machine/elf_machdep.h
@@ -1,21 +1,7 @@
/* $NetBSD: elf_machdep.h,v 1.4 2010/03/18 08:28:33 cegger Exp $ */
-#if !defined __i386__
-
-#define ELF32_MACHDEP_ENDIANNESS ELFDATA2LSB
-#define ELF32_MACHDEP_ID_CASES \
- case EM_386: \
- break;
-
-#define ELF64_MACHDEP_ENDIANNESS ELFDATA2LSB
-#define ELF64_MACHDEP_ID_CASES \
- case EM_X86_64: \
- break;
-
-#define ELF32_MACHDEP_ID EM_386
-#define ELF64_MACHDEP_ID EM_X86_64
-
-#define ARCH_ELFSIZE 64 /* MD native binary size */
+#ifndef _X86_64_ELF_MACHDEP_H_
+#define _X86_64_ELF_MACHDEP_H_
/* x86-64 relocations */
@@ -50,8 +36,4 @@
#define R_TYPE(name) __CONCAT(R_X86_64_,name)
-#else /* !__i386__ */
-
-#include <i386/elf_machdep.h>
-
-#endif /* !__i386__ */
+#endif
diff --git a/libc/bionic/bionic_systrace.cpp b/libc/bionic/bionic_systrace.cpp
index 8e8ff76..5699f6e 100644
--- a/libc/bionic/bionic_systrace.cpp
+++ b/libc/bionic/bionic_systrace.cpp
@@ -14,7 +14,6 @@
* limitations under the License.
*/
-#include <cutils/trace.h>
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
@@ -23,55 +22,26 @@
#include "private/bionic_lock.h"
#include "private/bionic_systrace.h"
+#include "private/CachedProperty.h"
#include "private/libc_logging.h"
-#define _REALLY_INCLUDE_SYS__SYSTEM_PROPERTIES_H_
-#include <sys/_system_properties.h>
+#include <cutils/trace.h> // For ATRACE_TAG_BIONIC.
#define WRITE_OFFSET 32
-constexpr char SYSTRACE_PROPERTY_NAME[] = "debug.atrace.tags.enableflags";
-
static Lock g_lock;
-static const prop_info* g_pinfo;
-static uint32_t g_property_serial = -1;
-static uint32_t g_property_area_serial = -1;
-static uint64_t g_tags;
static int g_trace_marker_fd = -1;
static bool should_trace() {
- bool result = false;
- g_lock.lock();
- // debug.atrace.tags.enableflags is set to a safe non-tracing value during property
- // space initialization, so it should only be null in two cases, if there are
- // insufficient permissions for this process to access the property, in which
- // case an audit will be logged, and during boot before the property server has
- // been started, in which case we store the global property_area serial to prevent
- // the costly find operation until we see a changed property_area.
- if (g_pinfo == nullptr && g_property_area_serial != __system_property_area_serial()) {
- g_property_area_serial = __system_property_area_serial();
- g_pinfo = __system_property_find(SYSTRACE_PROPERTY_NAME);
- }
+ static CachedProperty g_debug_atrace_tags_enableflags("debug.atrace.tags.enableflags");
+ static uint64_t g_tags;
- if (g_pinfo) {
- // Find out which tags have been enabled on the command line and set
- // the value of tags accordingly. If the value of the property changes,
- // the serial will also change, so the costly system_property_read function
- // can be avoided by calling the much cheaper system_property_serial
- // first. The values within pinfo may change, but its location is guaranteed
- // not to move.
- uint32_t cur_serial = __system_property_serial(g_pinfo);
- if (cur_serial != g_property_serial) {
- __system_property_read_callback(g_pinfo,
- [] (void*, const char*, const char* value, uint32_t serial) {
- g_property_serial = serial;
- g_tags = strtoull(value, nullptr, 0);
- }, nullptr);
- }
- result = ((g_tags & ATRACE_TAG_BIONIC) != 0);
+ g_lock.lock();
+ if (g_debug_atrace_tags_enableflags.DidChange()) {
+ g_tags = strtoull(g_debug_atrace_tags_enableflags.Get(), nullptr, 0);
}
g_lock.unlock();
- return result;
+ return ((g_tags & ATRACE_TAG_BIONIC) != 0);
}
static int get_trace_marker_fd() {
diff --git a/libc/bionic/system_properties.cpp b/libc/bionic/system_properties.cpp
index e5947c8..9fb03ac 100644
--- a/libc/bionic/system_properties.cpp
+++ b/libc/bionic/system_properties.cpp
@@ -200,15 +200,6 @@
DISALLOW_IMPLICIT_CONSTRUCTORS(prop_info);
};
-struct find_nth_cookie {
- uint32_t count;
- const uint32_t n;
- const prop_info* pi;
-
- explicit find_nth_cookie(uint32_t n) : count(0), n(n), pi(nullptr) {
- }
-};
-
// This is public because it was exposed in the NDK. As of 2017-01, ~60 apps reference this symbol.
prop_area* __system_property_area__ = nullptr;
@@ -659,14 +650,6 @@
return result;
}
-static void find_nth_fn(const prop_info* pi, void* ptr) {
- find_nth_cookie* cookie = reinterpret_cast<find_nth_cookie*>(ptr);
-
- if (cookie->n == cookie->count) cookie->pi = pi;
-
- cookie->count++;
-}
-
bool prop_area::foreach_property(prop_bt* const trie,
void (*propfn)(const prop_info* pi, void* cookie), void* cookie) {
if (!trie) return false;
@@ -1456,20 +1439,19 @@
}
const prop_info* __system_property_find_nth(unsigned n) {
- if (bionic_get_application_target_sdk_version() >= __ANDROID_API_O__) {
- __libc_fatal(
- "__system_property_find_nth is not supported since Android O,"
- " please use __system_property_foreach instead.");
- }
+ struct find_nth {
+ const uint32_t sought;
+ uint32_t current;
+ const prop_info* result;
- find_nth_cookie cookie(n);
-
- const int err = __system_property_foreach(find_nth_fn, &cookie);
- if (err < 0) {
- return nullptr;
- }
-
- return cookie.pi;
+ explicit find_nth(uint32_t n) : sought(n), current(0), result(nullptr) {}
+ static void fn(const prop_info* pi, void* ptr) {
+ find_nth* self = reinterpret_cast<find_nth*>(ptr);
+ if (self->current++ == self->sought) self->result = pi;
+ }
+ } state(n);
+ __system_property_foreach(find_nth::fn, &state);
+ return state.result;
}
int __system_property_foreach(void (*propfn)(const prop_info* pi, void* cookie), void* cookie) {
@@ -1479,7 +1461,7 @@
list_foreach(contexts, [propfn, cookie](context_node* l) {
if (l->check_access_and_open()) {
- l->pa()->foreach (propfn, cookie);
+ l->pa()->foreach(propfn, cookie);
}
});
return 0;
diff --git a/libc/include/sys/system_properties.h b/libc/include/sys/system_properties.h
index b55566e..c0bd445 100644
--- a/libc/include/sys/system_properties.h
+++ b/libc/include/sys/system_properties.h
@@ -91,11 +91,11 @@
/* Deprecated. In Android O and above, there's no limit on property name length. */
#define PROP_NAME_MAX 32
/* Deprecated. Use __system_property_read_callback instead. */
-int __system_property_read(const prop_info *pi, char *name, char *value);
+int __system_property_read(const prop_info* pi, char* name, char* value);
/* Deprecated. Use __system_property_read_callback instead. */
-int __system_property_get(const char *name, char *value);
-/* Deprecated. Use __system_property_foreach instead. Aborts in Android O and above. */
-const prop_info *__system_property_find_nth(unsigned n) __REMOVED_IN(26);
+int __system_property_get(const char* name, char* value);
+/* Deprecated. Use __system_property_foreach instead. */
+const prop_info* __system_property_find_nth(unsigned n);
__END_DECLS
diff --git a/libc/private/CachedProperty.h b/libc/private/CachedProperty.h
index f0c81c9..417a855 100644
--- a/libc/private/CachedProperty.h
+++ b/libc/private/CachedProperty.h
@@ -46,6 +46,14 @@
cached_value_[0] = '\0';
}
+ // Returns true if the property has been updated (based on the serial rather than the value)
+ // since the last call to Get.
+ bool DidChange() {
+ uint32_t initial_property_serial_ = cached_property_serial_;
+ Get();
+ return (cached_property_serial_ != initial_property_serial_);
+ }
+
// Returns the current value of the underlying system property as cheaply as possible.
// The returned pointer is valid until the next call to Get. It is the caller's responsibility
// to provide a lock for thread-safety.
diff --git a/tests/system_properties_test.cpp b/tests/system_properties_test.cpp
index 23d0cad..7415b3c 100644
--- a/tests/system_properties_test.cpp
+++ b/tests/system_properties_test.cpp
@@ -253,10 +253,21 @@
ASSERT_EQ(0, __system_property_add("other_property", 14, "value2", 6));
ASSERT_EQ(0, __system_property_add("property_other", 14, "value3", 6));
- // This method is no longer supported and should result in abort
- ASSERT_EXIT(__system_property_find_nth(0), testing::KilledBySignal(SIGABRT),
- "__system_property_find_nth is not supported since Android O,"
- " please use __system_property_foreach instead.");
+ char name[PROP_NAME_MAX];
+ char value[PROP_VALUE_MAX];
+ EXPECT_EQ(6, __system_property_read(__system_property_find_nth(0), name, value));
+ EXPECT_STREQ("property", name);
+ EXPECT_STREQ("value1", value);
+ EXPECT_EQ(6, __system_property_read(__system_property_find_nth(1), name, value));
+ EXPECT_STREQ("other_property", name);
+ EXPECT_STREQ("value2", value);
+ EXPECT_EQ(6, __system_property_read(__system_property_find_nth(2), name, value));
+ EXPECT_STREQ("property_other", name);
+ EXPECT_STREQ("value3", value);
+
+ for (unsigned i = 3; i < 1024; ++i) {
+ ASSERT_TRUE(__system_property_find_nth(i) == nullptr);
+ }
#else // __BIONIC__
GTEST_LOG_(INFO) << "This test does nothing.\n";
#endif // __BIONIC__