Merge "Add test for elf-hash and packed relocations"
diff --git a/android-changes-for-ndk-developers.md b/android-changes-for-ndk-developers.md
index 5b0fe38..ec48870 100644
--- a/android-changes-for-ndk-developers.md
+++ b/android-changes-for-ndk-developers.md
@@ -321,3 +321,22 @@
 *Resolution*: don't use tools that produce invalid/malformed
 ELF files. Note that using them puts application under high risk of
 being incompatible with future versions of Android.
+
+## Enable logging of dlopen/dlsym and library loading errors for apps (Available in Android O)
+
+Starting with Android O it is possible to enable logging of all dlsym/dlopen calls
+for debuggable apps. Here is short instruction on how to do that:
+```
+adb shell setprop debug.ld.app.com.example.myapp dlsym,dlopen,dlerror
+adb logcat
+```
+
+Any subset of (dlsym,dlopen,dlerror) can be used.
+
+On userdebug and eng builds it is possible to enable tracing for the whole system
+by using debug.ld.all system property instead of app-specific one:
+```
+adb shell setprop debug.ld.all dlerror,dlopen
+```
+
+enables logging of all errors and dlopen calls
diff --git a/libc/bionic/__stack_chk_fail.cpp b/libc/bionic/__stack_chk_fail.cpp
index 6e052e3..cb039cf 100644
--- a/libc/bionic/__stack_chk_fail.cpp
+++ b/libc/bionic/__stack_chk_fail.cpp
@@ -32,5 +32,5 @@
 #include "private/libc_logging.h"
 
 void __stack_chk_fail() {
-  __libc_fatal("stack corruption detected");
+  __libc_fatal("stack corruption detected (-fstack-protector)");
 }
diff --git a/libc/include/sys/socket.h b/libc/include/sys/socket.h
index 8e05cf1..f9f6764 100644
--- a/libc/include/sys/socket.h
+++ b/libc/include/sys/socket.h
@@ -182,7 +182,9 @@
 #define AF_ALG 38
 #define AF_NFC 39
 #define AF_VSOCK 40
-#define AF_MAX 41
+#define AF_KCM 41
+#define AF_QIPCRTR 42
+#define AF_MAX 43
 
 #define PF_UNSPEC AF_UNSPEC
 #define PF_UNIX AF_UNIX
@@ -225,6 +227,8 @@
 #define PF_ALG AF_ALG
 #define PF_NFC AF_NFC
 #define PF_VSOCK AF_VSOCK
+#define PF_KCM AF_KCM
+#define PF_QIPCRTR AF_QIPCRTR
 #define PF_MAX AF_MAX
 
 #define SOMAXCONN 128
@@ -247,6 +251,7 @@
 #define MSG_NOSIGNAL 0x4000
 #define MSG_MORE 0x8000
 #define MSG_WAITFORONE 0x10000
+#define MSG_BATCH 0x40000
 #define MSG_FASTOPEN 0x20000000
 #define MSG_CMSG_CLOEXEC 0x40000000
 #define MSG_EOF MSG_FIN
@@ -275,6 +280,16 @@
 #define SOL_DCCP 269
 #define SOL_NETLINK 270
 #define SOL_TIPC 271
+#define SOL_RXRPC 272
+#define SOL_PPPOL2TP 273
+#define SOL_BLUETOOTH 274
+#define SOL_PNPIPE 275
+#define SOL_RDS 276
+#define SOL_IUCV 277
+#define SOL_CAIF 278
+#define SOL_ALG 279
+#define SOL_NFC 280
+#define SOL_KCM 281
 
 #define IPX_TYPE 1
 
diff --git a/libc/include/sys/types.h b/libc/include/sys/types.h
index 8188f89..637ef02 100644
--- a/libc/include/sys/types.h
+++ b/libc/include/sys/types.h
@@ -25,6 +25,7 @@
  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  * SUCH DAMAGE.
  */
+
 #ifndef _SYS_TYPES_H_
 #define _SYS_TYPES_H_
 
@@ -105,20 +106,6 @@
 typedef loff_t off64_t;
 #endif
 
-/* while POSIX wants these in <sys/types.h>, we
- * declare then in <pthread.h> instead */
-#if 0
-typedef  .... pthread_attr_t;
-typedef  .... pthread_cond_t;
-typedef  .... pthread_condattr_t;
-typedef  .... pthread_key_t;
-typedef  .... pthread_mutex_t;
-typedef  .... pthread_once_t;
-typedef  .... pthread_rwlock_t;
-typedef  .... pthread_rwlock_attr_t;
-typedef  .... pthread_t;
-#endif
-
 #if !defined(__LP64__)
 /* This historical accident means that we had a signed socklen_t on 32-bit architectures. */
 typedef int32_t __socklen_t;
diff --git a/linker/linker_logger.cpp b/linker/linker_logger.cpp
index a9d358a..8190cc9 100644
--- a/linker/linker_logger.cpp
+++ b/linker/linker_logger.cpp
@@ -45,6 +45,7 @@
 
 static const char* kOptionErrors = "dlerror";
 static const char* kOptionDlopen = "dlopen";
+static const char* kOptionDlsym = "dlsym";
 
 static std::string property_get(const char* name) {
   char value[PROP_VALUE_MAX] = {};
@@ -66,6 +67,8 @@
       flags |= kLogErrors;
     } else if (o == kOptionDlopen){
       flags |= kLogDlopen;
+    } else if (o == kOptionDlsym){
+      flags |= kLogDlsym;
     } else {
       __libc_format_log(ANDROID_LOG_WARN, "linker", "Unknown debug.ld option \"%s\", will ignore.", o.c_str());
     }
diff --git a/tests/dlfcn_test.cpp b/tests/dlfcn_test.cpp
index 1721019..76cf8de 100644
--- a/tests/dlfcn_test.cpp
+++ b/tests/dlfcn_test.cpp
@@ -184,6 +184,16 @@
   dlclose(handle);
 }
 
+TEST(dlfcn, dlsym_handle_empty_symbol) {
+  // check that dlsym of an empty symbol fails (see http://b/33530622)
+  void* handle = dlopen("libtest_dlsym_from_this.so", RTLD_NOW);
+  ASSERT_TRUE(handle != nullptr) << dlerror();
+  void* sym = dlsym(handle, "");
+  ASSERT_TRUE(sym == nullptr);
+  ASSERT_SUBSTR("undefined symbol: ", dlerror());
+  dlclose(handle);
+}
+
 TEST(dlfcn, dlsym_with_dependencies) {
   void* handle = dlopen("libtest_with_dependency.so", RTLD_NOW);
   ASSERT_TRUE(handle != nullptr);