Updated to arc-runtime-43.4410.311.0
diff --git a/mods/android/system/core/libutils/SystemClock.cpp b/mods/android/system/core/libutils/SystemClock.cpp
deleted file mode 100644
index 229c881..0000000
--- a/mods/android/system/core/libutils/SystemClock.cpp
+++ /dev/null
@@ -1,175 +0,0 @@
-/*
- * Copyright (C) 2008 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-
-/*
- * System clock functions.
- */
-
-#ifdef HAVE_ANDROID_OS
-/* ARC MOD BEGIN */
-#if !defined(HAVE_ARC)
-# include <linux/ioctl.h>
-# include <linux/rtc.h>
-#endif
-/* ARC MOD END */
-#include <utils/Atomic.h>
-#include <linux/android_alarm.h>
-#endif
-
-#include <sys/time.h>
-#include <limits.h>
-#include <fcntl.h>
-#include <errno.h>
-#include <string.h>
-
-#include <utils/SystemClock.h>
-#include <utils/Timers.h>
-
-#define LOG_TAG "SystemClock"
-#include <utils/Log.h>
-
-namespace android {
-
-/*
- * native public static long uptimeMillis();
- */
-int64_t uptimeMillis()
-{
-    int64_t when = systemTime(SYSTEM_TIME_MONOTONIC);
-    return (int64_t) nanoseconds_to_milliseconds(when);
-}
-
-/*
- * native public static long elapsedRealtime();
- */
-int64_t elapsedRealtime()
-{
-	return nanoseconds_to_milliseconds(elapsedRealtimeNano());
-}
-
-#define METHOD_CLOCK_GETTIME    0
-#define METHOD_IOCTL            1
-#define METHOD_SYSTEMTIME       2
-
-/*
- * To debug/verify the timestamps returned by the kernel, change
- * DEBUG_TIMESTAMP to 1 and call the timestamp routine from a single thread
- * in the test program. b/10899829
- */
-#define DEBUG_TIMESTAMP         0
-
-static const char *gettime_method_names[] = {
-    "clock_gettime",
-    "ioctl",
-    "systemTime",
-};
-
-#if DEBUG_TIMESTAMP
-static inline void checkTimeStamps(int64_t timestamp,
-                                   int64_t volatile *prevTimestampPtr,
-                                   int volatile *prevMethodPtr,
-                                   int curMethod)
-{
-    /*
-     * Disable the check for SDK since the prebuilt toolchain doesn't contain
-     * gettid, and int64_t is different on the ARM platform
-     * (ie long vs long long).
-     */
-#ifdef ARCH_ARM
-    int64_t prevTimestamp = *prevTimestampPtr;
-    int prevMethod = *prevMethodPtr;
-
-    if (timestamp < prevTimestamp) {
-        ALOGW("time going backwards: prev %lld(%s) vs now %lld(%s), tid=%d",
-              prevTimestamp, gettime_method_names[prevMethod],
-              timestamp, gettime_method_names[curMethod],
-              gettid());
-    }
-    // NOTE - not atomic and may generate spurious warnings if the 64-bit
-    // write is interrupted or not observed as a whole.
-    *prevTimestampPtr = timestamp;
-    *prevMethodPtr = curMethod;
-#endif
-}
-#else
-#define checkTimeStamps(timestamp, prevTimestampPtr, prevMethodPtr, curMethod)
-#endif
-
-/*
- * native public static long elapsedRealtimeNano();
- */
-int64_t elapsedRealtimeNano()
-{
-/* ARC MOD BEGIN */
-// /dev/alarm is not available on non-Android kernel.
-#if defined HAVE_ANDROID_OS && !(defined HAVE_ARC)
-/* ARC MOD END */
-    struct timespec ts;
-    int result;
-    int64_t timestamp;
-#if DEBUG_TIMESTAMP
-    static volatile int64_t prevTimestamp;
-    static volatile int prevMethod;
-#endif
-
-#if 0
-    /*
-     * b/7100774
-     * clock_gettime appears to have clock skews and can sometimes return
-     * backwards values. Disable its use until we find out what's wrong.
-     */
-    result = clock_gettime(CLOCK_BOOTTIME, &ts);
-    if (result == 0) {
-        timestamp = seconds_to_nanoseconds(ts.tv_sec) + ts.tv_nsec;
-        checkTimeStamps(timestamp, &prevTimestamp, &prevMethod,
-                        METHOD_CLOCK_GETTIME);
-        return timestamp;
-    }
-#endif
-
-    // CLOCK_BOOTTIME doesn't exist, fallback to /dev/alarm
-    static int s_fd = -1;
-
-    if (s_fd == -1) {
-        int fd = open("/dev/alarm", O_RDONLY);
-        if (android_atomic_cmpxchg(-1, fd, &s_fd)) {
-            close(fd);
-        }
-    }
-
-    result = ioctl(s_fd,
-            ANDROID_ALARM_GET_TIME(ANDROID_ALARM_ELAPSED_REALTIME), &ts);
-
-    if (result == 0) {
-        timestamp = seconds_to_nanoseconds(ts.tv_sec) + ts.tv_nsec;
-        checkTimeStamps(timestamp, &prevTimestamp, &prevMethod, METHOD_IOCTL);
-        return timestamp;
-    }
-
-    // XXX: there was an error, probably because the driver didn't
-    // exist ... this should return
-    // a real error, like an exception!
-    timestamp = systemTime(SYSTEM_TIME_MONOTONIC);
-    checkTimeStamps(timestamp, &prevTimestamp, &prevMethod,
-                    METHOD_SYSTEMTIME);
-    return timestamp;
-#else
-    return systemTime(SYSTEM_TIME_MONOTONIC);
-#endif
-}
-
-}; // namespace android
diff --git a/src/build/DEPS.arc-int b/src/build/DEPS.arc-int
index 7c16ce3..2269354 100644
--- a/src/build/DEPS.arc-int
+++ b/src/build/DEPS.arc-int
@@ -1 +1 @@
-d87cf4906a273dec40ed6249aa23555fbc1223e4
+178e78eb874a8ad7bec6dfdbbde99015f543c30d
diff --git a/src/build/ninja_generator.py b/src/build/ninja_generator.py
index caf90a7..c5f9d38 100644
--- a/src/build/ninja_generator.py
+++ b/src/build/ninja_generator.py
@@ -908,11 +908,12 @@
         self.add_include_paths('android/bionic/libc/include')
     if gl_flags:
       self.emit_gl_common_flags()
-    # We need 4-byte alignment to pass host function pointers to arm code.
-    if not self._is_host and not OPTIONS.is_nacl_build():
-      self.add_compiler_flags('-falign-functions=4')
     self._enable_clang = (enable_clang and
                           toolchain.has_clang(OPTIONS.target(), self._is_host))
+    # We need 4-byte alignment to pass host function pointers to arm code.
+    if (not self._is_host and not OPTIONS.is_nacl_build() and
+        not self._enable_clang):
+      self.add_compiler_flags('-falign-functions=4')
     self._object_list = []
     self._shared_deps = []
     self._static_deps = []
@@ -3604,9 +3605,6 @@
 class AaptNinjaGenerator(NinjaGenerator):
   """Implements a simple aapt package generator."""
 
-  _resource_paths = []
-  _assets_path = None
-
   def __init__(self, module_name, base_path, manifest, intermediates,
                install_path=None, **kwargs):
     super(AaptNinjaGenerator, self).__init__(
@@ -3614,6 +3612,8 @@
     self._manifest = manifest
     self._intermediates = intermediates
     self._install_path = install_path
+    self._resource_paths = []
+    self._assets_path = None
 
   def add_resource_paths(self, paths):
     self._resource_paths += paths
diff --git a/src/build/staging.py b/src/build/staging.py
index 688218d..7b6d33d 100755
--- a/src/build/staging.py
+++ b/src/build/staging.py
@@ -212,7 +212,7 @@
   for dirpath, dirs, fnames in os.walk(root):
     for name in fnames:
       link_path = os.path.join(dirpath, name)
-      if os.path.islink(link_path):
+      if os.path.islink(link_path) and os.path.isfile(link_path):
         link_target_map[link_path] = os.readlink(link_path)
   return link_target_map
 
@@ -247,11 +247,36 @@
 
   # Update modification time for files that do not point to the same location
   # that they pointed to in the previous tree to make sure they are built.
-  new_staging_links = _get_link_targets(staging_root)
-  for key in new_staging_links:
-    if key in old_staging_links:
-      if old_staging_links[key] != new_staging_links[key]:
-        os.utime(key, None)
+
+  if old_staging_links:
+    new_staging_links = _get_link_targets(staging_root)
+
+    # Every file under staging is in either one of following two states:
+    #
+    #   F. The file itself is a symbolic link to a file under third_party or
+    #      mods.
+    #   D. Some ancestor directory is a symbolic link to a directory under
+    #      third_party. (It is important that we do not create symbolic links to
+    #      directories under mods)
+    #
+    # Note that a file is in state F if and only if it is in |*_staging_links|
+    # dictionary. Let us say a file falls under "X-Y" case if it was in state X
+    # before re-staging and now in state Y. For all 4 possible cases, we can
+    # check if the actual destination of the file changed or not in the
+    # following way:
+    #
+    #   F-F: We can just compare the target of the link.
+    #   F-D, D-F: The target may have changed, but it needs some complicated
+    #        computation to check. We treat them as changed to be conservative.
+    #   D-D: We can leave it as-is since both point third_party.
+
+    for path in set(list(old_staging_links) + list(new_staging_links)):
+      if path in old_staging_links and path in new_staging_links:
+        should_touch = old_staging_links[path] != new_staging_links[path]
+      else:
+        should_touch = True
+      if should_touch and os.path.exists(path):
+        os.utime(path, None)
 
   timer.done()
   return True
diff --git a/src/common/arc_strace.cc b/src/common/arc_strace.cc
index e75c71b..c915e80 100644
--- a/src/common/arc_strace.cc
+++ b/src/common/arc_strace.cc
@@ -10,6 +10,7 @@
 #include <errno.h>
 #include <fcntl.h>
 #include <inttypes.h>
+#include <linux/android_alarm.h>  // ANDROID_ALARM_*
 #include <linux/ashmem.h>  // ASHMEM_*
 #include <linux/sched.h>  // SCHED_BATCH
 #include <linux/sync.h>  // SYNC_IOC_*
@@ -675,6 +676,14 @@
   g_arc_strace->ResetStats();
 }
 
+std::string GetStraceEnterString(const char* name, const char* format, ...) {
+  va_list ap;
+  va_start(ap, format);
+  std::string body = base::StringPrintV(format, ap);
+  va_end(ap);
+  return base::StringPrintf("%s(%s)", name, body.c_str());
+}
+
 void StraceInit(const std::string& plugin_type_prefix) {
   ALOG_ASSERT(!g_arc_strace);
   if (Options::GetInstance()->enable_arc_strace) {
@@ -776,8 +785,9 @@
 }
 
 std::string GetFdStr(int fd) {
-  ALOG_ASSERT(g_arc_strace);
-  const std::string result = g_arc_strace->GetFdString(fd);
+  std::string result;
+  if (g_arc_strace)
+    result = g_arc_strace->GetFdString(fd);
   return result.empty() ? "???" : result;
 }
 
@@ -1169,6 +1179,8 @@
   std::string result;
   switch (request) {
     CASE_APPEND_ENUM_STR(FIONREAD, result);
+    CASE_APPEND_ENUM_STR(ANDROID_ALARM_WAIT, result);
+    CASE_APPEND_ENUM_STR(ANDROID_ALARM_SET_RTC, result);
     default: {
       // Unable to write switch-case since Bionic ioctl.h enables _IOC_TYPECHECK
       // which is not allowed in constant expression.
@@ -1200,6 +1212,38 @@
       } else if (urequest == ASHMEM_PURGE_ALL_CACHES) {
         AppendResult("ASHMEM_PURGE_ALL_CACHES", &result);
       } else {
+        int android_alarm_cmd = ANDROID_ALARM_BASE_CMD(request);
+        int android_alarm_type = ANDROID_ALARM_IOCTL_TO_TYPE(request);
+        std::string cmd_str;
+        // To get command value, passing "0" for each macro.
+        switch (android_alarm_cmd) {
+          case ANDROID_ALARM_GET_TIME(0):
+            cmd_str = "ANDROID_ALARM_GET_TIME";
+            break;
+          case ANDROID_ALARM_CLEAR(0):
+            cmd_str = "ANDROID_ALARM_CLEAR";
+            break;
+          case ANDROID_ALARM_SET_AND_WAIT(0):
+            cmd_str = "ANDROID_ALARM_SET_AND_WAIT";
+            break;
+          case ANDROID_ALARM_SET(0):
+            cmd_str = "ANDROID_ALARM_SET";
+            break;
+        }
+        std::string type_str;
+        switch (android_alarm_type) {
+          CASE_APPEND_ENUM_STR(ANDROID_ALARM_RTC_WAKEUP, type_str);
+          CASE_APPEND_ENUM_STR(ANDROID_ALARM_RTC, type_str);
+          CASE_APPEND_ENUM_STR(ANDROID_ALARM_ELAPSED_REALTIME_WAKEUP, type_str);
+          CASE_APPEND_ENUM_STR(ANDROID_ALARM_ELAPSED_REALTIME, type_str);
+          CASE_APPEND_ENUM_STR(ANDROID_ALARM_SYSTEMTIME, type_str);
+        }
+
+        if (!cmd_str.empty() && !type_str.empty()) {
+          result = cmd_str + "(" + type_str + ")";
+          break;
+        }
+
         AppendResult(base::StringPrintf("%d???", request), &result);
       }
     }
diff --git a/src/common/arc_strace.h b/src/common/arc_strace.h
index 7f39852..b3a1a25 100644
--- a/src/common/arc_strace.h
+++ b/src/common/arc_strace.h
@@ -74,6 +74,8 @@
 void StraceDupFD(int oldfd, int newfd);
 void StraceDumpStats(const std::string& user_str);
 void StraceResetStats();
+std::string GetStraceEnterString(const char* name, const char* format, ...)
+    ATTR_PRINTF(2, 3);
 
 // Pretty printers for enum values.
 std::string GetAccessModeStr(int mode);
@@ -81,7 +83,6 @@
 std::string GetDlopenFlagStr(int flag);
 std::string GetEpollCtlOpStr(int op);
 std::string GetEpollEventStr(uint32_t events);
-std::string GetFdStr(int fd);
 std::string GetMadviseAdviceStr(int advice);
 std::string GetMmapProtStr(int prot);
 std::string GetMmapFlagStr(int flag);
@@ -98,6 +99,10 @@
 std::string GetFcntlCommandStr(int cmd);
 std::string GetIoctlRequestStr(int request);
 
+// A pretty printer for file descriptors. You can call this even when ARC-strace
+// is not enabled, but in that case, the function returns "???".
+std::string GetFdStr(int fd);
+
 // Pretty printers for struct values.
 std::string GetSockaddrStr(const struct sockaddr* addr, socklen_t addrlen);
 std::string GetDirentStr(const struct dirent* ent);
@@ -125,19 +130,64 @@
 // display variable arguments. You must call ARC_STRACE_RETURN* if
 // you called this.
 //
+// Note: Unlike others, this macro emits TWO blocks. Use with caution.
+//
 // TODO(crbug.com/345825): Reorganize the macros.
-# define ARC_STRACE_ENTER(...) do {           \
-    if (arc::StraceEnabled())                 \
-      arc::StraceEnter(__VA_ARGS__);          \
+# define ARC_STRACE_ENTER(...)                                                \
+  /* Remember the parameters passed to the macro without evaluating them. */  \
+  auto arc_strace_get_enter_string__                                          \
+  __attribute__((unused)) = [&]() -> std::string { /* NOLINT(build/c++11) */  \
+    return arc::GetStraceEnterString(__VA_ARGS__);                            \
+  };                                                                          \
+  do {                                                                        \
+    if (arc::StraceEnabled())                                                 \
+      arc::StraceEnter(__VA_ARGS__);                                          \
   } while (0)
 
 // ARC_STRACE_ENTER_FD(const char* name, const char* format, int fd, ...)
 //
 // The pathname or stream type of |fd| will be displayed. |format|
 // must start with "%d". Otherwise, this is as same as ARC_STRACE_ENTER.
-# define ARC_STRACE_ENTER_FD(...) do {        \
-    if (arc::StraceEnabled())                 \
-      arc::StraceEnterFD(__VA_ARGS__);        \
+//
+// Note: Unlike others, this macro emits TWO blocks. Use with caution.
+# define ARC_STRACE_ENTER_FD(...)                                             \
+  /* Remember the parameters passed to the macro without evaluating them. */  \
+  auto arc_strace_get_enter_string__                                          \
+  __attribute__((unused)) = [&]() -> std::string { /* NOLINT(build/c++11) */  \
+    return arc::GetStraceEnterString(__VA_ARGS__);                            \
+  };                                                                          \
+  do {                                                                        \
+    if (arc::StraceEnabled())                                                 \
+      arc::StraceEnterFD(__VA_ARGS__);                                        \
+  } while (0)
+
+// ARC_STRACE_ALWAYS_WARN_FAILURE()
+//
+// Emits a warning log that contains the current function name,
+// its parameters (pretty-printed), and the current errno.
+// This macro works regardress of whether ARC-strace is enabled or not,
+// but ARC_STRACE_ENTER*() must be called in the same function before
+// this macro is called.
+# define ARC_STRACE_ALWAYS_WARN_FAILURE() do {                    \
+    /* Do not check arc::StraceEnabled() here, hence 'ALWAYS' */  \
+    ALOGW("FAILED: %s: errno=%d (%s)",                            \
+          arc_strace_get_enter_string__().c_str(),                \
+          errno, safe_strerror(errno).c_str());                   \
+  } while (0)
+
+// ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED()
+//
+// Emits a warning log that contains the current function name,
+// its parameters (pretty-printed). This also calls ARC_STRACE_REPORT
+// with "not implemented yet".
+// This macro works regardress of whether ARC-strace is enabled or not,
+// but ARC_STRACE_ENTER*() must be called in the same function before
+// this macro is called.
+# define ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED() do {             \
+    /* Do not check arc::StraceEnabled() here, hence 'ALWAYS' */  \
+    ALOGW("NOT IMPLEMENTED: %s",                                  \
+          arc_strace_get_enter_string__().c_str());               \
+    ARC_STRACE_REPORT("not implemented yet");                     \
   } while (0)
 
 // ARC_STRACE_REPORT_HANDLER(const char* handler_name)
diff --git a/src/common/dlfcn_injection.cc b/src/common/dlfcn_injection.cc
index 99b85e3..8ee1874 100644
--- a/src/common/dlfcn_injection.cc
+++ b/src/common/dlfcn_injection.cc
@@ -75,9 +75,11 @@
   // of host's, we inject the syscall function for ARM.
   (*g_wrapped_symbol_map)["syscall"] =
       reinterpret_cast<void*>(&RunArmLibcSyscall);
-  // See src/common/ndk_support/mmap.cc for detail.
+  // See src/common/ndk_support/mmap.h for detail.
   (*g_wrapped_symbol_map)["mmap"] =
       reinterpret_cast<void*>(&MmapForNdk);
+  (*g_wrapped_symbol_map)["mprotect"] =
+      reinterpret_cast<void*>(&MprotectForNdk);
 #endif
 
   // Inject the custom symbol resolver and posix_translation based
diff --git a/src/common/ndk_support/mmap.cc b/src/common/ndk_support/mmap.cc
index fa4e89a..6953636 100644
--- a/src/common/ndk_support/mmap.cc
+++ b/src/common/ndk_support/mmap.cc
@@ -9,7 +9,12 @@
 #include <sys/mman.h>
 #include <unistd.h>
 
-#include "common/scoped_pthread_mutex_locker.h"
+#include <string>
+
+#include "base/md5.h"
+#include "common/alog.h"
+#include "common/mprotect_rwx.h"
+#include "common/options.h"
 
 namespace arc {
 
@@ -17,11 +22,55 @@
 
 uintptr_t g_mmap_hint_addr = 0x70000000;
 
+bool ShouldAllowDefaultAddressHint() {
+  // For now, we always give the default address hint on SFI NaCl as
+  // the address hint will not be bad for security on SFI NaCl.
+#if defined(__native_client__)
+  return true;
+#else
+  // Old NDK apps require the default address hint. If an app crashes
+  // inside its own copy of the Bionic's linker, saying something like
+  // "no vspace available", you would likely need to flip this.
+  //
+  // As this feature is bad for security, this is only for
+  // testing. You should manually flip this bit to test such apps.
+  // When we need to launch apps which require this, you should ask
+  // the app author to upgrade their runtime.
+  return false;
+#endif
+}
+
+#if defined(USE_NDK_DIRECT_EXECUTION)
+pthread_once_t g_tls_init = PTHREAD_ONCE_INIT;
+bool g_should_allow_rwx_pages;
+
+// We allow a few whitelisted apps to use RWX pages. Although an APK
+// package author can arbitrary choose the package name, this is safe
+// as long as ARC is running for only whitelisted packages.
+// TODO(crbug.com/462642): We need to update this comment and code
+// when we remove ARC whitelist.
+//
+// Please make sure you get an approval from security team when you
+// add an app to this list.
+void InitShouldAllowRwxPages() {
+  const std::string md5 = base::MD5String(
+      Options::GetInstance()->package_name);
+  g_should_allow_rwx_pages = (
+      md5 == "a1b1bbe5f63d5b96c1a0f87c197ebfae" ||
+      md5 == "77f62c7141dd3730bf844c1c55e92b1f");
+}
+
+bool ShouldAllowRwxPages() {
+  pthread_once(&g_tls_init, InitShouldAllowRwxPages);
+  return g_should_allow_rwx_pages;
+}
+#endif
+
 }  // namespace
 
 void* MmapForNdk(void* addr, size_t length, int prot, int flags,
                  int fd, off_t offset) {
-  if (!addr && !(flags & MAP_FIXED)) {
+  if (!addr && !(flags & MAP_FIXED) && ShouldAllowDefaultAddressHint()) {
     // We use 0x70000000 as the first hint address. Then, the next
     // hint address will be increased by |length|, so this function
     // will likely keep satisfying the limitation of old Bionic's
@@ -33,8 +82,6 @@
     //
     // Such NDK apps call mmap with NULL |addr| only twice at their
     // start-ups. On SFI NaCl these addresses are always not used.
-    // TODO(hamaji): Check if ASLR on BMM does never use this region
-    // and update the comment and/or code.
     //
     // Essentially this way we emulate Android's mmap() behavior
     // better, by hinting where it shall allocate, if application has
@@ -43,7 +90,39 @@
         __sync_fetch_and_add(&g_mmap_hint_addr,
                              (length + PAGE_SIZE - 1) & ~(PAGE_SIZE - 1)));
   }
-  return mmap(addr, length, prot, flags, fd, offset);
+
+#if defined(USE_NDK_DIRECT_EXECUTION)
+  bool needs_wx_prot = false;
+  if ((prot & PROT_WRITE) && (prot & PROT_EXEC) && ShouldAllowRwxPages()) {
+    prot &= ~PROT_EXEC;
+    needs_wx_prot = true;
+  }
+  // Even when RWX mmap is requested and ShouldAllowRwxPages()
+  // returns false, call normal libc's mmap which will not honor
+  // RWX permissions. See also libc/arch-nacl/syscalls/mmap.c.
+#endif
+
+  void* result = mmap(addr, length, prot, flags, fd, offset);
+
+#if defined(USE_NDK_DIRECT_EXECUTION)
+  if (needs_wx_prot && result != MAP_FAILED) {
+    int r = MprotectRWX(result, length);
+    LOG_ALWAYS_FATAL_IF(r != 0, "RWX mprotect unexpectedly failed");
+  }
+#endif
+
+  return result;
 }
 
+#if defined(USE_NDK_DIRECT_EXECUTION)
+int MprotectForNdk(void* addr, size_t len, int prot) {
+  if ((prot & PROT_WRITE) && (prot & PROT_EXEC) && ShouldAllowRwxPages())
+    return MprotectRWX(addr, len);
+  // Even when RWX mprotect is requested and ShouldAllowRwxPages()
+  // returns false, call normal libc's mprotect which will not honor
+  // RWX permissions. See also libc/arch-nacl/syscalls/mprotect.c.
+  return mprotect(addr, len, prot);
+}
+#endif
+
 }  // namespace arc
diff --git a/src/common/ndk_support/mmap.h b/src/common/ndk_support/mmap.h
index 2dab9b8..e8e2a05 100644
--- a/src/common/ndk_support/mmap.h
+++ b/src/common/ndk_support/mmap.h
@@ -16,9 +16,17 @@
 // https://android.googlesource.com/platform/bionic/+/gingerbread/linker/linker.c
 // TODO(olonho): investigate why even with hint 0 linker expects memory
 // in certain range. Short ARM branches?
+//
+// Also handle RWX pages for whitelisted apps on Bare Metal mode.
 void* MmapForNdk(void* addr, size_t length, int prot, int flags,
                  int fd, off_t offset);
 
+#if defined(USE_NDK_DIRECT_EXECUTION)
+// Handles RWX pages for whitelisted apps on Bare Metal mode with NDK
+// direct execution.
+int MprotectForNdk(void* addr, size_t len, int prot);
+#endif
+
 }  // namespace arc
 
 #endif  // COMMON_NDK_SUPPORT_MMAP_H_
diff --git a/src/posix_translation/dev_alarm.cc b/src/posix_translation/dev_alarm.cc
new file mode 100644
index 0000000..591599f
--- /dev/null
+++ b/src/posix_translation/dev_alarm.cc
@@ -0,0 +1,132 @@
+// Copyright (c) 2015 The Chromium OS Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "posix_translation/dev_alarm.h"
+
+#include <linux/android_alarm.h>
+#include <string.h>
+
+#include "posix_translation/dir.h"
+#include "posix_translation/statfs.h"
+#include "posix_translation/virtual_file_system.h"
+
+namespace posix_translation {
+
+namespace {
+
+int DoStatLocked(const std::string& pathname, struct stat* out) {
+  memset(out, 0, sizeof(struct stat));
+  // Follwoing values are from Android device.
+  out->st_dev = 11;
+  out->st_ino =
+      VirtualFileSystem::GetVirtualFileSystem()->GetInodeLocked(pathname);
+  out->st_mode = S_IFCHR | 0664;
+  out->st_nlink = 1;
+  out->st_uid = 1000;
+  out->st_gid = 1001;
+  out->st_rdev = DeviceHandler::GetDeviceId(pathname);
+  out->st_size = 0;
+  out->st_blksize = 4096;
+  out->st_blocks = 0;
+  return 0;
+}
+
+}  // namespace
+
+DevAlarmHandler::DevAlarmHandler() : DeviceHandler("DevAlarmHandler") {
+}
+
+DevAlarmHandler::~DevAlarmHandler() {
+}
+
+scoped_refptr<FileStream> DevAlarmHandler::open(
+    int fd, const std::string& pathname, int oflag, mode_t cmode) {
+  if (oflag & O_DIRECTORY) {
+    errno = ENOTDIR;
+    return NULL;
+  }
+  return new DevAlarm(pathname, oflag, boottime_origin_);
+}
+
+int DevAlarmHandler::stat(const std::string& pathname, struct stat* out) {
+  return DoStatLocked(pathname, out);
+}
+
+DevAlarm::DevAlarm(const std::string& pathname, int oflag,
+                   const timespec& boottime_origin)
+    : DeviceStream(oflag, pathname) {
+}
+
+DevAlarm::~DevAlarm() {
+}
+
+int DevAlarm::fstat(struct stat* out) {
+  return DoStatLocked(pathname(), out);
+}
+
+ssize_t DevAlarm::read(void* buf, size_t count) {
+  errno = EINVAL;
+  return -1;
+}
+
+ssize_t DevAlarm::write(const void* buf, size_t count) {
+  errno = EBADF;
+  return -1;
+}
+
+int DevAlarm::ioctl(int request, va_list ap) {
+  // The alarm ioctl request is constructed by two part: the upper 4 bits are
+  // for alarm type and lower 4 bits are for alarm command.
+  int command = ANDROID_ALARM_BASE_CMD(request);
+  int alarm_type = ANDROID_ALARM_IOCTL_TO_TYPE(request);
+
+  // Getting command value by specifying "0" for each macro.
+  switch (command) {
+    case ANDROID_ALARM_GET_TIME(0):
+      return GetTime(alarm_type, va_arg(ap, timespec*));
+    case ANDROID_ALARM_CLEAR(0):
+    case ANDROID_ALARM_SET_AND_WAIT(0):
+    case ANDROID_ALARM_SET(0):
+    case ANDROID_ALARM_WAIT:
+    case ANDROID_ALARM_SET_RTC:
+      ARC_STRACE_REPORT("ioctl %d for /dev/alarm is not supported.", request);
+      errno = ENOSYS;
+      return -1;
+    default:
+      errno = EINVAL;
+      return -1;
+  }
+}
+
+int DevAlarm::GetTime(int alarm_type, timespec* out) {
+  if (!out) {
+    errno = EFAULT;
+    return -1;
+  }
+  // See http://developer.android.com/reference/android/app/AlarmManager.html
+  // for more details.
+  switch (alarm_type) {
+    case ANDROID_ALARM_RTC_WAKEUP:
+    case ANDROID_ALARM_RTC:
+      clock_gettime(CLOCK_REALTIME, out);
+      return 0;
+    case ANDROID_ALARM_ELAPSED_REALTIME_WAKEUP:
+    case ANDROID_ALARM_ELAPSED_REALTIME: {
+      // Here, we cannot use other than CLOCK_MONOTONIC since Android calls
+      // clock_gettime(CLOCK_MONOTONIC) for getting uptime.
+      clock_gettime(CLOCK_MONOTONIC, out);
+      return 0;
+    }
+    case ANDROID_ALARM_SYSTEMTIME:
+      clock_gettime(CLOCK_MONOTONIC, out);
+      return 0;
+    default:
+      errno = EINVAL;
+      return -1;
+  }
+}
+
+const char* DevAlarm::GetStreamType() const { return "alarm"; }
+
+}  // namespace posix_translation
diff --git a/src/posix_translation/dev_alarm.h b/src/posix_translation/dev_alarm.h
new file mode 100644
index 0000000..adfe585
--- /dev/null
+++ b/src/posix_translation/dev_alarm.h
@@ -0,0 +1,54 @@
+// Copyright (c) 2015 The Chromium OS Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef POSIX_TRANSLATION_DEV_ALARM_H_
+#define POSIX_TRANSLATION_DEV_ALARM_H_
+
+#include <string>
+
+#include "base/basictypes.h"
+#include "base/compiler_specific.h"
+#include "common/export.h"
+#include "posix_translation/device_file.h"
+
+namespace posix_translation {
+
+// This handler is for emulating /dev/alarm device in Android.
+class ARC_EXPORT DevAlarmHandler : public DeviceHandler {
+ public:
+  DevAlarmHandler();
+  virtual ~DevAlarmHandler();
+
+  virtual scoped_refptr<FileStream> open(
+      int fd, const std::string& pathname, int oflag, mode_t cmode) OVERRIDE;
+  virtual int stat(const std::string& pathname, struct stat* out) OVERRIDE;
+
+ private:
+  timespec boottime_origin_;
+  DISALLOW_COPY_AND_ASSIGN(DevAlarmHandler);
+};
+
+class DevAlarm : public DeviceStream {
+ public:
+  DevAlarm(const std::string& pathname, int oflag,
+           const timespec& boottime_origin);
+
+  virtual int fstat(struct stat* out) OVERRIDE;
+  virtual ssize_t read(void* buf, size_t count) OVERRIDE;
+  virtual ssize_t write(const void* buf, size_t count) OVERRIDE;
+  virtual int ioctl(int request, va_list ap) OVERRIDE;
+  virtual const char* GetStreamType() const OVERRIDE;
+
+ protected:
+  virtual ~DevAlarm();
+
+ private:
+  // Handles ANDROID_ALARM_GET_TIME request.
+  int GetTime(int alarm_type, timespec* out);
+
+  DISALLOW_COPY_AND_ASSIGN(DevAlarm);
+};
+
+}  // namespace posix_translation
+#endif  // POSIX_TRANSLATION_DEV_ALARM_H_
diff --git a/src/posix_translation/dev_alarm_test.cc b/src/posix_translation/dev_alarm_test.cc
new file mode 100644
index 0000000..5630561
--- /dev/null
+++ b/src/posix_translation/dev_alarm_test.cc
@@ -0,0 +1,155 @@
+// Copyright (c) 2015 The Chromium OS Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include <sys/sysmacros.h>
+#include <linux/android_alarm.h>  // Can't sort this, requirs sys/sysmacros.h.
+
+#include "base/compiler_specific.h"
+#include "base/memory/scoped_ptr.h"
+#include "gtest/gtest.h"
+#include "posix_translation/dev_alarm.h"
+#include "posix_translation/test_util/file_system_test_common.h"
+
+// We use random numbers for this test.
+const int kAlarmMajorId = 50;
+const int kAlarmMinorId = 51;
+
+namespace posix_translation {
+
+namespace {
+
+// Helper function for calling ioctl of |stream|.
+int CallIoctl(scoped_refptr<FileStream> stream, int request, ...) {
+  va_list ap;
+  va_start(ap, request);
+  int ret = stream->ioctl(request, ap);
+  va_end(ap);
+  return ret;
+}
+}  // namespace
+
+class DevAlarmTest : public FileSystemTestCommon {
+ protected:
+  DevAlarmTest()
+      : handler_(new DevAlarmHandler) {
+  }
+
+  scoped_ptr<FileSystemHandler> handler_;
+
+ private:
+  virtual void SetUp() OVERRIDE {
+    FileSystemTestCommon::SetUp();
+    DeviceHandler::AddDeviceId("/dev/alarm", kAlarmMajorId, kAlarmMinorId);
+  }
+
+  DISALLOW_COPY_AND_ASSIGN(DevAlarmTest);
+};
+
+TEST_F(DevAlarmTest, TestInit) {
+}
+
+TEST_F(DevAlarmTest, TestMkdir) {
+  EXPECT_EQ(-1, handler_->mkdir("/dev/alarm", 0700));
+  EXPECT_EQ(EEXIST, errno);
+}
+
+TEST_F(DevAlarmTest, TestRename) {
+  EXPECT_EQ(-1, handler_->rename("/dev/alarm", "/dev/foo"));
+  EXPECT_EQ(EACCES, errno);
+  EXPECT_EQ(0, handler_->rename("/dev/alarm", "/dev/alarm"));
+}
+
+TEST_F(DevAlarmTest, TestStat) {
+  struct stat st = {};
+  EXPECT_EQ(0, handler_->stat("/dev/alarm", &st));
+  EXPECT_NE(0U, st.st_ino);
+  EXPECT_EQ(S_IFCHR | 0664U, st.st_mode);
+}
+
+TEST_F(DevAlarmTest, TestStatfs) {
+  struct statfs st = {};
+  EXPECT_EQ(0, handler_->statfs("/dev/alarm", &st));
+  EXPECT_NE(0U, st.f_type);  // check something is filled.
+}
+
+TEST_F(DevAlarmTest, TestTruncate) {
+  EXPECT_EQ(-1, handler_->truncate("/dev/alarm", 0));
+  EXPECT_EQ(EINVAL, errno);
+}
+
+TEST_F(DevAlarmTest, TestUnlink) {
+  EXPECT_EQ(-1, handler_->unlink("/dev/alarm"));
+  EXPECT_EQ(EACCES, errno);
+}
+
+TEST_F(DevAlarmTest, TestUtimes) {
+  struct timeval times[2] = {};
+  EXPECT_EQ(-1, handler_->utimes("/dev/alarm", times));
+  EXPECT_EQ(EPERM, errno);
+}
+
+TEST_F(DevAlarmTest, TestOpenClose) {
+  scoped_refptr<FileStream> stream =
+      handler_->open(512, "/dev/alarm", O_RDONLY, 0);
+  ASSERT_TRUE(stream != NULL);
+}
+
+TEST_F(DevAlarmTest, TestFstat) {
+  scoped_refptr<FileStream> stream =
+      handler_->open(512, "/dev/alarm", O_RDONLY, 0);
+  ASSERT_TRUE(stream != NULL);
+  struct stat st = {};
+  stream->fstat(&st);
+  EXPECT_NE(0U, st.st_ino);
+  EXPECT_EQ(S_IFCHR | 0664U, st.st_mode);
+  EXPECT_EQ(makedev(kAlarmMajorId, kAlarmMinorId), st.st_rdev);
+}
+
+TEST_F(DevAlarmTest, TestRead) {
+  scoped_refptr<FileStream> stream =
+      handler_->open(512, "/dev/alarm", O_RDONLY, 0);
+  ASSERT_TRUE(stream != NULL);
+  char buf[16] = {};
+  errno = 0;
+  EXPECT_EQ(-1, stream->read(buf, sizeof(buf)));
+  EXPECT_EQ(EINVAL, errno);
+}
+
+TEST_F(DevAlarmTest, TestWrite) {
+  scoped_refptr<FileStream> stream =
+      handler_->open(512, "/dev/alarm", O_RDONLY, 0);
+  ASSERT_TRUE(stream != NULL);
+  errno = 0;
+  EXPECT_EQ(-1, stream->write("abc", 3));
+  EXPECT_EQ(EBADF, errno);
+}
+
+TEST_F(DevAlarmTest, GET_TIME) {
+  const int requests[] = {
+    ANDROID_ALARM_GET_TIME(ANDROID_ALARM_RTC_WAKEUP),
+    ANDROID_ALARM_GET_TIME(ANDROID_ALARM_RTC),
+    ANDROID_ALARM_GET_TIME(ANDROID_ALARM_ELAPSED_REALTIME_WAKEUP),
+    ANDROID_ALARM_GET_TIME(ANDROID_ALARM_ELAPSED_REALTIME),
+    ANDROID_ALARM_GET_TIME(ANDROID_ALARM_SYSTEMTIME),
+  };
+
+  scoped_refptr<FileStream> stream =
+      handler_->open(512, "/dev/alarm", O_RDONLY, 0);
+  ASSERT_TRUE(stream != NULL);
+  for (int i = 0; i < arraysize(requests); ++i) {
+    timespec ts = {};
+    errno = 0;
+    EXPECT_EQ(0, CallIoctl(stream, requests[i], &ts));
+    EXPECT_EQ(0, errno);
+    EXPECT_FALSE(ts.tv_sec == 0 && ts.tv_nsec == 0);
+    EXPECT_LE(0, ts.tv_sec);
+    EXPECT_LE(0, ts.tv_nsec);
+
+    errno = 0;
+    ASSERT_EQ(-1,  CallIoctl(stream, requests[i], NULL));
+    EXPECT_EQ(EFAULT, errno);
+  }
+}
+
+}  // namespace posix_translation
diff --git a/src/posix_translation/file_wrap.cc b/src/posix_translation/file_wrap.cc
index dee49dc..68c6320 100644
--- a/src/posix_translation/file_wrap.cc
+++ b/src/posix_translation/file_wrap.cc
@@ -227,10 +227,8 @@
                    arc::GetAccessModeStr(mode).c_str());
   int result = VirtualFileSystem::GetVirtualFileSystem()->access(
       pathname, mode);
-  if (result == -1 && errno != ENOENT) {
-    DANGERF("path=%s mode=%d: %s",
-            SAFE_CSTR(pathname), mode, safe_strerror(errno).c_str());
-  }
+  if (result == -1 && errno != ENOENT)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -388,9 +386,8 @@
   struct stat st;
   int result = VirtualFileSystem::GetVirtualFileSystem()->lstat(path, &st);
   if (result == -1) {
-    if (errno != ENOENT) {
-      DANGERF("path=%s: %s", SAFE_CSTR(path), safe_strerror(errno).c_str());
-    }
+    if (errno != ENOENT)
+      ARC_STRACE_ALWAYS_WARN_FAILURE();
   } else {
     StatToNaClAbiStat(&st, buf);
     ARC_STRACE_REPORT("buf=%s", arc::GetNaClAbiStatStr(buf).c_str());
@@ -401,10 +398,8 @@
 IRT_WRAPPER(mkdir, const char* pathname, mode_t mode) {
   ARC_STRACE_ENTER("mkdir", "\"%s\", 0%o", SAFE_CSTR(pathname), mode);
   int result = VirtualFileSystem::GetVirtualFileSystem()->mkdir(pathname, mode);
-  if (result == -1 && errno != EEXIST) {
-    DANGERF("path=%s mode=%d: %s",
-            SAFE_CSTR(pathname), mode, safe_strerror(errno).c_str());
-  }
+  if (result == -1 && errno != EEXIST)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN_IRT_WRAPPER(result == 0 ? 0 : errno);
 }
 
@@ -438,10 +433,8 @@
   } else {
     fd = VirtualFileSystem::GetVirtualFileSystem()->open(pathname, flags, mode);
   }
-  if (fd == -1 && errno != ENOENT) {
-    DANGERF("pathname=%s flags=%d: %s",
-            SAFE_CSTR(pathname), flags, safe_strerror(errno).c_str());
-  }
+  if (fd == -1 && errno != ENOENT)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_REGISTER_FD(fd, SAFE_CSTR(pathname));
   ARC_STRACE_RETURN(fd);
 }
@@ -473,10 +466,8 @@
                    SAFE_CSTR(path), buf, bufsiz);
   ssize_t result = VirtualFileSystem::GetVirtualFileSystem()->readlink(
       path, buf, bufsiz);
-  if (result == -1) {
-    DANGERF("path=%s bufsiz=%zu: %s",
-            SAFE_CSTR(path), bufsiz, safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -484,10 +475,8 @@
   ARC_STRACE_ENTER("realpath", "\"%s\", %p", SAFE_CSTR(path), resolved_path);
   char* result = VirtualFileSystem::GetVirtualFileSystem()->realpath(
       path, resolved_path);
-  if (!result) {
-    DANGERF("path=%s resolved_path=%p: %s",
-            SAFE_CSTR(path), resolved_path, safe_strerror(errno).c_str());
-  }
+  if (!result)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN_PTR(result, !result);
 }
 
@@ -495,7 +484,7 @@
   ARC_STRACE_ENTER("remove", "\"%s\"", SAFE_CSTR(pathname));
   int result = VirtualFileSystem::GetVirtualFileSystem()->remove(pathname);
   if (result == -1 && errno != ENOENT)
-    DANGERF("path=%s: %s", SAFE_CSTR(pathname), safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -504,11 +493,8 @@
                    SAFE_CSTR(oldpath), SAFE_CSTR(newpath));
   int result = VirtualFileSystem::GetVirtualFileSystem()->rename(
       oldpath, newpath);
-  if (result == -1) {
-    DANGERF("oldpath=%s newpath=%s: %s",
-            SAFE_CSTR(oldpath), SAFE_CSTR(newpath),
-            safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -535,7 +521,7 @@
   int result = VirtualFileSystem::GetVirtualFileSystem()->statfs(
       pathname, stat);
   if (result == -1 && errno != ENOENT)
-    DANGERF("path=%s: %s", SAFE_CSTR(pathname), safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_REPORT(
       "stat={type=%lld bsize=%lld blocks=%llu bfree=%llu bavail=%llu "
       "files=%llu ffree=%llu fsid=%d,%d namelen=%lld frsize=%lld "
@@ -592,11 +578,8 @@
                    SAFE_CSTR(pathname), static_cast<int64_t>(length));
   int result = VirtualFileSystem::GetVirtualFileSystem()->truncate(
       pathname, length);
-  if (result == -1) {
-    DANGERF("path=%s length=%lld: %s",
-            SAFE_CSTR(pathname), static_cast<int64_t>(length),
-            safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -612,7 +595,7 @@
   ARC_STRACE_ENTER("unlink", "\"%s\"", SAFE_CSTR(pathname));
   int result = VirtualFileSystem::GetVirtualFileSystem()->unlink(pathname);
   if (result == -1 && errno != ENOENT)
-    DANGERF("path=%s: %s", SAFE_CSTR(pathname), safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -620,10 +603,8 @@
   ARC_STRACE_ENTER("utimes", "\"%s\", %p", SAFE_CSTR(filename), times);
   int result = VirtualFileSystem::GetVirtualFileSystem()->utimes(
       filename, times);
-  if (result == -1 && errno != ENOENT) {
-    DANGERF("path=%s: %s",
-            SAFE_CSTR(filename), safe_strerror(errno).c_str());
-  }
+  if (result == -1 && errno != ENOENT)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -632,9 +613,8 @@
   struct stat st;
   int result = VirtualFileSystem::GetVirtualFileSystem()->stat(pathname, &st);
   if (result == -1) {
-    if (errno != ENOENT) {
-      DANGERF("path=%s: %s", SAFE_CSTR(pathname), safe_strerror(errno).c_str());
-    }
+    if (errno != ENOENT)
+      ARC_STRACE_ALWAYS_WARN_FAILURE();
   } else {
     StatToNaClAbiStat(&st, buf);
     ARC_STRACE_REPORT("buf=%s", arc::GetNaClAbiStatStr(buf).c_str());
@@ -659,7 +639,7 @@
     // hits the case.
     if (errno == EBADF)
       DANGERF("Close of bad file descriptor may indicate double close");
-    DANGERF("fd=%d: %s", fd, safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   }
   ARC_STRACE_RETURN(result);
 }
@@ -676,7 +656,7 @@
   ARC_STRACE_ENTER_FD("dup", "%d", oldfd);
   int fd = VirtualFileSystem::GetVirtualFileSystem()->dup(oldfd);
   if (fd == -1)
-    DANGERF("oldfd=%d: %s", oldfd, safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   *newfd = fd;
   ARC_STRACE_RETURN_IRT_WRAPPER(fd >= 0 ? 0 : errno);
 }
@@ -684,10 +664,8 @@
 IRT_WRAPPER(dup2, int oldfd, int newfd) {
   ARC_STRACE_ENTER_FD("dup2", "%d, %d", oldfd, newfd);
   int fd = VirtualFileSystem::GetVirtualFileSystem()->dup2(oldfd, newfd);
-  if (fd == -1) {
-    DANGERF("oldfd=%d newfd=%d: %s",
-            oldfd, newfd, safe_strerror(errno).c_str());
-  }
+  if (fd == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN_IRT_WRAPPER(fd >= 0 ? 0 : errno);
 }
 
@@ -704,7 +682,7 @@
   va_end(ap);
 
   if (result == -1)
-    DANGERF("fd=%d cmd=%d: %s", fd, cmd, safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -726,7 +704,7 @@
   int result = VirtualFileSystem::GetVirtualFileSystem()->fstat(fd, &st);
   if (result) {
     result = errno;
-    DANGERF("fd=%d: %s", fd, safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   } else {
     StatToNaClAbiStat(&st, buf);
     ARC_STRACE_REPORT("buf=%s", arc::GetNaClAbiStatStr(buf).c_str());
@@ -739,10 +717,8 @@
   ARC_STRACE_ENTER_FD("ftruncate", "%d, %lld",
                       fd, static_cast<int64_t>(length));
   int result = VirtualFileSystem::GetVirtualFileSystem()->ftruncate(fd, length);
-  if (result == -1) {
-    DANGERF("fd=%d length=%lld: %s", fd, static_cast<int64_t>(length),
-            safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -764,7 +740,7 @@
       fd, request, ap);
   va_end(ap);
   if (result == -1)
-    DANGERF("fd=%d request=%d: %s", fd, request, safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -775,11 +751,8 @@
                       arc::GetLseekWhenceStr(whence).c_str());
   OffsetType result = VirtualFileSystem::GetVirtualFileSystem()->lseek(
       fd, offset, whence);
-  if (result == -1) {
-    DANGERF("fd=%d offset=%lld whence=%d: %s",
-            fd, static_cast<int64_t>(offset), whence,
-            safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -794,8 +767,7 @@
   int result = VirtualFileSystem::GetVirtualFileSystem()->madvise(
       addr, length, advice);
   if (result != 0) {
-    DANGERF("errno=%d addr=%p length=%zu advice=%d: %s",
-            errno, addr, length, advice, safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
     if (errno == ENOSYS && advice != MADV_REMOVE) {
       // TODO(crbug.com/362862): Stop special-casing ENOSYS once the bug is
       // fixed.
@@ -859,11 +831,8 @@
         MapCurrentStackFrame(result, length);
 #endif
 
-  if (result == MAP_FAILED) {
-    DANGERF("addr=%p length=%zu prot=%d flags=%d fd=%d offset=%lld: %s",
-            addr, length, prot, flags, fd, static_cast<int64_t>(offset),
-            safe_strerror(errno).c_str());
-  }
+  if (result == MAP_FAILED)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN_PTR(result, result == MAP_FAILED);
 }
 
@@ -953,8 +922,7 @@
   int result = VirtualFileSystem::GetVirtualFileSystem()->poll(
       fds, nfds, timeout);
   if (result == -1) {
-    DANGERF("fds=%p nfds=%u timeout=%d[ms]: %s",
-            fds, nfds, timeout, safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   } else if (arc::StraceEnabled()) {
     for (int i = 0; i < result; ++i) {
       if (!fds[i].revents)
@@ -973,11 +941,8 @@
                       fd, buf, count, static_cast<int64_t>(offset));
   ssize_t result = VirtualFileSystem::GetVirtualFileSystem()->pread(
       fd, buf, count, offset);
-  if (result == -1) {
-    DANGERF("fd=%d buf=%p count=%zu offset=%lld: %s",
-            fd, buf, count, static_cast<int64_t>(offset),
-            safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   if (result >= 0)
     ARC_STRACE_REPORT("buf=%s", arc::GetRWBufStr(buf, result).c_str());
   ARC_STRACE_RETURN(result);
@@ -998,11 +963,8 @@
                       fd, buf, count, static_cast<int64_t>(offset));
   ssize_t result = VirtualFileSystem::GetVirtualFileSystem()->pwrite(
       fd, buf, count, offset);
-  if (result == -1) {
-    DANGERF("fd=%d buf=%p count=%zu offset=%lld: %s",
-            fd, buf, count, static_cast<int64_t>(offset),
-            safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   if (errno != EFAULT)
     ARC_STRACE_REPORT("buf=%s", arc::GetRWBufStr(buf, count).c_str());
   ARC_STRACE_RETURN(result);
@@ -1021,10 +983,8 @@
   ARC_STRACE_ENTER_FD("read", "%d, %p, %zu", fd, buf, count);
   ssize_t result = VirtualFileSystem::GetVirtualFileSystem()->read(
       fd, buf, count);
-  if (result == -1 && errno != EAGAIN) {
-    DANGERF("fd=%d buf=%p count=%zu: %s",
-            fd, buf, count, safe_strerror(errno).c_str());
-  }
+  if (result == -1 && errno != EAGAIN)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   if (result >= 0)
     ARC_STRACE_REPORT("buf=%s", arc::GetRWBufStr(buf, result).c_str());
   ARC_STRACE_RETURN(result);
@@ -1035,10 +995,8 @@
   ARC_STRACE_ENTER_FD("readv", "%d, %p, %d", fd, iov, iovcnt);
   ssize_t result = VirtualFileSystem::GetVirtualFileSystem()->readv(
       fd, iov, iovcnt);
-  if (result == -1) {
-    DANGERF("fd=%d iov=%p iovcnt=%d: %s",
-            fd, iov, iovcnt, safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -1046,7 +1004,7 @@
   ARC_STRACE_ENTER("rmdir", "\"%s\"", SAFE_CSTR(pathname));
   int result = VirtualFileSystem::GetVirtualFileSystem()->rmdir(pathname);
   if (result == -1 && errno != ENOENT)
-    DANGERF("path=%s: %s", SAFE_CSTR(pathname), safe_strerror(errno).c_str());
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -1054,10 +1012,8 @@
   ARC_STRACE_ENTER("utime", "\"%s\", %p", SAFE_CSTR(filename), times);
   int result = VirtualFileSystem::GetVirtualFileSystem()->utime(
       filename, times);
-  if (result == -1 && errno != ENOENT) {
-    DANGERF("path=%s: %s",
-            SAFE_CSTR(filename), safe_strerror(errno).c_str());
-  }
+  if (result == -1 && errno != ENOENT)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
@@ -1080,10 +1036,8 @@
     if (errno != EFAULT)
       ARC_STRACE_REPORT("buf=%s", arc::GetRWBufStr(buf, count).c_str());
     g_wrap_write_nest_count.Set(wrap_write_nest_count);
-    if (result == -1 && errno != EAGAIN) {
-      DANGERF("fd=%d buf=%p count=%zu: %s",
-              fd, buf, count, safe_strerror(errno).c_str());
-    }
+    if (result == -1 && errno != EAGAIN)
+      ARC_STRACE_ALWAYS_WARN_FAILURE();
     ARC_STRACE_RETURN(result);
   }
 }
@@ -1094,10 +1048,8 @@
   ARC_STRACE_ENTER_FD("writev", "%d, %p, %d", fd, iov, iovcnt);
   ssize_t result = VirtualFileSystem::GetVirtualFileSystem()->writev(
       fd, iov, iovcnt);
-  if (result == -1) {
-    DANGERF("fd=%d iov=%p iovcnt=%d: %s",
-            fd, iov, iovcnt, safe_strerror(errno).c_str());
-  }
+  if (result == -1)
+    ARC_STRACE_ALWAYS_WARN_FAILURE();
   ARC_STRACE_RETURN(result);
 }
 
diff --git a/src/posix_translation/file_wrap_stub.cc b/src/posix_translation/file_wrap_stub.cc
index 5c76f7f..e1209a7 100644
--- a/src/posix_translation/file_wrap_stub.cc
+++ b/src/posix_translation/file_wrap_stub.cc
@@ -31,7 +31,7 @@
 extern "C" ARC_EXPORT int __wrap_fchdir(int fd) {
   ARC_STRACE_ENTER_FD("fchdir", "%d", fd);
   // TODO(crbug.com/178515): Implement this.
-  DANGERF("fchdir: fd=%d", fd);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
@@ -45,7 +45,8 @@
   //   at the same time.
   ARC_STRACE_ENTER_FD("flock", "%d, %s",
                       fd, arc::GetFlockOperationStr(operation).c_str());
-  ARC_STRACE_REPORT("not implemented, always succeeds");
+  // Do not call ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED() which is too noisy.
+  ARC_STRACE_REPORT("not implemented yet");
   ARC_STRACE_RETURN(0);
 }
 
@@ -53,8 +54,7 @@
     const char* path, uid_t owner, gid_t group) {
   ARC_STRACE_ENTER("lchown", "\"%s\", %u, %u",
                    SAFE_CSTR(path), owner, group);
-  DANGERF("lchown: path=%s owner=%u group=%u",
-          SAFE_CSTR(path), owner, group);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
@@ -62,7 +62,7 @@
 
 extern "C" ARC_EXPORT int __wrap_mlock(const void* addr, size_t len) {
   ARC_STRACE_ENTER("mlock", "%p, %zu", addr, len);
-  DANGERF("mlock: addr=%p len=%zu", addr, len);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
 }
@@ -70,7 +70,7 @@
 extern "C" ARC_EXPORT int __wrap_mlockall(int flags) {
   // TODO(crbug.com/241955): Stringify |flags|?
   ARC_STRACE_ENTER("mlockall", "%d", flags);
-  DANGERF("mlockall: flags=%d", flags);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
@@ -84,10 +84,7 @@
   ARC_STRACE_ENTER("mount", "\"%s\", \"%s\", \"%s\", %lu, %p",
                    SAFE_CSTR(source), SAFE_CSTR(target),
                    SAFE_CSTR(filesystemtype), mountflags, data);
-  DANGERF("mount: source=%s target=%s "
-          "filesystemtype=%s mountflags=%lu data=%p",
-          SAFE_CSTR(source), SAFE_CSTR(target),
-          SAFE_CSTR(filesystemtype), mountflags, data);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
@@ -98,8 +95,7 @@
   ARC_STRACE_ENTER("mremap", "%p, %zu, %zu, %s",
                    old_address, old_size, new_size,
                    arc::GetMremapFlagStr(flags).c_str());
-  DANGERF("mremap: old_address=%p old_size=%zu new_size=%zu flags=%d",
-          old_address, old_size, new_size, flags);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN_PTR(MAP_FAILED, true);
@@ -107,14 +103,14 @@
 
 extern "C" ARC_EXPORT int __wrap_munlock(const void* addr, size_t len) {
   ARC_STRACE_ENTER("munlock", "%p, %zu", addr, len);
-  DANGERF("munlock: addr=%p len=%zu", addr, len);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
 }
 
 extern "C" ARC_EXPORT int __wrap_munlockall() {
   ARC_STRACE_ENTER("munlockall", "%s", "");
-  DANGERF("munlockall");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
@@ -122,7 +118,7 @@
 
 extern "C" ARC_EXPORT int __wrap_umount(const char* target) {
   ARC_STRACE_ENTER("umount", "\"%s\"", SAFE_CSTR(target));
-  DANGERF("umount: target=%s", SAFE_CSTR(target));
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
@@ -131,7 +127,7 @@
 extern "C" ARC_EXPORT int __wrap_umount2(const char* target, int flags) {
   // TODO(crbug.com/241955): Stringify |flags|?
   ARC_STRACE_ENTER("umount2", "\"%s\", %d", SAFE_CSTR(target), flags);
-  DANGERF("umount2: target=%s flags=%d", SAFE_CSTR(target), flags);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ALOG_ASSERT(0);
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
@@ -144,13 +140,13 @@
 extern "C" ARC_EXPORT int __wrap_chmod(const char* path, mode_t mode) {
   // TODO(crbug.com/242355): Implement this.
   ARC_STRACE_ENTER("chmod", "\"%s\", 0%o", SAFE_CSTR(path), mode);
-  ARC_STRACE_REPORT("not implemented yet");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ARC_STRACE_RETURN(0);  // Returning -1 breaks SQLite.
 }
 
 extern "C" ARC_EXPORT int __wrap_eventfd(unsigned int initval, int flags) {
   ARC_STRACE_ENTER("eventfd", "%u, %d", initval, flags);
-  ARC_STRACE_REPORT("not implemented yet");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
 }
@@ -158,21 +154,21 @@
 extern "C" ARC_EXPORT int __wrap_fchmod(int fd, mode_t mode) {
   // TODO(crbug.com/242355): Implement this.
   ARC_STRACE_ENTER_FD("fchmod", "%d, 0%o", fd, mode);
-  ARC_STRACE_REPORT("not implemented yet");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ARC_STRACE_RETURN(0);
 }
 
 extern "C" ARC_EXPORT int __wrap_fchown(int fd, uid_t owner, gid_t group) {
   // TODO(crbug.com/242355): Implement this.
   ARC_STRACE_ENTER_FD("fchown", "%d, %u, %u", fd, owner, group);
-  ARC_STRACE_REPORT("not implemented yet");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   ARC_STRACE_RETURN(0);
 }
 
 extern "C" ARC_EXPORT int __wrap_futimens(
     int fd, const struct timespec times[2]) {
   ARC_STRACE_ENTER_FD("futimens", "%d, %p", fd, times);
-  ARC_STRACE_REPORT("not implemented yet");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
 }
@@ -182,8 +178,7 @@
   ARC_STRACE_ENTER_FD("inotify_add_watch", "%d, \"%s\", %u",
                       fd, SAFE_CSTR(pathname), mask);
   // TODO(crbug.com/236903): Implement this.
-  DANGERF("inotify_add_watch: fd=%d pathname=%s mask=%u",
-          fd, SAFE_CSTR(pathname), mask);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
 }
@@ -191,7 +186,7 @@
 extern "C" ARC_EXPORT int __wrap_inotify_init() {
   ARC_STRACE_ENTER("inotify_init", "%s", "");
   // TODO(crbug.com/236903): Implement this.
-  DANGERF("inotify_init");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
 }
@@ -199,14 +194,14 @@
 extern "C" ARC_EXPORT int __wrap_inotify_rm_watch(int fd, int wd) {
   ARC_STRACE_ENTER_FD("inotify_rm_watch", "%d, %d", fd, wd);
   // TODO(crbug.com/236903): Implement this.
-  DANGERF("inotify_rm_watch: fd=%d wd=%d", fd, wd);
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   errno = ENOSYS;
   ARC_STRACE_RETURN(-1);
 }
 
 extern "C" ARC_EXPORT int __wrap_msync(void* addr, size_t length, int flags) {
   ARC_STRACE_ENTER("msync", "%p, %zu, %d", addr, length, flags);
-  ARC_STRACE_REPORT("not implemented yet");
+  ARC_STRACE_ALWAYS_WARN_NOTIMPLEMENTED();
   // msync is called by dexopt and some apps (crbug.com/363545). Although dexopt
   // does not check the return value, the apps may. Return 0 without doing
   // anything so that such apps will not fail. This should be safe as long as