Support priority inheritance mutex in 32-bit programs.

Add fast path calling PIMutexTryLock() in pthread_mutex_lock.
Add trace for pi mutex waiting.

Bug: http://b/29177606
Test: run bionic-unit-tests.
Test: run bionic-benchmarks.

Change-Id: I30b6436692d5ea6b63ca9905df745edb843b5528
diff --git a/tests/pthread_test.cpp b/tests/pthread_test.cpp
index 9ecb10c..40059d0 100644
--- a/tests/pthread_test.cpp
+++ b/tests/pthread_test.cpp
@@ -1730,15 +1730,42 @@
 }
 
 TEST(pthread, pthread_mutex_lock_pi) {
-#if defined(__BIONIC__) && !defined(__LP64__)
-  GTEST_LOG_(INFO) << "PTHREAD_PRIO_INHERIT isn't supported in 32bit programs, skipping test";
-  return;
-#endif
   TestPthreadMutexLockNormal(PTHREAD_PRIO_INHERIT);
   TestPthreadMutexLockErrorCheck(PTHREAD_PRIO_INHERIT);
   TestPthreadMutexLockRecursive(PTHREAD_PRIO_INHERIT);
 }
 
+TEST(pthread, pthread_mutex_pi_count_limit) {
+#if defined(__BIONIC__) && !defined(__LP64__)
+  // Bionic only supports 65536 pi mutexes in 32-bit programs.
+  pthread_mutexattr_t attr;
+  ASSERT_EQ(0, pthread_mutexattr_init(&attr));
+  ASSERT_EQ(0, pthread_mutexattr_setprotocol(&attr, PTHREAD_PRIO_INHERIT));
+  std::vector<pthread_mutex_t> mutexes(65536);
+  // Test if we can use 65536 pi mutexes at the same time.
+  // Run 2 times to check if freed pi mutexes can be recycled.
+  for (int repeat = 0; repeat < 2; ++repeat) {
+    for (auto& m : mutexes) {
+      ASSERT_EQ(0, pthread_mutex_init(&m, &attr));
+    }
+    pthread_mutex_t m;
+    ASSERT_EQ(ENOMEM, pthread_mutex_init(&m, &attr));
+    for (auto& m : mutexes) {
+      ASSERT_EQ(0, pthread_mutex_lock(&m));
+    }
+    for (auto& m : mutexes) {
+      ASSERT_EQ(0, pthread_mutex_unlock(&m));
+    }
+    for (auto& m : mutexes) {
+      ASSERT_EQ(0, pthread_mutex_destroy(&m));
+    }
+  }
+  ASSERT_EQ(0, pthread_mutexattr_destroy(&attr));
+#else
+  GTEST_LOG_(INFO) << "This test does nothing as pi mutex count isn't limited.\n";
+#endif
+}
+
 TEST(pthread, pthread_mutex_init_same_as_static_initializers) {
   pthread_mutex_t lock_normal = PTHREAD_MUTEX_INITIALIZER;
   PthreadMutex m1(PTHREAD_MUTEX_NORMAL);
@@ -1755,6 +1782,7 @@
   ASSERT_EQ(0, memcmp(&lock_recursive, &m3.lock, sizeof(pthread_mutex_t)));
   ASSERT_EQ(0, pthread_mutex_destroy(&lock_recursive));
 }
+
 class MutexWakeupHelper {
  private:
   PthreadMutex m;
@@ -1903,10 +1931,6 @@
 };
 
 TEST(pthread, pthread_mutex_pi_wakeup) {
-#if defined(__BIONIC__) && !defined(__LP64__)
-  GTEST_LOG_(INFO) << "PTHREAD_PRIO_INHERIT isn't supported in 32bit programs, skipping test";
-  return;
-#endif
   for (int type : {PTHREAD_MUTEX_NORMAL, PTHREAD_MUTEX_RECURSIVE, PTHREAD_MUTEX_ERRORCHECK}) {
     for (int protocol : {PTHREAD_PRIO_INHERIT}) {
       PIMutexWakeupHelper helper(type, protocol);
@@ -1959,10 +1983,6 @@
 }
 
 TEST(pthread, pthread_mutex_timedlock_pi) {
-#if defined(__BIONIC__) && !defined(__LP64__)
-  GTEST_LOG_(INFO) << "PTHREAD_PRIO_INHERIT isn't supported in 32bit programs, skipping test";
-  return;
-#endif
   PthreadMutex m(PTHREAD_MUTEX_NORMAL, PTHREAD_PRIO_INHERIT);
   timespec ts;
   clock_gettime(CLOCK_REALTIME, &ts);