Merge "Revert "Add debug logging for memtag level""
diff --git a/README.md b/README.md
index 8d8e583..5107f42 100644
--- a/README.md
+++ b/README.md
@@ -48,7 +48,9 @@
 #### tests/ --- unit tests
 
 The `tests/` directory contains unit tests. Roughly arranged as one file per
-publicly-exported header file.
+publicly-exported header file. `tests/headers/` contains compile-only tests
+that just check that things are _in_ the headers, whereas the "real" tests
+check actual _behavior_.
 
 #### benchmarks/ --- benchmarks
 
diff --git a/android-changes-for-ndk-developers.md b/android-changes-for-ndk-developers.md
index c5a6ac3..8ffd96f 100644
--- a/android-changes-for-ndk-developers.md
+++ b/android-changes-for-ndk-developers.md
@@ -107,7 +107,7 @@
 ## Correct soname/path handling (Available in API level >= 23)
 
 The dynamic linker now understands the difference
-between a library’s soname and its path  (public bug
+between a library’s soname and its path (public bug
 https://code.google.com/p/android/issues/detail?id=6670). API level 23
 is the first release where search by soname is implemented. Earlier
 releases would assume that the basename of the library was the soname,
@@ -326,12 +326,12 @@
 
 ## Missing SONAME (Enforced for API level >= 23)
 
-Each ELF shared object (“native library”) must have a SONAME (Shared
-Object Name) attribute. The NDK toolchain adds this attribute by default,
-so its absence indicates either a misconfigured alternative toolchain
-or a misconfiguration in your build system. A missing SONAME may lead
-to runtime issues such as the wrong library being loaded: the filename
-is used instead when this attribute is missing.
+Each ELF shared object (“native library”) must have a SONAME
+(Shared Object Name) attribute. The NDK build systems add this
+attribute by default, so its absence (or an incorrect soname) indicates
+a misconfiguration in your build system. A missing SONAME may lead to
+runtime issues such as the wrong library being loaded: the filename is
+used instead when this attribute is missing.
 
 ```
 $ readelf --dynamic libWithSoName.so | grep SONAME
@@ -346,7 +346,7 @@
 *Resolution*: the current NDK generates the correct SONAME by
 default. Ensure you're using the current NDK and that you haven't
 configured your build system to generate incorrect SONAME entries (using
-the -soname linker option).
+the `-soname` linker option).
 
 ## `__register_atfork` (Available in API level >= 23)
 
diff --git a/apex/Android.bp b/apex/Android.bp
index 90a14b2..6201ad1 100644
--- a/apex/Android.bp
+++ b/apex/Android.bp
@@ -41,6 +41,11 @@
         "libc_malloc_debug",
         "libc_malloc_hooks",
     ],
+    arch: {
+        arm64: {
+            native_shared_libs: ["libc_hwasan", "libclang_rt.hwasan"],
+        },
+    },
     binaries: [
         "linkerconfig",
     ],
diff --git a/benchmarks/malloc_benchmark.cpp b/benchmarks/malloc_benchmark.cpp
index 18ba523..e733cd0 100644
--- a/benchmarks/malloc_benchmark.cpp
+++ b/benchmarks/malloc_benchmark.cpp
@@ -36,11 +36,11 @@
 
 #if defined(__BIONIC__)
 
-static void BM_mallopt_purge(benchmark::State& state) {
+static void RunMalloptPurge(benchmark::State& state, int purge_value) {
   static size_t sizes[] = {8, 16, 32, 64, 128, 1024, 4096, 16384, 65536, 131072, 1048576};
   static int pagesize = getpagesize();
   mallopt(M_DECAY_TIME, 1);
-  mallopt(M_PURGE, 0);
+  mallopt(M_PURGE_ALL, 0);
   for (auto _ : state) {
     state.PauseTiming();
     std::vector<void*> ptrs;
@@ -63,10 +63,19 @@
     ptrs.clear();
     state.ResumeTiming();
 
-    mallopt(M_PURGE, 0);
+    mallopt(purge_value, 0);
   }
   mallopt(M_DECAY_TIME, 0);
 }
+
+static void BM_mallopt_purge(benchmark::State& state) {
+  RunMalloptPurge(state, M_PURGE);
+}
 BIONIC_BENCHMARK(BM_mallopt_purge);
 
+static void BM_mallopt_purge_all(benchmark::State& state) {
+  RunMalloptPurge(state, M_PURGE_ALL);
+}
+BIONIC_BENCHMARK(BM_mallopt_purge_all);
+
 #endif
diff --git a/benchmarks/malloc_map_benchmark.cpp b/benchmarks/malloc_map_benchmark.cpp
index ba4d62c..5757325 100644
--- a/benchmarks/malloc_map_benchmark.cpp
+++ b/benchmarks/malloc_map_benchmark.cpp
@@ -69,7 +69,7 @@
   for (auto _ : state) {
 #if defined(__BIONIC__)
     state.PauseTiming();
-    mallopt(M_PURGE, 0);
+    mallopt(M_PURGE_ALL, 0);
     uint64_t rss_bytes_before = 0;
     Gather(&rss_bytes_before);
     state.ResumeTiming();
@@ -80,7 +80,7 @@
     }
 #if defined(__BIONIC__)
     state.PauseTiming();
-    mallopt(M_PURGE, 0);
+    mallopt(M_PURGE_ALL, 0);
     Gather(&rss_bytes);
     // Try and record only the memory used in the map.
     rss_bytes -= rss_bytes_before;
diff --git a/benchmarks/malloc_rss_benchmark.cpp b/benchmarks/malloc_rss_benchmark.cpp
index 58f61d9..4b34e72 100644
--- a/benchmarks/malloc_rss_benchmark.cpp
+++ b/benchmarks/malloc_rss_benchmark.cpp
@@ -112,7 +112,7 @@
 
   // Do an explicit purge to ensure we will be more likely to get the actual
   // in-use memory.
-  mallopt(M_PURGE, 0);
+  mallopt(M_PURGE_ALL, 0);
 
   android::meminfo::ProcMemInfo proc_mem(getpid());
   const std::vector<android::meminfo::Vma>& maps = proc_mem.MapsWithoutUsageStats();
diff --git a/docs/defines.md b/docs/defines.md
index 4775cd2..65a715e 100644
--- a/docs/defines.md
+++ b/docs/defines.md
@@ -54,7 +54,7 @@
 work around issues with some of them, use these macros to detect the versinon of
 the NDK you're being built with. Usually only `__NDK_MAJOR__` will be necessary.
 
-## `__arm__`, `__aarch64__`, `__i386__`, `__x86_64__`
+## `__arm__`, `__aarch64__`, `__i386__`, `__x86_64__`, `__riscv`
 
 If your code is specific to a particular processor architecture, use these
 macros to conditionally compile. Note that the ABI usually called `arm64` uses
diff --git a/docs/elf-tls.md b/docs/elf-tls.md
index 4a62793..d408b3f 100644
--- a/docs/elf-tls.md
+++ b/docs/elf-tls.md
@@ -101,9 +101,9 @@
 `R_TLS_DTPOFF` is a dynamic relocation to the offset of `tls_var` within its module's `PT_TLS`
 segment.
 
-`__tls_get_addr` looks up `TlsIndex::module`'s entry in the DTV and adds `TlsIndex::offset` to the
-module's TLS block. Before it can do this, it ensures that the module's TLS block is allocated. A
-simple approach is to allocate memory lazily:
+`__tls_get_addr` looks up `TlsIndex::module_id`'s entry in the DTV and adds `TlsIndex::offset` to
+the module's TLS block. Before it can do this, it ensures that the module's TLS block is allocated.
+A simple approach is to allocate memory lazily:
 
 1. If the current thread's DTV generation count is less than the current global TLS generation, then
    `__tls_get_addr` may reallocate the DTV or free blocks for unloaded modules.
diff --git a/docs/status.md b/docs/status.md
index 5d2603a..411b140 100644
--- a/docs/status.md
+++ b/docs/status.md
@@ -55,15 +55,23 @@
 
 Current libc symbols: https://android.googlesource.com/platform/bionic/+/master/libc/libc.map.txt
 
+New libc functions in V (API level 35):
+  * `timespec_getres` (C23 addition).
+
 New libc functions in U (API level 34):
   * `close_range` and `copy_file_range` (Linux-specific GNU extensions).
   * `memset_explicit` in <string.h> (C23 addition).
   * `__freadahead` in <stdio_ext.h> (in musl but not glibc).
+  * `posix_spawn_file_actions_addchdir_np` and
+    `posix_spawn_file_actions_addfchdir_np` in <spawn.h> (in musl/glibc
+    and macOS, but not iOS).
 
 New libc behavior in U (API level 34):
   * Support for `%b` and `%B` in the printf/wprintf family, `%b` in the
     scanf/wscanf family, and `0b` prefixes with base 0 in the strtol/wcstol
     family.
+  * Support for `wN` length modifiers in the printf/wprintf family.
+  * tmpfile() now respects $TMPDIR.
 
 New libc functions in T (API level 33):
   * `backtrace`, `backtrace_symbols`, `backtrace_symbols_fd` (`<execinfo.h>`).
diff --git a/libc/Android.bp b/libc/Android.bp
index c101f45..ecabb06 100644
--- a/libc/Android.bp
+++ b/libc/Android.bp
@@ -827,6 +827,7 @@
         riscv64: {
             srcs: [
                "arch-riscv64/string/__memset_chk.S",
+               "arch-riscv64/string/__memcpy_chk.S",
             ],
         },
     },
@@ -1204,8 +1205,8 @@
         "bionic/termios.cpp",
         "bionic/thread_private.cpp",
         "bionic/threads.cpp",
+        "bionic/time.cpp",
         "bionic/time_l.cpp",
-        "bionic/timespec_get.cpp",
         "bionic/tmpfile.cpp",
         "bionic/umount.cpp",
         "bionic/unlink.cpp",
@@ -1317,7 +1318,7 @@
 // ========================================================
 
 genrule {
-    name: "syscalls-arm.S",
+    name: "syscalls-arm",
     out: ["syscalls-arm.S"],
     srcs: ["SYSCALLS.TXT"],
     tools: ["gensyscalls"],
@@ -1325,7 +1326,7 @@
 }
 
 genrule {
-    name: "syscalls-arm64.S",
+    name: "syscalls-arm64",
     out: ["syscalls-arm64.S"],
     srcs: ["SYSCALLS.TXT"],
     tools: ["gensyscalls"],
@@ -1333,7 +1334,7 @@
 }
 
 genrule {
-    name: "syscalls-riscv64.S",
+    name: "syscalls-riscv64",
     out: ["syscalls-riscv64.S"],
     srcs: ["SYSCALLS.TXT"],
     tools: ["gensyscalls"],
@@ -1341,7 +1342,7 @@
 }
 
 genrule {
-    name: "syscalls-x86.S",
+    name: "syscalls-x86",
     out: ["syscalls-x86.S"],
     srcs: ["SYSCALLS.TXT"],
     tools: ["gensyscalls"],
@@ -1349,7 +1350,7 @@
 }
 
 genrule {
-    name: "syscalls-x86_64.S",
+    name: "syscalls-x86_64",
     out: ["syscalls-x86_64.S"],
     srcs: ["SYSCALLS.TXT"],
     tools: ["gensyscalls"],
@@ -1361,19 +1362,19 @@
     srcs: ["bionic/__set_errno.cpp"],
     arch: {
         arm: {
-            srcs: [":syscalls-arm.S"],
+            srcs: [":syscalls-arm"],
         },
         arm64: {
-            srcs: [":syscalls-arm64.S"],
+            srcs: [":syscalls-arm64"],
         },
         riscv64: {
-            srcs: [":syscalls-riscv64.S"],
+            srcs: [":syscalls-riscv64"],
         },
         x86: {
-            srcs: [":syscalls-x86.S"],
+            srcs: [":syscalls-x86"],
         },
         x86_64: {
-            srcs: [":syscalls-x86_64.S"],
+            srcs: [":syscalls-x86_64"],
         },
     },
     name: "libc_syscalls",
@@ -1673,13 +1674,12 @@
 // ========================================================
 // libc.a + libc.so
 // ========================================================
-cc_library {
+cc_defaults {
     defaults: [
         "libc_defaults",
         "libc_native_allocator_defaults",
     ],
-    name: "libc",
-    static_ndk_lib: true,
+    name: "libc_library_defaults",
     product_variables: {
         platform_sdk_version: {
             asflags: ["-DPLATFORM_SDK_VERSION=%d"],
@@ -1806,20 +1806,7 @@
         },
     },
 
-    stubs: {
-        symbol_file: "libc.map.txt",
-        versions: [
-            "29",
-            "R",
-            "current",
-        ],
-    },
-    llndk: {
-        symbol_file: "libc.map.txt",
-        export_headers_as_system: true,
-        export_preprocessed_headers: ["include"],
-        export_llndk_headers: ["libc_llndk_headers"],
-    },
+
     apex_available: [
         "//apex_available:platform",
         "com.android.runtime",
@@ -1834,9 +1821,58 @@
     },
 }
 
+cc_library {
+    name: "libc",
+      defaults: [
+        "libc_library_defaults",
+    ],
+    stubs: {
+        symbol_file: "libc.map.txt",
+        versions: [
+            "29",
+            "R",
+            "current",
+        ],
+    },
+    static_ndk_lib: true,
+    llndk: {
+        symbol_file: "libc.map.txt",
+        export_headers_as_system: true,
+        export_preprocessed_headers: ["include"],
+        export_llndk_headers: ["libc_llndk_headers"],
+    },
+}
+
+cc_library {
+    name: "libc_hwasan",
+      defaults: [
+        "libc_library_defaults",
+    ],
+    sanitize: {
+        hwaddress: true,
+    },
+    enabled: false,
+    target: {
+        android_arm64: {
+            enabled: true,
+        },
+    },
+    stem: "libc",
+    relative_install_path: "hwasan",
+    // We don't really need the stubs, but this needs to stay to trigger the
+    // symlink logic in soong.
+    stubs: {
+        symbol_file: "libc.map.txt",
+    },
+    native_bridge_supported: false,
+    // It is never correct to depend on this directly. This is only
+    // needed for the runtime apex, and in base_system.mk.
+    visibility: ["//bionic/apex"],
+}
+
 genrule {
     name: "libc.arm.map",
-    out: ["libc.arm.map"],
+    out: ["libc.arm.map.txt"],
     srcs: ["libc.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm $(in) $(out)",
@@ -1844,7 +1880,7 @@
 
 genrule {
     name: "libc.arm64.map",
-    out: ["libc.arm64.map"],
+    out: ["libc.arm64.map.txt"],
     srcs: ["libc.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm64 $(in) $(out)",
@@ -1852,7 +1888,7 @@
 
 genrule {
     name: "libc.riscv64.map",
-    out: ["libc.riscv64.map"],
+    out: ["libc.riscv64.map.txt"],
     srcs: ["libc.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) riscv64 $(in) $(out)",
@@ -1860,7 +1896,7 @@
 
 genrule {
     name: "libc.x86.map",
-    out: ["libc.x86.map"],
+    out: ["libc.x86.map.txt"],
     srcs: ["libc.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86 $(in) $(out)",
@@ -1868,7 +1904,7 @@
 
 genrule {
     name: "libc.x86_64.map",
-    out: ["libc.x86_64.map"],
+    out: ["libc.x86_64.map.txt"],
     srcs: ["libc.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86_64 $(in) $(out)",
@@ -2073,7 +2109,7 @@
 
 genrule {
     name: "libstdc++.arm.map",
-    out: ["libstdc++.arm.map"],
+    out: ["libstdc++.arm.map.txt"],
     srcs: ["libstdc++.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm $(in) $(out)",
@@ -2081,7 +2117,7 @@
 
 genrule {
     name: "libstdc++.arm64.map",
-    out: ["libstdc++.arm64.map"],
+    out: ["libstdc++.arm64.map.txt"],
     srcs: ["libstdc++.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm64 $(in) $(out)",
@@ -2089,7 +2125,7 @@
 
 genrule {
     name: "libstdc++.riscv64.map",
-    out: ["libstdc++.riscv64.map"],
+    out: ["libstdc++.riscv64.map.txt"],
     srcs: ["libstdc++.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) riscv64 $(in) $(out)",
@@ -2097,7 +2133,7 @@
 
 genrule {
     name: "libstdc++.x86.map",
-    out: ["libstdc++.x86.map"],
+    out: ["libstdc++.x86.map.txt"],
     srcs: ["libstdc++.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86 $(in) $(out)",
@@ -2105,7 +2141,7 @@
 
 genrule {
     name: "libstdc++.x86_64.map",
-    out: ["libstdc++.x86_64.map"],
+    out: ["libstdc++.x86_64.map.txt"],
     srcs: ["libstdc++.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86_64 $(in) $(out)",
@@ -2178,6 +2214,8 @@
     srcs: ["arch-common/bionic/crtbrand.S"],
 
     defaults: ["crt_so_defaults"],
+    // crtbrand is an intermediate artifact, not a final CRT object.
+    exclude_from_ndk_sysroot: true,
 }
 
 cc_object {
@@ -2307,6 +2345,11 @@
                 "arch-arm64/string/__memcpy_chk.S",
             ],
         },
+        riscv64: {
+            srcs: [
+               "arch-riscv64/string/__memcpy_chk.S",
+            ],
+        },
     },
     whole_static_libs: [
         "libarm-optimized-routines-mem",
diff --git a/libc/NOTICE b/libc/NOTICE
index 9d55592..4d3a108 100644
--- a/libc/NOTICE
+++ b/libc/NOTICE
@@ -894,6 +894,34 @@
 
 -------------------------------------------------------------------
 
+Copyright (C) 2023 The Android Open Source Project
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+ * Redistributions of source code must retain the above copyright
+   notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above copyright
+   notice, this list of conditions and the following disclaimer in
+   the documentation and/or other materials provided with the
+   distribution.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+SUCH DAMAGE.
+
+-------------------------------------------------------------------
+
 Copyright (c) 1980, 1983, 1988, 1993
    The Regents of the University of California.  All rights reserved.
 
diff --git a/libc/arch-arm64/bionic/setjmp.S b/libc/arch-arm64/bionic/setjmp.S
index 8e00b56..d787a56 100644
--- a/libc/arch-arm64/bionic/setjmp.S
+++ b/libc/arch-arm64/bionic/setjmp.S
@@ -46,8 +46,6 @@
 // 0      sigflag/cookie  setjmp cookie in top 31 bits, signal mask flag in low bit
 // 1      sigmask         signal mask (not used with _setjmp / _longjmp)
 // 2      core_base       base of core registers (x18-x30, sp)
-//                        (We only store the low bits of x18 to avoid leaking the
-//                        shadow call stack address into memory.)
 // 16     float_base      base of float registers (d8-d15)
 // 24     checksum        checksum of core registers
 // 25     reserved        reserved entries (room to grow)
@@ -68,8 +66,6 @@
 #define _JB_D8_D9       (_JB_D10_D11 + 2)
 #define _JB_CHECKSUM    (_JB_D8_D9 + 2)
 
-#define SCS_MASK (SCS_SIZE - 1)
-
 .macro m_mangle_registers reg, sp_reg
   eor x3, x3, \reg
   eor x19, x19, \reg
@@ -155,6 +151,9 @@
   bic x1, x1, #1
 
   // Mask off the high bits of the shadow call stack pointer.
+  // We only store the low bits of x18 to avoid leaking the
+  // shadow call stack address into memory.
+  // See the SCS commentary in pthread_internal.h for more detail.
   and x3, x18, #SCS_MASK
 
   // Save core registers.
diff --git a/libc/arch-arm64/bionic/vfork.S b/libc/arch-arm64/bionic/vfork.S
index 9eb82d8..9b19232 100644
--- a/libc/arch-arm64/bionic/vfork.S
+++ b/libc/arch-arm64/bionic/vfork.S
@@ -28,6 +28,7 @@
 
 #include <platform/bionic/tls_defines.h>
 #include <private/bionic_asm.h>
+#include <private/bionic_asm_offsets.h>
 #include <asm/signal.h>
 #include <linux/sched.h>
 
@@ -42,10 +43,29 @@
     ldr     w10, [x9, #20]
     str     w0, [x9, #20]
 
-    // Clear vfork_child_stack_bottom_.
-    str     xzr, [x9, #776]
+    mov     x0, #SIGCHLD
 
-    mov     x0, #(CLONE_VM | CLONE_VFORK | SIGCHLD)
+    // If either HWASan or stack MTE is enabled, set up the clone() flags to
+    // make vfork() act like fork(). We don't call the atfork handlers, so we
+    // may deadlock if the child allocates, but we have seen badly written
+    // atfork handlers themselves cause deadlocks [1]. ndk_translation already
+    // implements vfork() as fork() without calling handlers, so we have some
+    // evidence that it isn't necessary to call them.
+    //
+    // POSIX.1 defines vfork() to have the same effect as fork() except that
+    // most behavior, including heap allocation, becomes undefined in the child,
+    // so we aren't violating POSIX by doing this.
+    //
+    // [1] https://cs.android.com/android/platform/superproject/+/master:system/extras/simpleperf/app_api/cpp/simpleperf.cpp;drc=788fa4183441f4977ddbd5a055e42a7fe7691d21;l=308
+#if !__has_feature(hwaddress_sanitizer)
+    // if (!__libc_globals->memtag_stack) x0 |= CLONE_VM | CLONE_VFORK;
+    adrp    x1, __libc_globals + OFFSETOF_libc_globals_memtag_stack
+    ldrb    w1, [x1, :lo12:__libc_globals + OFFSETOF_libc_globals_memtag_stack]
+    cbnz    w1, 1f
+    orr     x0, x0, #CLONE_VM
+    orr     x0, x0, #CLONE_VFORK
+1:
+#endif
     mov     x1, xzr
     mov     x2, xzr
     mov     x3, xzr
@@ -62,25 +82,6 @@
     cneg    x0, x0, hi
     b.hi    __set_errno_internal
 
-    // Clean up stack shadow in the parent process.
-    // https://github.com/google/sanitizers/issues/925
-    paciasp
-    .cfi_negate_ra_state
-    stp x0, x30, [sp, #-16]!
-    .cfi_adjust_cfa_offset 16
-    .cfi_rel_offset x0, 0
-    .cfi_rel_offset x30, 8
-
-    add x0, sp, #16
-    bl memtag_handle_vfork
-
-    ldp x0, x30, [sp], #16
-    .cfi_adjust_cfa_offset -16
-    .cfi_restore x0
-    .cfi_restore x30
-    autiasp
-    .cfi_negate_ra_state
-
 .L_exit:
     ret
 END(vfork)
diff --git a/libc/arch-riscv64/bionic/setjmp.S b/libc/arch-riscv64/bionic/setjmp.S
index eea2978..26f7ec9 100644
--- a/libc/arch-riscv64/bionic/setjmp.S
+++ b/libc/arch-riscv64/bionic/setjmp.S
@@ -36,45 +36,47 @@
 // 0      sigflag/cookie  setjmp cookie in top 31 bits, signal mask flag in low bit
 // 1      sigmask         64-bit signal mask
 // 2      ra
-// 3      s0
+// 3      sp
+// 4      gp
+// 5      s0
 // ......
-// 14     s11
-// 15     sp
-// 16     fs0
+// 16     s11
+// 17     fs0
 // ......
-// 27     fs11
-// 28     checksum
+// 28     fs11
+// 29     checksum
 // _JBLEN: defined in bionic/libc/include/setjmp.h
 
 #define _JB_SIGFLAG   0
 #define _JB_SIGMASK   1 * 8
 #define _JB_RA        2 * 8
-#define _JB_S0        3 * 8
-#define _JB_S1        4 * 8
-#define _JB_S2        5 * 8
-#define _JB_S3        6 * 8
-#define _JB_S4        7 * 8
-#define _JB_S5        8 * 8
-#define _JB_S6        9 * 8
-#define _JB_S7       10 * 8
-#define _JB_S8       11 * 8
-#define _JB_S9       12 * 8
-#define _JB_S10      13 * 8
-#define _JB_S11      14 * 8
-#define _JB_SP       15 * 8
-#define _JB_FS0      16 * 8
-#define _JB_FS1      17 * 8
-#define _JB_FS2      18 * 8
-#define _JB_FS3      19 * 8
-#define _JB_FS4      20 * 8
-#define _JB_FS5      21 * 8
-#define _JB_FS6      22 * 8
-#define _JB_FS7      23 * 8
-#define _JB_FS8      24 * 8
-#define _JB_FS9      25 * 8
-#define _JB_FS10     26 * 8
-#define _JB_FS11     27 * 8
-#define _JB_CHECKSUM 28 * 8
+#define _JB_SP        3 * 8
+#define _JB_GP        4 * 8
+#define _JB_S0        5 * 8
+#define _JB_S1        6 * 8
+#define _JB_S2        7 * 8
+#define _JB_S3        8 * 8
+#define _JB_S4        9 * 8
+#define _JB_S5       10 * 8
+#define _JB_S6       11 * 8
+#define _JB_S7       12 * 8
+#define _JB_S8       13 * 8
+#define _JB_S9       14 * 8
+#define _JB_S10      15 * 8
+#define _JB_S11      16 * 8
+#define _JB_FS0      17 * 8
+#define _JB_FS1      18 * 8
+#define _JB_FS2      19 * 8
+#define _JB_FS3      20 * 8
+#define _JB_FS4      21 * 8
+#define _JB_FS5      22 * 8
+#define _JB_FS6      23 * 8
+#define _JB_FS7      24 * 8
+#define _JB_FS8      25 * 8
+#define _JB_FS9      26 * 8
+#define _JB_FS10     27 * 8
+#define _JB_FS11     28 * 8
+#define _JB_CHECKSUM 29 * 8
 
 .macro m_mangle_registers reg, sp_reg
   xor s0, s0, \reg
@@ -89,12 +91,13 @@
   xor s9, s9, \reg
   xor s10, s10, \reg
   xor s11, s11, \reg
+  xor a4, a4, \reg  // a4 is the masked gp (x3) for SCS.
   xor \sp_reg, \sp_reg, \reg
 .endm
 
 .macro m_calculate_checksum dst, src, scratch
   li \dst, 0
-  .irp i,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27
+  .irp i,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27,28
     ld \scratch, (\i * 8)(\src)
     xor \dst, \dst, \scratch
   .endr
@@ -151,10 +154,19 @@
   ld a1, _JB_SIGFLAG(a0)
   andi a1, a1, -2
 
+  // Mask off the high bits of the shadow call stack pointer.
+  // We only store the low bits of gp to avoid leaking the
+  // shadow call stack address into memory.
+  // See the SCS commentary in pthread_internal.h for more detail.
+  li a4, SCS_MASK
+  and a4, a4, gp
+
   // Save core registers.
   mv a2, sp
   m_mangle_registers a1, sp_reg=a2
   sd ra,  _JB_RA(a0)
+  sd a4,  _JB_GP(a0)  // a4 is the masked gp (x3) for SCS.
+  sd a2,  _JB_SP(a0)
   sd s0,  _JB_S0(a0)
   sd s1,  _JB_S1(a0)
   sd s2,  _JB_S2(a0)
@@ -167,7 +179,6 @@
   sd s9,  _JB_S9(a0)
   sd s10, _JB_S10(a0)
   sd s11, _JB_S11(a0)
-  sd a2,  _JB_SP(a0)
   m_unmangle_registers a1, sp_reg=a2
 
   // Save floating point registers.
@@ -229,6 +240,7 @@
   // Restore core registers.
   andi a2, a2, -2
   ld ra,  _JB_RA(a0)
+  ld a4,  _JB_GP(a0)  // Don't clobber the upper bits of gp (x3) used for SCS yet.
   ld s0,  _JB_S0(a0)
   ld s1,  _JB_S1(a0)
   ld s2,  _JB_S2(a0)
@@ -245,6 +257,11 @@
   m_unmangle_registers a2, sp_reg=a3
   mv sp, a3
 
+  // Restore the low bits of the shadow call stack pointer.
+  li a5, ~SCS_MASK
+  and gp, gp, a5
+  or gp, gp, a4
+
   addi sp, sp, -24
   sd   ra, 0(sp)
   sd   a0, 8(sp)
diff --git a/libc/arch-riscv64/string/__memcpy_chk.S b/libc/arch-riscv64/string/__memcpy_chk.S
new file mode 100644
index 0000000..4a2d13d
--- /dev/null
+++ b/libc/arch-riscv64/string/__memcpy_chk.S
@@ -0,0 +1,9 @@
+#include <private/bionic_asm.h>
+
+ENTRY(__memcpy_chk)
+  bleu a2, a3, 1f
+  call __memcpy_chk_fail
+
+1:
+   tail memcpy
+END(__memcpy_chk)
diff --git a/libc/async_safe/async_safe_log.cpp b/libc/async_safe/async_safe_log.cpp
index d31fe03..420560f 100644
--- a/libc/async_safe/async_safe_log.cpp
+++ b/libc/async_safe/async_safe_log.cpp
@@ -254,7 +254,7 @@
     bool alternate = false;
     size_t bytelen = sizeof(int);
     int slen;
-    char buffer[32]; /* temporary buffer used to format numbers */
+    char buffer[64];  // temporary buffer used to format numbers/format errno string
 
     char c;
 
@@ -345,7 +345,6 @@
 
     /* conversion specifier */
     const char* str = buffer;
-    char strerror_buf[256];
     if (c == 's') {
       /* string */
       str = va_arg(args, const char*);
@@ -360,7 +359,7 @@
       buffer[1] = 'x';
       format_integer(buffer + 2, sizeof(buffer) - 2, value, 'x');
     } else if (c == 'm') {
-      str = strerror_r(errno, strerror_buf, sizeof(strerror_buf));
+      strerror_r(errno, buffer, sizeof(buffer));
     } else if (c == 'd' || c == 'i' || c == 'o' || c == 'u' || c == 'x' || c == 'X') {
       /* integers - first read value from stack */
       uint64_t value;
diff --git a/libc/bionic/exec.cpp b/libc/bionic/exec.cpp
index 40612e7..863aa97 100644
--- a/libc/bionic/exec.cpp
+++ b/libc/bionic/exec.cpp
@@ -186,6 +186,5 @@
 
 __attribute__((no_sanitize("memtag"))) int execve(const char* pathname, char* const* argv,
                                                   char* const* envp) {
-  __get_thread()->vfork_child_stack_bottom = __builtin_frame_address(0);
   return __execve(pathname, argv, envp);
 }
diff --git a/libc/bionic/exit.cpp b/libc/bionic/exit.cpp
index 52fd193..04baac2 100644
--- a/libc/bionic/exit.cpp
+++ b/libc/bionic/exit.cpp
@@ -37,7 +37,6 @@
 extern "C" __noreturn void __exit_group(int status);
 
 __attribute__((no_sanitize("memtag"))) void _exit(int status) {
-  __get_thread()->vfork_child_stack_bottom = __builtin_frame_address(0);
   __exit_group(status);
 }
 
diff --git a/libc/bionic/fortify.cpp b/libc/bionic/fortify.cpp
index 73cf973..7dee5e3 100644
--- a/libc/bionic/fortify.cpp
+++ b/libc/bionic/fortify.cpp
@@ -489,9 +489,9 @@
   return strcpy(dst, src);
 }
 
-#if !defined(__arm__) && !defined(__aarch64__)
+#if !defined(__arm__) && !defined(__aarch64__) && !defined(__riscv)
 // Runtime implementation of __memcpy_chk (used directly by compiler, not in headers).
-// arm32 and arm64 have assembler implementations, and don't need this C fallback.
+// arm32,arm64,riscv have assembler implementations, and don't need this C fallback.
 extern "C" void* __memcpy_chk(void* dst, const void* src, size_t count, size_t dst_len) {
   __check_count("memcpy", "count", count);
   __check_buffer_access("memcpy", "write into", count, dst_len);
diff --git a/libc/bionic/heap_tagging.cpp b/libc/bionic/heap_tagging.cpp
index 78d21b0..be21e0c 100644
--- a/libc/bionic/heap_tagging.cpp
+++ b/libc/bionic/heap_tagging.cpp
@@ -212,29 +212,3 @@
   __hwasan_handle_longjmp(sp_dst);
 #endif  // __has_feature(hwaddress_sanitizer)
 }
-
-extern "C" __LIBC_HIDDEN__ __attribute__((no_sanitize("memtag"), no_sanitize("hwaddress"))) void
-memtag_handle_vfork(void* sp __unused) {
-#ifdef __aarch64__
-  if (__libc_globals->memtag_stack) {
-    void* child_sp = __get_thread()->vfork_child_stack_bottom;
-    __get_thread()->vfork_child_stack_bottom = nullptr;
-    if (child_sp) {
-      size_t distance = reinterpret_cast<uintptr_t>(sp) - reinterpret_cast<uintptr_t>(child_sp);
-      if (distance > kUntagLimit) {
-        async_safe_fatal(
-            "memtag_handle_vfork: stack adjustment too large! %p -> %p, distance %zx > %zx\n",
-            child_sp, sp, distance, kUntagLimit);
-      } else {
-        untag_memory(child_sp, sp);
-      }
-    } else {
-      async_safe_fatal("memtag_handle_vfork: child SP unknown\n");
-    }
-  }
-#endif  // __aarch64__
-
-#if __has_feature(hwaddress_sanitizer)
-  __hwasan_handle_vfork(sp);
-#endif  // __has_feature(hwaddress_sanitizer)
-}
diff --git a/libc/bionic/jemalloc_wrapper.cpp b/libc/bionic/jemalloc_wrapper.cpp
index ef488ee..ce3f314 100644
--- a/libc/bionic/jemalloc_wrapper.cpp
+++ b/libc/bionic/jemalloc_wrapper.cpp
@@ -102,7 +102,7 @@
       }
     }
     return 1;
-  } else if (param == M_PURGE) {
+  } else if (param == M_PURGE || param == M_PURGE_ALL) {
     // Only clear the current thread cache since there is no easy way to
     // clear the caches of other threads.
     // This must be done first so that cleared allocations get purged
diff --git a/libc/bionic/libc_init_common.cpp b/libc/bionic/libc_init_common.cpp
index 5d5ecac..59b2ddb 100644
--- a/libc/bionic/libc_init_common.cpp
+++ b/libc/bionic/libc_init_common.cpp
@@ -289,6 +289,7 @@
       "LD_DEBUG",
       "LD_DEBUG_OUTPUT",
       "LD_DYNAMIC_WEAK",
+      "LD_HWASAN",
       "LD_LIBRARY_PATH",
       "LD_ORIGIN_PATH",
       "LD_PRELOAD",
diff --git a/libc/bionic/pthread_create.cpp b/libc/bionic/pthread_create.cpp
index 417ce76..844f9d8 100644
--- a/libc/bionic/pthread_create.cpp
+++ b/libc/bionic/pthread_create.cpp
@@ -116,14 +116,14 @@
 }
 
 static void __init_shadow_call_stack(pthread_internal_t* thread __unused) {
-#ifdef __aarch64__
+#if defined(__aarch64__) || defined(__riscv)
   // Allocate the stack and the guard region.
   char* scs_guard_region = reinterpret_cast<char*>(
       mmap(nullptr, SCS_GUARD_REGION_SIZE, 0, MAP_PRIVATE | MAP_ANON, -1, 0));
   thread->shadow_call_stack_guard_region = scs_guard_region;
 
   // The address is aligned to SCS_SIZE so that we only need to store the lower log2(SCS_SIZE) bits
-  // in jmp_buf.
+  // in jmp_buf. See the SCS commentary in pthread_internal.h for more detail.
   char* scs_aligned_guard_region =
       reinterpret_cast<char*>(align_up(reinterpret_cast<uintptr_t>(scs_guard_region), SCS_SIZE));
 
@@ -133,11 +133,15 @@
   size_t scs_offset =
       (getpid() == 1) ? 0 : (arc4random_uniform(SCS_GUARD_REGION_SIZE / SCS_SIZE - 1) * SCS_SIZE);
 
-  // Make the stack readable and writable and store its address in register x18. This is
-  // deliberately the only place where the address is stored.
-  char *scs = scs_aligned_guard_region + scs_offset;
+  // Make the stack read-write, and store its address in the register we're using as the shadow
+  // stack pointer. This is deliberately the only place where the address is stored.
+  char* scs = scs_aligned_guard_region + scs_offset;
   mprotect(scs, SCS_SIZE, PROT_READ | PROT_WRITE);
+#if defined(__aarch64__)
   __asm__ __volatile__("mov x18, %0" ::"r"(scs));
+#elif defined(__riscv)
+  __asm__ __volatile__("mv x3, %0" ::"r"(scs));
+#endif
 #endif
 }
 
diff --git a/libc/bionic/pthread_exit.cpp b/libc/bionic/pthread_exit.cpp
index bde95ec..f584b27 100644
--- a/libc/bionic/pthread_exit.cpp
+++ b/libc/bionic/pthread_exit.cpp
@@ -117,7 +117,7 @@
     __rt_sigprocmask(SIG_BLOCK, &set, nullptr, sizeof(sigset64_t));
   }
 
-#ifdef __aarch64__
+#if defined(__aarch64__) || defined(__riscv)
   // Free the shadow call stack and guard pages.
   munmap(thread->shadow_call_stack_guard_region, SCS_GUARD_REGION_SIZE);
 #endif
diff --git a/libc/bionic/pthread_internal.h b/libc/bionic/pthread_internal.h
index 7222b62..7efbf6d 100644
--- a/libc/bionic/pthread_internal.h
+++ b/libc/bionic/pthread_internal.h
@@ -105,9 +105,14 @@
 
   void* alternate_signal_stack;
 
-  // The start address of the shadow call stack's guard region (arm64 only).
+  // The start address of the shadow call stack's guard region (arm64/riscv64).
+  // This region is SCS_GUARD_REGION_SIZE bytes large, but only SCS_SIZE bytes
+  // are actually used.
+  //
   // This address is only used to deallocate the shadow call stack on thread
-  // exit; the address of the stack itself is stored only in the x18 register.
+  // exit; the address of the stack itself is stored only in the register used
+  // as the shadow stack pointer (x18 on arm64, gp on riscv64).
+  //
   // Because the protection offered by SCS relies on the secrecy of the stack
   // address, storing the address here weakens the protection, but only
   // slightly, because it is relatively easy for an attacker to discover the
@@ -115,13 +120,24 @@
   // to other allocations), but not the stack itself, which is <0.1% of the size
   // of the guard region.
   //
+  // longjmp()/setjmp() don't store all the bits of the shadow stack pointer,
+  // only the bottom bits covered by SCS_MASK. Since longjmp()/setjmp() between
+  // different threads is undefined behavior (and unsupported on Android), we
+  // can retrieve the high bits of the shadow stack pointer from the current
+  // value in the register --- all the jmp_buf needs to store is where exactly
+  // the shadow stack pointer is *within* the thread's shadow stack: the bottom
+  // bits of the register.
+  //
   // There are at least two other options for discovering the start address of
   // the guard region on thread exit, but they are not as simple as storing in
   // TLS.
-  // 1) Derive it from the value of the x18 register. This is only possible in
-  //    processes that do not contain legacy code that might clobber x18,
-  //    therefore each process must declare early during process startup whether
-  //    it might load legacy code.
+  //
+  // 1) Derive it from the current value of the shadow stack pointer. This is
+  //    only possible in processes that do not contain legacy code that might
+  //    clobber x18 on arm64, therefore each process must declare early during
+  //    process startup whether it might load legacy code.
+  //    TODO: riscv64 has no legacy code, so we can actually go this route
+  //    there, but hopefully we'll actually get the Zisslpcfi extension instead.
   // 2) Mark the guard region as such using prctl(PR_SET_VMA_ANON_NAME) and
   //    discover its address by reading /proc/self/maps. One issue with this is
   //    that reading /proc/self/maps can race with allocations, so we may need
@@ -160,13 +176,6 @@
   bionic_tls* bionic_tls;
 
   int errno_value;
-
-  // The last observed value of SP in a vfork child process.
-  // The part of the stack between this address and the value of SP when the vfork parent process
-  // regains control may have stale MTE tags and needs cleanup. This field is only meaningful while
-  // the parent is waiting for the vfork child to return control by calling either exec*() or
-  // exit().
-  void* vfork_child_stack_bottom;
 };
 
 struct ThreadMapping {
diff --git a/libc/bionic/scandir.cpp b/libc/bionic/scandir.cpp
index f528286..0acef36 100644
--- a/libc/bionic/scandir.cpp
+++ b/libc/bionic/scandir.cpp
@@ -69,11 +69,8 @@
   }
 
   void Sort(int (*comparator)(const dirent**, const dirent**)) {
-    // If we have entries and a comparator, sort them.
-    if (size_ > 0 && comparator != nullptr) {
-      qsort(names_, size_, sizeof(dirent*),
-            reinterpret_cast<int (*)(const void*, const void*)>(comparator));
-    }
+    qsort(names_, size_, sizeof(dirent*),
+          reinterpret_cast<int (*)(const void*, const void*)>(comparator));
   }
 
  private:
@@ -120,7 +117,9 @@
     names.Add(entry);
   }
 
-  names.Sort(comparator);
+  if (comparator != nullptr) {
+    names.Sort(comparator);
+  }
 
   size_t size = names.size();
   *name_list = names.release();
diff --git a/libc/bionic/spawn.cpp b/libc/bionic/spawn.cpp
index 7e80ef6..5d76f77 100644
--- a/libc/bionic/spawn.cpp
+++ b/libc/bionic/spawn.cpp
@@ -68,7 +68,9 @@
 enum Action {
   kOpen,
   kClose,
-  kDup2
+  kDup2,
+  kChdir,
+  kFchdir,
 };
 
 struct __posix_spawn_file_action {
@@ -93,6 +95,10 @@
     } else if (what == kClose) {
       // Failure to close is ignored.
       close(fd);
+    } else if (what == kChdir) {
+      if (chdir(path) == -1) _exit(127);
+    } else if (what == kFchdir) {
+      if (fchdir(fd) == -1) _exit(127);
     } else {
       // It's a dup2.
       if (fd == new_fd) {
@@ -340,7 +346,7 @@
   if (action == nullptr) return errno;
 
   action->next = nullptr;
-  if (path != nullptr) {
+  if (what == kOpen || what == kChdir) {
     action->path = strdup(path);
     if (action->path == nullptr) {
       free(action);
@@ -380,3 +386,12 @@
   if (fd < 0 || new_fd < 0) return EBADF;
   return posix_spawn_add_file_action(actions, kDup2, fd, new_fd, nullptr, 0, 0);
 }
+
+int posix_spawn_file_actions_addchdir_np(posix_spawn_file_actions_t* actions, const char* path) {
+  return posix_spawn_add_file_action(actions, kChdir, -1, -1, path, 0, 0);
+}
+
+int posix_spawn_file_actions_addfchdir_np(posix_spawn_file_actions_t* actions, int fd) {
+  if (fd < 0) return EBADF;
+  return posix_spawn_add_file_action(actions, kFchdir, fd, -1, nullptr, 0, 0);
+}
diff --git a/libc/bionic/syslog.cpp b/libc/bionic/syslog.cpp
index 6b17d26..a459c6b 100644
--- a/libc/bionic/syslog.cpp
+++ b/libc/bionic/syslog.cpp
@@ -18,18 +18,22 @@
 #include <stdlib.h>
 #include <string.h>
 #include <syslog.h>
+#include <unistd.h>
 
 #include <async_safe/log.h>
 
 static const char* syslog_log_tag = nullptr;
 static int syslog_priority_mask = 0xff;
+static int syslog_options = 0;
 
 void closelog() {
   syslog_log_tag = nullptr;
+  syslog_options = 0;
 }
 
-void openlog(const char* log_tag, int /*options*/, int /*facility*/) {
+void openlog(const char* log_tag, int options, int /*facility*/) {
   syslog_log_tag = log_tag;
+  syslog_options = options;
 }
 
 int setlogmask(int new_mask) {
@@ -73,10 +77,16 @@
     android_log_priority = ANDROID_LOG_DEBUG;
   }
 
-  // We can't let async_safe_format_log do the formatting because it doesn't support
-  // all the printf functionality.
+  // We can't let async_safe_format_log do the formatting because it doesn't
+  // support all the printf functionality.
   char log_line[1024];
-  vsnprintf(log_line, sizeof(log_line), fmt, args);
+  int n = vsnprintf(log_line, sizeof(log_line), fmt, args);
+  if (n < 0) return;
 
   async_safe_format_log(android_log_priority, log_tag, "%s", log_line);
+  if ((syslog_options & LOG_PERROR) != 0) {
+    bool have_newline =
+        (n > 0 && n < static_cast<int>(sizeof(log_line)) && log_line[n - 1] == '\n');
+    dprintf(STDERR_FILENO, "%s: %s%s", log_tag, log_line, have_newline ? "" : "\n");
+  }
 }
diff --git a/libc/bionic/timespec_get.cpp b/libc/bionic/time.cpp
similarity index 89%
rename from libc/bionic/timespec_get.cpp
rename to libc/bionic/time.cpp
index 7fc2182..800395e 100644
--- a/libc/bionic/timespec_get.cpp
+++ b/libc/bionic/time.cpp
@@ -29,5 +29,9 @@
 #include <time.h>
 
 int timespec_get(timespec* ts, int base) {
-  return (base == TIME_UTC && clock_gettime(CLOCK_REALTIME, ts) != -1) ? base : 0;
+  return (clock_gettime(base - 1, ts) != -1) ? base : 0;
+}
+
+int timespec_getres(timespec* ts, int base) {
+  return (clock_getres(base - 1, ts) != -1) ? base : 0;
 }
diff --git a/libc/bionic/tmpfile.cpp b/libc/bionic/tmpfile.cpp
index 3d04610..4d6a1fb 100644
--- a/libc/bionic/tmpfile.cpp
+++ b/libc/bionic/tmpfile.cpp
@@ -51,6 +51,9 @@
   return nullptr;
 }
 
+// O_TMPFILE isn't available until Linux 3.11, so we fall back to this on
+// older kernels. AOSP was on a new enough kernel in the Lollipop timeframe,
+// so this code should be obsolete by 2025.
 static FILE* __tmpfile_dir_legacy(const char* tmp_dir) {
   char* path = nullptr;
   if (asprintf(&path, "%s/tmp.XXXXXXXXXX", tmp_dir) == -1) {
@@ -79,25 +82,18 @@
   return __fd_to_fp(fd);
 }
 
-static FILE* __tmpfile_dir(const char* tmp_dir) {
-  int fd = open(tmp_dir, O_TMPFILE | O_RDWR, S_IRUSR | S_IWUSR);
-  if (fd == -1) return __tmpfile_dir_legacy(tmp_dir);
-  return __fd_to_fp(fd);
+const char* __get_TMPDIR() {
+  // Use $TMPDIR if set, or fall back to /data/local/tmp otherwise.
+  // Useless for apps, but good enough for the shell.
+  const char* tmpdir = getenv("TMPDIR");
+  return (tmpdir == nullptr) ? "/data/local/tmp" : tmpdir;
 }
 
 FILE* tmpfile() {
-  // TODO: get this app's temporary directory from the framework ("/data/data/app/cache").
-
-  // $EXTERNAL_STORAGE turns out not to be very useful because it doesn't support hard links.
-  // This means we can't do the usual trick of calling unlink before handing the file back.
-
-  FILE* fp = __tmpfile_dir("/data/local/tmp");
-  if (fp == nullptr) {
-    // P_tmpdir is "/tmp/", but POSIX explicitly says that tmpdir(3) should try P_tmpdir before
-    // giving up. This is potentially useful for bionic on the host anyway.
-    fp = __tmpfile_dir(P_tmpdir);
-  }
-  return fp;
+  const char* tmpdir = __get_TMPDIR();
+  int fd = open(tmpdir, O_TMPFILE | O_RDWR, S_IRUSR | S_IWUSR);
+  if (fd == -1) return __tmpfile_dir_legacy(tmpdir);
+  return __fd_to_fp(fd);
 }
 __strong_alias(tmpfile64, tmpfile);
 
@@ -107,7 +103,7 @@
   // since we can't easily remove it...
 
   // $TMPDIR overrides any directory passed in.
-  char* tmpdir = getenv("TMPDIR");
+  const char* tmpdir = getenv("TMPDIR");
   if (tmpdir != nullptr) dir = tmpdir;
 
   // If we still have no directory, we'll give you a default.
@@ -136,12 +132,7 @@
   static char buf[L_tmpnam];
   if (s == nullptr) s = buf;
 
-  // Use $TMPDIR if set, or fall back to /data/local/tmp otherwise.
-  // Useless for apps, but good enough for the shell.
-  const char* dir = getenv("TMPDIR");
-  if (dir == nullptr) dir = "/data/local/tmp";
-
   // Make up a mktemp(3) template and defer to it for the real work.
-  snprintf(s, L_tmpnam, "%s/tmpnam.XXXXXXXXXX", dir);
+  snprintf(s, L_tmpnam, "%s/tmpnam.XXXXXXXXXX", __get_TMPDIR());
   return mktemp(s);
 }
diff --git a/libc/include/android/api-level.h b/libc/include/android/api-level.h
index 79085d1..6602e5d 100644
--- a/libc/include/android/api-level.h
+++ b/libc/include/android/api-level.h
@@ -162,9 +162,15 @@
  */
 #define __ANDROID_API_T__ 33
 
-/** Names the "U" API level (34), for comparison against `__ANDROID_API__`. */
+/**
+ * Names the Android 14 (aka "U" or "UpsideDownCake") API level (34),
+ * for comparison against `__ANDROID_API__`.
+ */
 #define __ANDROID_API_U__ 34
 
+/** Names the "V" API level (35), for comparison against `__ANDROID_API__`. */
+#define __ANDROID_API_V__ 35
+
 /* This file is included in <features.h>, and might be used from .S files. */
 #if !defined(__ASSEMBLY__)
 
diff --git a/libc/include/android/dlext.h b/libc/include/android/dlext.h
index f0b731c..f216aab 100644
--- a/libc/include/android/dlext.h
+++ b/libc/include/android/dlext.h
@@ -157,7 +157,7 @@
   uint64_t flags;
 
   /** Used by `ANDROID_DLEXT_RESERVED_ADDRESS` and `ANDROID_DLEXT_RESERVED_ADDRESS_HINT`. */
-  void*   reserved_addr;
+  void*   _Nullable reserved_addr;
   /** Used by `ANDROID_DLEXT_RESERVED_ADDRESS` and `ANDROID_DLEXT_RESERVED_ADDRESS_HINT`. */
   size_t  reserved_size;
 
@@ -170,7 +170,7 @@
   off64_t library_fd_offset;
 
   /** Used by `ANDROID_DLEXT_USE_NAMESPACE`. */
-  struct android_namespace_t* library_namespace;
+  struct android_namespace_t* _Nullable library_namespace;
 } android_dlextinfo;
 
 /**
@@ -180,7 +180,7 @@
  *
  * Available since API level 21.
  */
-void* android_dlopen_ext(const char* __filename, int __flags, const android_dlextinfo* __info)
+void* _Nullable android_dlopen_ext(const char* _Nullable __filename, int __flags, const android_dlextinfo* _Nullable __info)
   __INTRODUCED_IN(21);
 
 __END_DECLS
diff --git a/libc/include/android/fdsan.h b/libc/include/android/fdsan.h
index 59ce133..3de0649 100644
--- a/libc/include/android/fdsan.h
+++ b/libc/include/android/fdsan.h
@@ -159,7 +159,7 @@
  *
  * The return value points to memory with static lifetime, do not attempt to modify it.
  */
-const char* android_fdsan_get_tag_type(uint64_t tag) __INTRODUCED_IN(29);
+const char* _Nonnull android_fdsan_get_tag_type(uint64_t tag) __INTRODUCED_IN(29);
 
 /*
  * Get an owner tag's value, with the type masked off.
diff --git a/libc/include/android/legacy_stdlib_inlines.h b/libc/include/android/legacy_stdlib_inlines.h
index e9b606a..f0985fe 100644
--- a/libc/include/android/legacy_stdlib_inlines.h
+++ b/libc/include/android/legacy_stdlib_inlines.h
@@ -38,15 +38,15 @@
 
 __BEGIN_DECLS
 
-static __inline double strtod_l(const char* __s, char** __end_ptr, locale_t __l) {
+static __inline double strtod_l(const char* _Nonnull __s, char* _Nullable * _Nullable __end_ptr, locale_t _Nonnull __l) {
   return strtod(__s, __end_ptr);
 }
 
-static __inline float strtof_l(const char* __s, char** __end_ptr, locale_t __l) {
+static __inline float strtof_l(const char* _Nonnull __s, char* _Nullable * _Nullable __end_ptr, locale_t _Nonnull __l) {
   return strtof(__s, __end_ptr);
 }
 
-static __inline long strtol_l(const char* __s, char** __end_ptr, int __base, locale_t __l) {
+static __inline long strtol_l(const char* _Nonnull __s, char* _Nullable * _Nullable __end_ptr, int __base, locale_t _Nonnull __l) {
   return strtol(__s, __end_ptr, __base);
 }
 
diff --git a/libc/include/android/set_abort_message.h b/libc/include/android/set_abort_message.h
index 5d8d8ee..2be01a9 100644
--- a/libc/include/android/set_abort_message.h
+++ b/libc/include/android/set_abort_message.h
@@ -46,6 +46,6 @@
  *
  * Available since API level 21.
  */
-void android_set_abort_message(const char* __msg) __INTRODUCED_IN(21);
+void android_set_abort_message(const char* _Nullable __msg) __INTRODUCED_IN(21);
 
 __END_DECLS
diff --git a/libc/include/bits/ctype_inlines.h b/libc/include/bits/ctype_inlines.h
index 744eb91..089a642 100644
--- a/libc/include/bits/ctype_inlines.h
+++ b/libc/include/bits/ctype_inlines.h
@@ -61,7 +61,7 @@
 __BEGIN_DECLS
 
 /** Internal implementation detail. Do not use. */
-extern const char* _ctype_;
+extern const char* _Nonnull _ctype_;
 
 /** Returns true if `ch` is in `[A-Za-z0-9]`. */
 __BIONIC_CTYPE_INLINE int isalnum(int __ch) {
@@ -175,33 +175,33 @@
 
 #if __ANDROID_API__ >= 21
 /** Like isalnum but with an ignored `locale_t`. */
-int isalnum_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isalnum_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isalpha but with an ignored `locale_t`. */
-int isalpha_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isalpha_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isblank but with an ignored `locale_t`. */
-int isblank_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isblank_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like iscntrl but with an ignored `locale_t`. */
-int iscntrl_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int iscntrl_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isdigit but with an ignored `locale_t`. */
-int isdigit_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isdigit_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isgraph but with an ignored `locale_t`. */
-int isgraph_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isgraph_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like islower but with an ignored `locale_t`. */
-int islower_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int islower_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isprint but with an ignored `locale_t`. */
-int isprint_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isprint_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like ispunct but with an ignored `locale_t`. */
-int ispunct_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int ispunct_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isspace but with an ignored `locale_t`. */
-int isspace_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isspace_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isupper but with an ignored `locale_t`. */
-int isupper_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isupper_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like isxdigit but with an ignored `locale_t`. */
-int isxdigit_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int isxdigit_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like tolower but with an ignored `locale_t`. */
-int tolower_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int tolower_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 /** Like toupper but with an ignored `locale_t`. */
-int toupper_l(int __ch, locale_t __l) __INTRODUCED_IN(21);
+int toupper_l(int __ch, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 #else
 // Implemented as static inlines in libc++ before 21.
 #endif
diff --git a/libc/include/bits/elf_common.h b/libc/include/bits/elf_common.h
index ea833f4..b3c57a2 100644
--- a/libc/include/bits/elf_common.h
+++ b/libc/include/bits/elf_common.h
@@ -418,12 +418,12 @@
 #define	SHT_HIOS		0x6fffffff	/* Last of OS specific semantics */
 #define	SHT_LOPROC		0x70000000	/* reserved range for processor */
 #define	SHT_X86_64_UNWIND	0x70000001	/* unwind information */
-#define	SHT_AMD64_UNWIND	SHT_X86_64_UNWIND 
+#define	SHT_AMD64_UNWIND	SHT_X86_64_UNWIND
 
 #define	SHT_ARM_EXIDX		0x70000001	/* Exception index table. */
-#define	SHT_ARM_PREEMPTMAP	0x70000002	/* BPABI DLL dynamic linking 
+#define	SHT_ARM_PREEMPTMAP	0x70000002	/* BPABI DLL dynamic linking
 						   pre-emption map. */
-#define	SHT_ARM_ATTRIBUTES	0x70000003	/* Object file compatibility 
+#define	SHT_ARM_ATTRIBUTES	0x70000003	/* Object file compatibility
 						   attributes. */
 #define	SHT_ARM_DEBUGOVERLAY	0x70000004	/* See DBGOVL for details. */
 #define	SHT_ARM_OVERLAYSECTION	0x70000005	/* See DBGOVL for details. */
@@ -648,6 +648,11 @@
 #define	DT_AARCH64_BTI_PLT		0x70000001
 #define	DT_AARCH64_PAC_PLT		0x70000003
 #define	DT_AARCH64_VARIANT_PCS		0x70000005
+#define DT_AARCH64_MEMTAG_MODE		0x70000009
+#define DT_AARCH64_MEMTAG_HEAP		0x7000000b
+#define DT_AARCH64_MEMTAG_STACK		0x7000000c
+#define DT_AARCH64_MEMTAG_GLOBALS	0x7000000d
+#define DT_AARCH64_MEMTAG_GLOBALSSZ	0x7000000f
 
 #define	DT_ARM_SYMTABSZ			0x70000001
 #define	DT_ARM_PREEMPTMAP		0x70000002
diff --git a/libc/include/bits/get_device_api_level_inlines.h b/libc/include/bits/get_device_api_level_inlines.h
index d14eb2c..dc5871b 100644
--- a/libc/include/bits/get_device_api_level_inlines.h
+++ b/libc/include/bits/get_device_api_level_inlines.h
@@ -35,8 +35,8 @@
 __BEGIN_DECLS
 
 // Avoid circular dependencies since this is exposed from <sys/cdefs.h>.
-int __system_property_get(const char* __name, char* __value);
-int atoi(const char* __s) __attribute_pure__;
+int __system_property_get(const char* _Nonnull __name, char*  _Nonnull __value);
+int atoi(const char* _Nonnull __s) __attribute_pure__;
 
 __BIONIC_GET_DEVICE_API_LEVEL_INLINE int android_get_device_api_level() {
   char value[92] = { 0 };
diff --git a/libc/include/bits/getopt.h b/libc/include/bits/getopt.h
index 0411716..60a89ed 100644
--- a/libc/include/bits/getopt.h
+++ b/libc/include/bits/getopt.h
@@ -38,12 +38,12 @@
  * Returns the next option character on success, returns -1 if all options have been parsed, and
  * returns `'?'` on error.
  */
-int getopt(int __argc, char* const __argv[], const char* __options);
+int getopt(int __argc, char* const _Nonnull __argv[_Nullable], const char* _Nonnull __options);
 
 /**
  * Points to the text of the corresponding value for options that take an argument.
  */
-extern char* optarg;
+extern char* _Nullable optarg;
 
 /**
  * The index of the next element to be processed.
diff --git a/libc/include/bits/glibc-syscalls.h b/libc/include/bits/glibc-syscalls.h
index c144919..79f7da0 100644
--- a/libc/include/bits/glibc-syscalls.h
+++ b/libc/include/bits/glibc-syscalls.h
@@ -906,6 +906,9 @@
 #if defined(__NR_restart_syscall)
   #define SYS_restart_syscall __NR_restart_syscall
 #endif
+#if defined(__NR_riscv_flush_icache)
+  #define SYS_riscv_flush_icache __NR_riscv_flush_icache
+#endif
 #if defined(__NR_rmdir)
   #define SYS_rmdir __NR_rmdir
 #endif
diff --git a/libc/include/bits/strcasecmp.h b/libc/include/bits/strcasecmp.h
index 3994b68..23acbe5 100644
--- a/libc/include/bits/strcasecmp.h
+++ b/libc/include/bits/strcasecmp.h
@@ -46,12 +46,12 @@
  * Returns an integer less than, equal to, or greater than zero if the first string is less than,
  * equal to, or greater than the second string (ignoring case).
  */
-int strcasecmp(const char* __s1, const char* __s2) __attribute_pure__;
+int strcasecmp(const char* _Nonnull __s1, const char* _Nonnull __s2) __attribute_pure__;
 
 /**
  * Like strcasecmp() but taking a `locale_t`.
  */
-int strcasecmp_l(const char* __s1, const char* __s2, locale_t __l) __attribute_pure__ __INTRODUCED_IN(23);
+int strcasecmp_l(const char* _Nonnull __s1, const char* _Nonnull __s2, locale_t _Nonnull __l) __attribute_pure__ __INTRODUCED_IN(23);
 
 /**
  * [strncasecmp(3)](http://man7.org/linux/man-pages/man3/strncasecmp.3.html) compares the first
@@ -61,11 +61,11 @@
  * first string is less than, equal to, or greater than the first `n` bytes of the second
  * string (ignoring case).
  */
-int strncasecmp(const char* __s1, const char* __s2, size_t __n) __attribute_pure__;
+int strncasecmp(const char* _Nonnull __s1, const char* _Nonnull __s2, size_t __n) __attribute_pure__;
 
 /**
  * Like strncasecmp() but taking a `locale_t`.
  */
-int strncasecmp_l(const char* __s1, const char* __s2, size_t __n, locale_t __l) __attribute_pure__ __INTRODUCED_IN(23);
+int strncasecmp_l(const char* _Nonnull __s1, const char* _Nonnull __s2, size_t __n, locale_t _Nonnull __l) __attribute_pure__ __INTRODUCED_IN(23);
 
 __END_DECLS
diff --git a/libc/include/bits/swab.h b/libc/include/bits/swab.h
index 63281b6..9591c2e 100644
--- a/libc/include/bits/swab.h
+++ b/libc/include/bits/swab.h
@@ -38,7 +38,7 @@
 
 __BEGIN_DECLS
 
-__BIONIC_SWAB_INLINE void swab(const void* __void_src, void* __void_dst, ssize_t __byte_count) {
+__BIONIC_SWAB_INLINE void swab(const void* _Nonnull __void_src, void* _Nonnull __void_dst, ssize_t __byte_count) {
   const uint8_t* __src = __BIONIC_CAST(static_cast, const uint8_t*, __void_src);
   uint8_t* __dst = __BIONIC_CAST(static_cast, uint8_t*, __void_dst);
   while (__byte_count > 1) {
diff --git a/libc/include/bits/wait.h b/libc/include/bits/wait.h
index a6a2129..c7f1fb0 100644
--- a/libc/include/bits/wait.h
+++ b/libc/include/bits/wait.h
@@ -53,7 +53,7 @@
 #define WIFEXITED(__status) (WTERMSIG(__status) == 0)
 
 /** Returns true if the process was stopped by a signal. */
-#define WIFSTOPPED(__status) (WTERMSIG(__status) == 0x7f)
+#define WIFSTOPPED(__status) (((__status) & 0xff) == 0x7f)
 
 /** Returns true if the process was terminated by a signal. */
 #define WIFSIGNALED(__status) (WTERMSIG((__status)+1) >= 2)
diff --git a/libc/include/dirent.h b/libc/include/dirent.h
index 2328b1a..2751b9e 100644
--- a/libc/include/dirent.h
+++ b/libc/include/dirent.h
@@ -95,7 +95,7 @@
  *
  * Returns null and sets `errno` on failure.
  */
-DIR* opendir(const char* __path);
+DIR* _Nullable opendir(const char* _Nonnull __path);
 
 /**
  * [fopendir(3)](http://man7.org/linux/man-pages/man3/opendir.3.html)
@@ -103,7 +103,7 @@
  *
  * Returns null and sets `errno` on failure.
  */
-DIR* fdopendir(int __dir_fd);
+DIR* _Nullable fdopendir(int __dir_fd);
 
 /**
  * [readdir(3)](http://man7.org/linux/man-pages/man3/readdir.3.html)
@@ -113,7 +113,7 @@
  * or returns null and leaves `errno` unchanged at the end of the directory,
  * or returns null and sets `errno` on failure.
  */
-struct dirent* readdir(DIR* __dir);
+struct dirent* _Nullable readdir(DIR* _Nonnull __dir);
 
 /**
  * [readdir64(3)](http://man7.org/linux/man-pages/man3/readdir.3.html)
@@ -123,10 +123,10 @@
  * or returns null and leaves `errno` unchanged at the end of the directory,
  * or returns null and sets `errno` on failure.
  */
-struct dirent64* readdir64(DIR* __dir) __INTRODUCED_IN(21);
+struct dirent64* _Nullable readdir64(DIR* _Nonnull __dir) __INTRODUCED_IN(21);
 
-int readdir_r(DIR* __dir, struct dirent* __entry, struct dirent** __buffer) __attribute__((__deprecated__("readdir_r is deprecated; use readdir instead")));
-int readdir64_r(DIR* __dir, struct dirent64* __entry, struct dirent64** __buffer) __INTRODUCED_IN(21) __attribute__((__deprecated__("readdir64_r is deprecated; use readdir64 instead")));
+int readdir_r(DIR* _Nonnull __dir, struct dirent* _Nonnull __entry, struct dirent* _Nullable * _Nonnull __buffer) __attribute__((__deprecated__("readdir_r is deprecated; use readdir instead")));
+int readdir64_r(DIR* _Nonnull __dir, struct dirent64* _Nonnull __entry, struct dirent64* _Nullable * _Nonnull __buffer) __INTRODUCED_IN(21) __attribute__((__deprecated__("readdir64_r is deprecated; use readdir64 instead")));
 
 /**
  * [closedir(3)](http://man7.org/linux/man-pages/man3/closedir.3.html)
@@ -134,13 +134,13 @@
  *
  * Returns 0 on success and returns -1 and sets `errno` on failure.
  */
-int closedir(DIR* __dir);
+int closedir(DIR* _Nonnull __dir);
 
 /**
  * [rewinddir(3)](http://man7.org/linux/man-pages/man3/rewinddir.3.html)
  * rewinds a directory stream to the first entry.
  */
-void rewinddir(DIR* __dir);
+void rewinddir(DIR* _Nonnull __dir);
 
 /**
  * [seekdir(3)](http://man7.org/linux/man-pages/man3/seekdir.3.html)
@@ -149,7 +149,7 @@
  *
  * Available since API level 23.
  */
-void seekdir(DIR* __dir, long __location) __INTRODUCED_IN(23);
+void seekdir(DIR* _Nonnull __dir, long __location) __INTRODUCED_IN(23);
 
 /**
  * [telldir(3)](http://man7.org/linux/man-pages/man3/telldir.3.html)
@@ -160,7 +160,7 @@
  *
  * Available since API level 23.
  */
-long telldir(DIR* __dir) __INTRODUCED_IN(23);
+long telldir(DIR* _Nonnull __dir) __INTRODUCED_IN(23);
 
 /**
  * [dirfd(3)](http://man7.org/linux/man-pages/man3/dirfd.3.html)
@@ -168,13 +168,13 @@
  *
  * Returns a file descriptor on success and returns -1 and sets `errno` on failure.
  */
-int dirfd(DIR* __dir);
+int dirfd(DIR* _Nonnull __dir);
 
 /**
  * [alphasort](http://man7.org/linux/man-pages/man3/alphasort.3.html) is a
  * comparator for use with scandir() that uses strcoll().
  */
-int alphasort(const struct dirent** __lhs, const struct dirent** __rhs);
+int alphasort(const struct dirent* _Nonnull * _Nonnull __lhs, const struct dirent* _Nonnull * _Nonnull __rhs);
 
 /**
  * [alphasort64](http://man7.org/linux/man-pages/man3/alphasort.3.html) is a
@@ -182,31 +182,33 @@
  *
  * Available since API level 21.
  */
-int alphasort64(const struct dirent64** __lhs, const struct dirent64** __rhs) __INTRODUCED_IN(21);
+int alphasort64(const struct dirent64* _Nonnull * _Nonnull __lhs, const struct dirent64* _Nonnull * _Nonnull __rhs) __INTRODUCED_IN(21);
 
 /**
  * [scandir(3)](http://man7.org/linux/man-pages/man3/scandir.3.html)
  * scans all the directory `__path`, filtering entries with `__filter` and
  * sorting them with qsort() using the given `__comparator`, and storing them
  * into `__name_list`. Passing NULL as the filter accepts all entries.
+ * Passing NULL as the comparator skips sorting.
  *
  * Returns the number of entries returned in the list on success,
  * and returns -1 and sets `errno` on failure.
  */
-int scandir(const char* __path, struct dirent*** __name_list, int (*__filter)(const struct dirent*), int (*__comparator)(const struct dirent**, const struct dirent**));
+int scandir(const char* _Nonnull __path, struct dirent* _Nonnull * _Nonnull * _Nonnull __name_list, int (* _Nullable __filter)(const struct dirent* _Nonnull), int (* _Nullable __comparator)(const struct dirent* _Nonnull * _Nonnull, const struct dirent* _Nonnull * _Nonnull));
 
 /**
  * [scandir64(3)](http://man7.org/linux/man-pages/man3/scandir.3.html)
  * scans all the directory `__path`, filtering entries with `__filter` and
  * sorting them with qsort() using the given `__comparator`, and storing them
  * into `__name_list`. Passing NULL as the filter accepts all entries.
+ * Passing NULL as the comparator skips sorting.
  *
  * Returns the number of entries returned in the list on success,
  * and returns -1 and sets `errno` on failure.
  *
  * Available since API level 21.
  */
-int scandir64(const char* __path, struct dirent64*** __name_list, int (*__filter)(const struct dirent64*), int (*__comparator)(const struct dirent64**, const struct dirent64**)) __INTRODUCED_IN(21);
+int scandir64(const char* _Nonnull __path, struct dirent64* _Nonnull * _Nonnull * _Nonnull __name_list, int (* _Nullable __filter)(const struct dirent64* _Nonnull), int (* _Nullable __comparator)(const struct dirent64* _Nonnull * _Nonnull, const struct dirent64* _Nonnull * _Nonnull)) __INTRODUCED_IN(21);
 
 #if defined(__USE_GNU)
 
@@ -216,13 +218,14 @@
  * filtering entries with `__filter` and sorting them with qsort() using the
  * given `__comparator`, and storing them into `__name_list`. Passing NULL as
  * the filter accepts all entries.
+ * Passing NULL as the comparator skips sorting.
  *
  * Returns the number of entries returned in the list on success,
  * and returns -1 and sets `errno` on failure.
  *
  * Available since API level 24.
  */
-int scandirat64(int __dir_fd, const char* __path, struct dirent64*** __name_list, int (*__filter)(const struct dirent64*), int (*__comparator)(const struct dirent64**, const struct dirent64**)) __INTRODUCED_IN(24);
+int scandirat64(int __dir_fd, const char* _Nonnull __path, struct dirent64* _Nonnull * _Nonnull * _Nonnull __name_list, int (* _Nullable __filter)(const struct dirent64* _Nonnull), int (* _Nullable __comparator)(const struct dirent64* _Nonnull * _Nonnull, const struct dirent64* _Nonnull * _Nonnull)) __INTRODUCED_IN(24);
 
 /**
  * [scandirat(3)](http://man7.org/linux/man-pages/man3/scandirat.3.html)
@@ -230,13 +233,14 @@
  * filtering entries with `__filter` and sorting them with qsort() using the
  * given `__comparator`, and storing them into `__name_list`. Passing NULL as
  * the filter accepts all entries.
+ * Passing NULL as the comparator skips sorting.
  *
  * Returns the number of entries returned in the list on success,
  * and returns -1 and sets `errno` on failure.
  *
  * Available since API level 24.
  */
-int scandirat(int __dir_fd, const char* __path, struct dirent*** __name_list, int (*__filter)(const struct dirent*), int (*__comparator)(const struct dirent**, const struct dirent**)) __INTRODUCED_IN(24);
+int scandirat(int __dir_fd, const char* _Nonnull __path, struct dirent* _Nonnull * _Nonnull * _Nonnull __name_list, int (* _Nullable __filter)(const struct dirent* _Nonnull), int (* _Nullable __comparator)(const struct dirent* _Nonnull * _Nonnull, const struct dirent* _Nonnull * _Nonnull)) __INTRODUCED_IN(24);
 
 #endif
 
diff --git a/libc/include/fts.h b/libc/include/fts.h
index 7e63111..bae2615 100644
--- a/libc/include/fts.h
+++ b/libc/include/fts.h
@@ -39,15 +39,15 @@
 #include <sys/types.h>
 
 typedef struct {
-	struct _ftsent *fts_cur;	/* current node */
-	struct _ftsent *fts_child;	/* linked list of children */
-	struct _ftsent **fts_array;	/* sort array */
+	struct _ftsent * _Nullable fts_cur;	/* current node */
+	struct _ftsent * _Nullable fts_child;	/* linked list of children */
+	struct _ftsent * _Nullable * _Nullable fts_array;	/* sort array */
 	dev_t fts_dev;			/* starting device # */
-	char *fts_path;			/* path for this descent */
+	char * _Nullable fts_path;			/* path for this descent */
 	int fts_rfd;			/* fd for root */
 	size_t fts_pathlen;		/* sizeof(path) */
 	int fts_nitems;			/* elements in the sort array */
-	int (*fts_compar)();		/* compare function */
+	int (* _Nullable fts_compar)();		/* compare function */
 
 #define	FTS_COMFOLLOW	0x0001		/* follow command line symlinks */
 #define	FTS_LOGICAL	0x0002		/* logical walk */
@@ -65,13 +65,13 @@
 } FTS;
 
 typedef struct _ftsent {
-	struct _ftsent *fts_cycle;	/* cycle node */
-	struct _ftsent *fts_parent;	/* parent directory */
-	struct _ftsent *fts_link;	/* next file in directory */
+	struct _ftsent * _Nullable fts_cycle;	/* cycle node */
+	struct _ftsent * _Nullable fts_parent;	/* parent directory */
+	struct _ftsent * _Nullable fts_link;	/* next file in directory */
 	long fts_number;	        /* local numeric value */
-	void *fts_pointer;	        /* local address value */
-	char *fts_accpath;		/* access path */
-	char *fts_path;			/* root path */
+	void * _Nullable fts_pointer;	        /* local address value */
+	char * _Nullable fts_accpath;		/* access path */
+	char * _Nullable fts_path;			/* root path */
 	int fts_errno;			/* errno for this node */
 	int fts_symfd;			/* fd for symlink */
 	size_t fts_pathlen;		/* strlen(fts_path) */
@@ -111,7 +111,7 @@
 #define	FTS_SKIP	 4		/* discard node */
 	unsigned short fts_instr;	/* fts_set() instructions */
 
-	struct stat *fts_statp;		/* stat(2) information */
+	struct stat * _Nullable fts_statp;		/* stat(2) information */
 	char fts_name[1];		/* file name */
 } FTSENT;
 
@@ -122,11 +122,11 @@
  * breakage in 21 that means you can't write code that runs on current devices and pre-21 devices,
  * so we break the tie in favor of current and future devices.
  */
-FTSENT* fts_children(FTS* __fts, int __options) __INTRODUCED_IN(21);
-int fts_close(FTS* __fts) __INTRODUCED_IN(21);
-FTS* fts_open(char* const* __path, int __options, int (*__comparator)(const FTSENT** __lhs, const FTSENT** __rhs)) __INTRODUCED_IN(21);
-FTSENT* fts_read(FTS* __fts) __INTRODUCED_IN(21);
-int fts_set(FTS* __fts, FTSENT* __entry, int __options) __INTRODUCED_IN(21);
+FTSENT* _Nullable fts_children(FTS* _Nonnull __fts, int __options) __INTRODUCED_IN(21);
+int fts_close(FTS* _Nonnull __fts) __INTRODUCED_IN(21);
+FTS* _Nullable fts_open(char* _Nonnull const* _Nonnull __path, int __options, int (* _Nullable __comparator)(const FTSENT* _Nonnull * _Nonnull  __lhs, const FTSENT* _Nonnull * _Nonnull __rhs)) __INTRODUCED_IN(21);
+FTSENT* _Nullable fts_read(FTS* _Nonnull __fts) __INTRODUCED_IN(21);
+int fts_set(FTS* _Nonnull __fts, FTSENT* _Nonnull __entry, int __options) __INTRODUCED_IN(21);
 
 __END_DECLS
 
diff --git a/libc/include/link.h b/libc/include/link.h
index bd430f5..a0a3d60 100644
--- a/libc/include/link.h
+++ b/libc/include/link.h
@@ -44,41 +44,41 @@
 
 struct dl_phdr_info {
   ElfW(Addr) dlpi_addr;
-  const char* dlpi_name;
-  const ElfW(Phdr)* dlpi_phdr;
+  const char* _Nullable dlpi_name;
+  const ElfW(Phdr)* _Nullable dlpi_phdr;
   ElfW(Half) dlpi_phnum;
 
   // These fields were added in Android R.
   unsigned long long dlpi_adds;
   unsigned long long dlpi_subs;
   size_t dlpi_tls_modid;
-  void* dlpi_tls_data;
+  void* _Nullable dlpi_tls_data;
 };
 
 #if defined(__arm__)
-int dl_iterate_phdr(int (*__callback)(struct dl_phdr_info*, size_t, void*), void* __data) __INTRODUCED_IN(21);
+int dl_iterate_phdr(int (* _Nonnull __callback)(struct dl_phdr_info* _Nonnull, size_t, void* _Nullable), void* _Nullable __data) __INTRODUCED_IN(21);
 #else
-int dl_iterate_phdr(int (*__callback)(struct dl_phdr_info*, size_t, void*), void* __data);
+int dl_iterate_phdr(int (* _Nonnull __callback)(struct dl_phdr_info* _Nonnull, size_t, void*_Nullable ), void* _Nullable __data);
 #endif
 
 #ifdef __arm__
 typedef uintptr_t _Unwind_Ptr;
-_Unwind_Ptr dl_unwind_find_exidx(_Unwind_Ptr, int*);
+_Unwind_Ptr dl_unwind_find_exidx(_Unwind_Ptr, int* _Nonnull);
 #endif
 
 /* Used by the dynamic linker to communicate with the debugger. */
 struct link_map {
   ElfW(Addr) l_addr;
-  char* l_name;
-  ElfW(Dyn)* l_ld;
-  struct link_map* l_next;
-  struct link_map* l_prev;
+  char* _Nullable l_name;
+  ElfW(Dyn)* _Nullable l_ld;
+  struct link_map* _Nullable l_next;
+  struct link_map* _Nullable l_prev;
 };
 
 /* Used by the dynamic linker to communicate with the debugger. */
 struct r_debug {
   int32_t r_version;
-  struct link_map* r_map;
+  struct link_map* _Nullable r_map;
   ElfW(Addr) r_brk;
   enum {
     RT_CONSISTENT,
diff --git a/libc/include/malloc.h b/libc/include/malloc.h
index 02bda60..91d63b3 100644
--- a/libc/include/malloc.h
+++ b/libc/include/malloc.h
@@ -183,7 +183,15 @@
  * Available since API level 28.
  */
 #define M_PURGE (-101)
-
+/**
+ * mallopt() option to immediately purge all possible memory back to
+ * the kernel. This call can take longer than a normal purge since it
+ * examines everything. In some cases, it can take more than twice the
+ * time of a M_PURGE call. The value is ignored.
+ *
+ * Available since API level 34.
+ */
+#define M_PURGE_ALL (-104)
 
 /**
  * mallopt() option to tune the allocator's choice of memory tags to
@@ -224,8 +232,9 @@
 /**
  * mallopt() option for per-thread memory initialization tuning.
  * The value argument should be one of:
- * 1: Disable automatic heap initialization and, where possible, memory tagging,
- *    on this thread.
+ * 1: Disable automatic heap initialization on this thread only.
+ *    If memory tagging is enabled, disable as much as possible of the
+ *    memory tagging initialization for this thread.
  * 0: Normal behavior.
  *
  * Available since API level 31.
diff --git a/libc/include/net/if.h b/libc/include/net/if.h
index f261f71..79b4195 100644
--- a/libc/include/net/if.h
+++ b/libc/include/net/if.h
@@ -41,13 +41,13 @@
 
 struct if_nameindex {
   unsigned if_index;
-  char* if_name;
+  char* _Nullable if_name;
 };
 
-char* if_indextoname(unsigned __index, char* __buf);
-unsigned if_nametoindex(const char* __name);
-struct if_nameindex* if_nameindex(void) __INTRODUCED_IN(24);
-void if_freenameindex(struct if_nameindex* __ptr) __INTRODUCED_IN(24);
+char* _Nullable if_indextoname(unsigned __index, char* _Nonnull __buf);
+unsigned if_nametoindex(const char* _Nonnull __name);
+struct if_nameindex* _Nullable if_nameindex(void) __INTRODUCED_IN(24);
+void if_freenameindex(struct if_nameindex* _Nullable __ptr) __INTRODUCED_IN(24);
 
 __END_DECLS
 
diff --git a/libc/include/netdb.h b/libc/include/netdb.h
index 7a1987e..7afdc1a 100644
--- a/libc/include/netdb.h
+++ b/libc/include/netdb.h
@@ -79,31 +79,31 @@
  * use in system calls).
  */
 struct hostent {
-	char	*h_name;	/* official name of host */
-	char	**h_aliases;	/* alias list */
+	char	* _Nullable h_name;	/* official name of host */
+	char	* _Nullable * _Nullable h_aliases;	/* alias list */
 	int	h_addrtype;	/* host address type */
 	int	h_length;	/* length of address */
-	char	**h_addr_list;	/* list of addresses from name server */
+	char	* _Nullable * _Nullable h_addr_list;	/* list of addresses from name server */
 #define	h_addr	h_addr_list[0]	/* address, for backward compatibility */
 };
 
 struct netent {
-	char		*n_name;	/* official name of net */
-	char		**n_aliases;	/* alias list */
+	char		* _Nullable n_name;	/* official name of net */
+	char		* _Nullable * _Nullable n_aliases;	/* alias list */
 	int		n_addrtype;	/* net address type */
 	uint32_t	n_net;		/* network # */
 };
 
 struct servent {
-	char	*s_name;	/* official service name */
-	char	**s_aliases;	/* alias list */
+	char	* _Nullable s_name;	/* official service name */
+	char	* _Nullable * _Nullable s_aliases;	/* alias list */
 	int	s_port;		/* port # */
-	char	*s_proto;	/* protocol to use */
+	char	* _Nullable s_proto;	/* protocol to use */
 };
 
 struct protoent {
-	char	*p_name;	/* official protocol name */
-	char	**p_aliases;	/* alias list */
+	char	* _Nullable p_name;	/* official protocol name */
+	char	* _Nullable * _Nullable p_aliases;	/* alias list */
 	int	p_proto;	/* protocol # */
 };
 
@@ -113,9 +113,9 @@
 	int	ai_socktype;	/* SOCK_xxx */
 	int	ai_protocol;	/* 0 or IPPROTO_xxx for IPv4 and IPv6 */
 	socklen_t ai_addrlen;	/* length of ai_addr */
-	char	*ai_canonname;	/* canonical name for hostname */
-	struct	sockaddr *ai_addr;	/* binary address */
-	struct	addrinfo *ai_next;	/* next structure in linked list */
+	char	* _Nullable ai_canonname;	/* canonical name for hostname */
+	struct	sockaddr * _Nullable ai_addr;	/* binary address */
+	struct	addrinfo * _Nullable ai_next;	/* next structure in linked list */
 };
 
 /*
@@ -196,47 +196,47 @@
 
 __BEGIN_DECLS
 
-int getaddrinfo(const char* __node, const char* __service, const struct addrinfo* __hints, struct addrinfo** __result);
-void freeaddrinfo(struct addrinfo* __ptr);
+int getaddrinfo(const char* _Nullable __node, const char* _Nullable __service, const struct addrinfo* _Nullable __hints, struct addrinfo* _Nullable * _Nonnull __result);
+void freeaddrinfo(struct addrinfo* _Nullable __ptr);
 
 /* Android ABI error: POSIX getnameinfo(3) uses socklen_t rather than size_t. */
-int getnameinfo(const struct sockaddr* __sa, socklen_t __sa_length, char* __host, size_t __host_length, char* __service, size_t __service_length, int __flags);
-const char* gai_strerror(int __error);
+int getnameinfo(const struct sockaddr* _Nonnull __sa, socklen_t __sa_length, char* _Nullable __host, size_t __host_length, char* _Nullable __service, size_t __service_length, int __flags);
+const char* _Nonnull gai_strerror(int __error);
 
 /* These functions are obsolete. Use getaddrinfo/getnameinfo instead. */
 #define h_errno (*__get_h_errno())
-int* __get_h_errno(void);
-void herror(const char* __s);
-const char* hstrerror(int __error);
-struct hostent* gethostbyaddr(const void* __addr, socklen_t __length, int __type);
-int gethostbyaddr_r(const void* __addr, socklen_t __length, int __type, struct hostent* __ret, char* __buf, size_t __buf_size, struct hostent** __result, int* __h_errno_ptr) __INTRODUCED_IN(23);
-struct hostent* gethostbyname(const char* __name);
-int gethostbyname_r(const char* __name, struct hostent* __ret, char* __buf, size_t __buf_size, struct hostent** __result, int* __h_errno_ptr);
-struct hostent* gethostbyname2(const char* __name, int __af);
-int gethostbyname2_r(const char* __name, int __af, struct hostent* __ret, char* __buf, size_t __buf_size, struct hostent** __result, int* __h_errno_ptr) __INTRODUCED_IN(23);
+int* _Nonnull __get_h_errno(void);
+void herror(const char* _Nonnull __s);
+const char* _Nonnull hstrerror(int __error);
+struct hostent* _Nullable gethostbyaddr(const void* _Nonnull __addr, socklen_t __length, int __type);
+int gethostbyaddr_r(const void* _Nonnull __addr, socklen_t __length, int __type, struct hostent* _Nonnull __ret, char* _Nonnull __buf, size_t __buf_size, struct hostent* _Nullable * _Nonnull __result, int* _Nonnull __h_errno_ptr) __INTRODUCED_IN(23);
+struct hostent* _Nullable gethostbyname(const char* _Nonnull __name);
+int gethostbyname_r(const char* _Nonnull __name, struct hostent* _Nonnull __ret, char* _Nonnull __buf, size_t __buf_size, struct hostent* _Nullable * _Nonnull __result, int* _Nonnull __h_errno_ptr);
+struct hostent* _Nullable gethostbyname2(const char* _Nonnull __name, int __af);
+int gethostbyname2_r(const char* _Nonnull __name, int __af, struct hostent* _Nonnull __ret, char* _Nonnull __buf, size_t __buf_size, struct hostent* _Nullable * _Nonnull __result, int* _Nonnull __h_errno_ptr) __INTRODUCED_IN(23);
 void endhostent(void) __INTRODUCED_IN(28);
-struct hostent* gethostent(void);
+struct hostent* _Nullable gethostent(void);
 void sethostent(int __stay_open) __INTRODUCED_IN(28);
 
 /* These functions are obsolete. None of these functions return anything but nullptr. */
 void endnetent(void) __INTRODUCED_IN(28);
-struct netent* getnetbyaddr(uint32_t __net, int __type);
-struct netent* getnetbyname(const char* __name);
-struct netent* getnetent(void) __INTRODUCED_IN(28);
+struct netent* _Nullable getnetbyaddr(uint32_t __net, int __type);
+struct netent* _Nullable getnetbyname(const char* _Nonnull __name);
+struct netent* _Nullable getnetent(void) __INTRODUCED_IN(28);
 void setnetent(int __stay_open) __INTRODUCED_IN(28);
 
 /* None of these functions return anything but nullptr. */
 void endprotoent(void) __INTRODUCED_IN(28);
-struct protoent* getprotobyname(const char* __name);
-struct protoent* getprotobynumber(int __proto);
-struct protoent* getprotoent(void) __INTRODUCED_IN(28);
+struct protoent* _Nullable getprotobyname(const char* _Nonnull __name);
+struct protoent* _Nullable getprotobynumber(int __proto);
+struct protoent* _Nullable getprotoent(void) __INTRODUCED_IN(28);
 void setprotoent(int __stay_open) __INTRODUCED_IN(28);
 
 /* These functions return entries from a built-in database. */
 void endservent(void);
-struct servent* getservbyname(const char* __name, const char* __proto);
-struct servent* getservbyport(int __port_in_network_order, const char* __proto);
-struct servent* getservent(void);
+struct servent* _Nullable getservbyname(const char* _Nonnull __name, const char* _Nullable __proto);
+struct servent* _Nullable getservbyport(int __port_in_network_order, const char* _Nullable __proto);
+struct servent* _Nullable getservent(void);
 void setservent(int __stay_open);
 
 __END_DECLS
diff --git a/libc/include/netinet/ether.h b/libc/include/netinet/ether.h
index 480063d..d570c18 100644
--- a/libc/include/netinet/ether.h
+++ b/libc/include/netinet/ether.h
@@ -44,7 +44,7 @@
  *
  * Returns a pointer to a static buffer.
  */
-char* ether_ntoa(const struct ether_addr* __addr);
+char* _Nonnull ether_ntoa(const struct ether_addr* _Nonnull __addr);
 
 /**
  * [ether_ntoa_r(3)](http://man7.org/linux/man-pages/man3/ether_ntoa_r.3.html) returns a string
@@ -52,7 +52,7 @@
  *
  * Returns a pointer to the given buffer.
  */
-char* ether_ntoa_r(const struct ether_addr* __addr, char* __buf);
+char* _Nonnull ether_ntoa_r(const struct ether_addr* _Nonnull __addr, char* _Nonnull __buf);
 
 /**
  * [ether_aton(3)](http://man7.org/linux/man-pages/man3/ether_aton.3.html) returns an `ether_addr`
@@ -60,7 +60,7 @@
  *
  * Returns a pointer to a static buffer, or NULL if the given string isn't a valid MAC address.
  */
-struct ether_addr* ether_aton(const char* __ascii);
+struct ether_addr* _Nullable ether_aton(const char* _Nonnull __ascii);
 
 /**
  * [ether_aton_r(3)](http://man7.org/linux/man-pages/man3/ether_aton_r.3.html) returns an
@@ -68,6 +68,6 @@
  *
  * Returns a pointer to the given buffer, or NULL if the given string isn't a valid MAC address.
  */
-struct ether_addr* ether_aton_r(const char* __ascii, struct ether_addr* __addr);
+struct ether_addr* _Nullable ether_aton_r(const char* _Nonnull __ascii, struct ether_addr* _Nonnull __addr);
 
 __END_DECLS
diff --git a/libc/include/netinet/in.h b/libc/include/netinet/in.h
index 46e3543..b235e6e 100644
--- a/libc/include/netinet/in.h
+++ b/libc/include/netinet/in.h
@@ -54,7 +54,7 @@
 
 typedef uint16_t in_port_t;
 
-int bindresvport(int __fd, struct sockaddr_in* __sin);
+int bindresvport(int __fd, struct sockaddr_in* _Nullable __sin);
 
 #if __ANDROID_API__ >= 24
 extern const struct in6_addr in6addr_any __INTRODUCED_IN(24);
diff --git a/libc/include/pthread.h b/libc/include/pthread.h
index fd1ebc3..98695eb 100644
--- a/libc/include/pthread.h
+++ b/libc/include/pthread.h
@@ -94,41 +94,41 @@
 #define PTHREAD_SCOPE_SYSTEM 0
 #define PTHREAD_SCOPE_PROCESS 1
 
-int pthread_atfork(void (*__prepare)(void), void (*__parent)(void), void (*__child)(void));
+int pthread_atfork(void (* _Nullable __prepare)(void), void (* _Nullable __parent)(void), void (* _Nullable __child)(void));
 
-int pthread_attr_destroy(pthread_attr_t* __attr);
-int pthread_attr_getdetachstate(const pthread_attr_t* __attr, int* __state);
-int pthread_attr_getguardsize(const pthread_attr_t* __attr, size_t* __size);
-int pthread_attr_getinheritsched(const pthread_attr_t* __attr, int* __flag) __INTRODUCED_IN(28);
-int pthread_attr_getschedparam(const pthread_attr_t* __attr, struct sched_param* __param);
-int pthread_attr_getschedpolicy(const pthread_attr_t* __attr, int* __policy);
-int pthread_attr_getscope(const pthread_attr_t* __attr, int* __scope);
-int pthread_attr_getstack(const pthread_attr_t* __attr, void** __addr, size_t* __size);
-int pthread_attr_getstacksize(const pthread_attr_t* __attr, size_t* __size);
-int pthread_attr_init(pthread_attr_t* __attr);
-int pthread_attr_setdetachstate(pthread_attr_t* __attr, int __state);
-int pthread_attr_setguardsize(pthread_attr_t* __attr, size_t __size);
-int pthread_attr_setinheritsched(pthread_attr_t* __attr, int __flag) __INTRODUCED_IN(28);
-int pthread_attr_setschedparam(pthread_attr_t* __attr, const struct sched_param* __param);
-int pthread_attr_setschedpolicy(pthread_attr_t* __attr, int __policy);
-int pthread_attr_setscope(pthread_attr_t* __attr, int __scope);
-int pthread_attr_setstack(pthread_attr_t* __attr, void* __addr, size_t __size);
-int pthread_attr_setstacksize(pthread_attr_t* __addr, size_t __size);
+int pthread_attr_destroy(pthread_attr_t* _Nonnull __attr);
+int pthread_attr_getdetachstate(const pthread_attr_t* _Nonnull __attr, int* _Nonnull __state);
+int pthread_attr_getguardsize(const pthread_attr_t* _Nonnull __attr, size_t* _Nonnull __size);
+int pthread_attr_getinheritsched(const pthread_attr_t* _Nonnull __attr, int* _Nonnull __flag) __INTRODUCED_IN(28);
+int pthread_attr_getschedparam(const pthread_attr_t* _Nonnull __attr, struct sched_param* _Nonnull __param);
+int pthread_attr_getschedpolicy(const pthread_attr_t* _Nonnull __attr, int* _Nonnull __policy);
+int pthread_attr_getscope(const pthread_attr_t* _Nonnull __attr, int* _Nonnull __scope);
+int pthread_attr_getstack(const pthread_attr_t* _Nonnull __attr, void* _Nullable * _Nonnull __addr, size_t* _Nonnull __size);
+int pthread_attr_getstacksize(const pthread_attr_t* _Nonnull __attr, size_t* _Nonnull __size);
+int pthread_attr_init(pthread_attr_t* _Nonnull __attr);
+int pthread_attr_setdetachstate(pthread_attr_t* _Nonnull __attr, int __state);
+int pthread_attr_setguardsize(pthread_attr_t* _Nonnull __attr, size_t __size);
+int pthread_attr_setinheritsched(pthread_attr_t* _Nonnull __attr, int __flag) __INTRODUCED_IN(28);
+int pthread_attr_setschedparam(pthread_attr_t* _Nonnull __attr, const struct sched_param* _Nonnull __param);
+int pthread_attr_setschedpolicy(pthread_attr_t* _Nonnull __attr, int __policy);
+int pthread_attr_setscope(pthread_attr_t* _Nonnull __attr, int __scope);
+int pthread_attr_setstack(pthread_attr_t* _Nonnull __attr, void* _Nonnull __addr, size_t __size);
+int pthread_attr_setstacksize(pthread_attr_t* _Nonnull __addr, size_t __size);
 
-int pthread_condattr_destroy(pthread_condattr_t* __attr);
-int pthread_condattr_getclock(const pthread_condattr_t* __attr, clockid_t* __clock) __INTRODUCED_IN(21);
-int pthread_condattr_getpshared(const pthread_condattr_t* __attr, int* __shared);
-int pthread_condattr_init(pthread_condattr_t* __attr);
-int pthread_condattr_setclock(pthread_condattr_t* __attr, clockid_t __clock) __INTRODUCED_IN(21);
-int pthread_condattr_setpshared(pthread_condattr_t* __attr, int __shared);
+int pthread_condattr_destroy(pthread_condattr_t* _Nonnull __attr);
+int pthread_condattr_getclock(const pthread_condattr_t* _Nonnull __attr, clockid_t* _Nonnull __clock) __INTRODUCED_IN(21);
+int pthread_condattr_getpshared(const pthread_condattr_t* _Nonnull __attr, int* _Nonnull __shared);
+int pthread_condattr_init(pthread_condattr_t* _Nonnull __attr);
+int pthread_condattr_setclock(pthread_condattr_t* _Nonnull __attr, clockid_t __clock) __INTRODUCED_IN(21);
+int pthread_condattr_setpshared(pthread_condattr_t* _Nonnull __attr, int __shared);
 
-int pthread_cond_broadcast(pthread_cond_t* __cond);
-int pthread_cond_clockwait(pthread_cond_t* __cond, pthread_mutex_t* __mutex, clockid_t __clock,
-                           const struct timespec* __timeout) __INTRODUCED_IN(30);
-int pthread_cond_destroy(pthread_cond_t* __cond);
-int pthread_cond_init(pthread_cond_t* __cond, const pthread_condattr_t* __attr);
-int pthread_cond_signal(pthread_cond_t* __cond);
-int pthread_cond_timedwait(pthread_cond_t* __cond, pthread_mutex_t* __mutex, const struct timespec* __timeout);
+int pthread_cond_broadcast(pthread_cond_t* _Nonnull __cond);
+int pthread_cond_clockwait(pthread_cond_t* _Nonnull __cond, pthread_mutex_t* _Nonnull __mutex, clockid_t __clock,
+                           const struct timespec* _Nullable __timeout) __INTRODUCED_IN(30);
+int pthread_cond_destroy(pthread_cond_t* _Nonnull __cond);
+int pthread_cond_init(pthread_cond_t* _Nonnull __cond, const pthread_condattr_t* _Nullable __attr);
+int pthread_cond_signal(pthread_cond_t* _Nonnull __cond);
+int pthread_cond_timedwait(pthread_cond_t* _Nonnull __cond, pthread_mutex_t* _Nonnull __mutex, const struct timespec* _Nullable __timeout);
 /*
  * Condition variables use CLOCK_REALTIME by default for their timeouts, however that is
  * typically inappropriate, since that clock can change dramatically, causing the timeout to
@@ -139,9 +139,9 @@
  * Note that pthread_cond_clockwait() allows specifying an arbitrary clock and has superseded this
  * function.
  */
-int pthread_cond_timedwait_monotonic_np(pthread_cond_t* __cond, pthread_mutex_t* __mutex,
-                                        const struct timespec* __timeout) __INTRODUCED_IN_64(28);
-int pthread_cond_wait(pthread_cond_t* __cond, pthread_mutex_t* __mutex);
+int pthread_cond_timedwait_monotonic_np(pthread_cond_t* _Nonnull __cond, pthread_mutex_t* _Nonnull __mutex,
+                                        const struct timespec* _Nullable __timeout) __INTRODUCED_IN_64(28);
+int pthread_cond_wait(pthread_cond_t* _Nonnull __cond, pthread_mutex_t* _Nonnull __mutex);
 
 #if defined(__clang__)
 /*
@@ -153,44 +153,44 @@
 #pragma clang diagnostic push
 #pragma clang diagnostic ignored "-Wbuiltin-requires-header"
 #endif
-int pthread_create(pthread_t* __pthread_ptr, pthread_attr_t const* __attr, void* (*__start_routine)(void*), void*);
+int pthread_create(pthread_t* _Nonnull __pthread_ptr, pthread_attr_t const* _Nullable __attr, void* _Nonnull (* _Nonnull __start_routine)(void* _Nonnull), void* _Nullable);
 #if defined(__clang__)
 #pragma clang diagnostic pop
 #endif
 
 int pthread_detach(pthread_t __pthread);
-void pthread_exit(void* __return_value) __noreturn;
+void pthread_exit(void* _Nullable __return_value) __noreturn;
 
 int pthread_equal(pthread_t __lhs, pthread_t __rhs);
 
-int pthread_getattr_np(pthread_t __pthread, pthread_attr_t* __attr);
+int pthread_getattr_np(pthread_t __pthread, pthread_attr_t* _Nonnull __attr);
 
-int pthread_getcpuclockid(pthread_t __pthread, clockid_t* __clock);
+int pthread_getcpuclockid(pthread_t __pthread, clockid_t* _Nonnull __clock);
 
-void* pthread_getspecific(pthread_key_t __key);
+void* _Nullable pthread_getspecific(pthread_key_t __key);
 
 pid_t pthread_gettid_np(pthread_t __pthread) __INTRODUCED_IN(21);
 
-int pthread_join(pthread_t __pthread, void** __return_value_ptr);
+int pthread_join(pthread_t __pthread, void* _Nullable * _Nullable __return_value_ptr);
 
-int pthread_key_create(pthread_key_t* __key_ptr, void (*__key_destructor)(void*));
+int pthread_key_create(pthread_key_t* _Nonnull __key_ptr, void (* _Nullable __key_destructor)(void* _Nullable));
 int pthread_key_delete(pthread_key_t __key);
 
-int pthread_mutexattr_destroy(pthread_mutexattr_t* __attr);
-int pthread_mutexattr_getpshared(const pthread_mutexattr_t* __attr, int* __shared);
-int pthread_mutexattr_gettype(const pthread_mutexattr_t* __attr, int* __type);
-int pthread_mutexattr_getprotocol(const pthread_mutexattr_t* __attr, int* __protocol) __INTRODUCED_IN(28);
-int pthread_mutexattr_init(pthread_mutexattr_t* __attr);
-int pthread_mutexattr_setpshared(pthread_mutexattr_t* __attr, int __shared);
-int pthread_mutexattr_settype(pthread_mutexattr_t* __attr, int __type);
-int pthread_mutexattr_setprotocol(pthread_mutexattr_t* __attr, int __protocol) __INTRODUCED_IN(28);
+int pthread_mutexattr_destroy(pthread_mutexattr_t* _Nonnull __attr);
+int pthread_mutexattr_getpshared(const pthread_mutexattr_t* _Nonnull __attr, int* _Nonnull __shared);
+int pthread_mutexattr_gettype(const pthread_mutexattr_t* _Nonnull __attr, int* _Nonnull __type);
+int pthread_mutexattr_getprotocol(const pthread_mutexattr_t* _Nonnull __attr, int* _Nonnull __protocol) __INTRODUCED_IN(28);
+int pthread_mutexattr_init(pthread_mutexattr_t* _Nonnull __attr);
+int pthread_mutexattr_setpshared(pthread_mutexattr_t* _Nonnull __attr, int __shared);
+int pthread_mutexattr_settype(pthread_mutexattr_t* _Nonnull __attr, int __type);
+int pthread_mutexattr_setprotocol(pthread_mutexattr_t* _Nonnull __attr, int __protocol) __INTRODUCED_IN(28);
 
-int pthread_mutex_clocklock(pthread_mutex_t* __mutex, clockid_t __clock,
-                            const struct timespec* __abstime) __INTRODUCED_IN(30);
-int pthread_mutex_destroy(pthread_mutex_t* __mutex);
-int pthread_mutex_init(pthread_mutex_t* __mutex, const pthread_mutexattr_t* __attr);
-int pthread_mutex_lock(pthread_mutex_t* __mutex);
-int pthread_mutex_timedlock(pthread_mutex_t* __mutex, const struct timespec* __timeout)
+int pthread_mutex_clocklock(pthread_mutex_t* _Nonnull __mutex, clockid_t __clock,
+                            const struct timespec* _Nullable __abstime) __INTRODUCED_IN(30);
+int pthread_mutex_destroy(pthread_mutex_t* _Nonnull __mutex);
+int pthread_mutex_init(pthread_mutex_t* _Nonnull __mutex, const pthread_mutexattr_t* _Nullable __attr);
+int pthread_mutex_lock(pthread_mutex_t* _Nonnull __mutex);
+int pthread_mutex_timedlock(pthread_mutex_t* _Nonnull __mutex, const struct timespec* _Nullable __timeout)
   __INTRODUCED_IN(21);
 
 /*
@@ -202,69 +202,69 @@
  * Note that pthread_mutex_clocklock() allows specifying an arbitrary clock and has superseded this
  * function.
  */
-int pthread_mutex_timedlock_monotonic_np(pthread_mutex_t* __mutex, const struct timespec* __timeout)
+int pthread_mutex_timedlock_monotonic_np(pthread_mutex_t* _Nonnull __mutex, const struct timespec* _Nullable __timeout)
     __INTRODUCED_IN(28);
-int pthread_mutex_trylock(pthread_mutex_t* __mutex);
-int pthread_mutex_unlock(pthread_mutex_t* __mutex);
+int pthread_mutex_trylock(pthread_mutex_t* _Nonnull __mutex);
+int pthread_mutex_unlock(pthread_mutex_t* _Nonnull __mutex);
 
-int pthread_once(pthread_once_t* __once, void (*__init_routine)(void));
+int pthread_once(pthread_once_t* _Nonnull __once, void (* _Nonnull __init_routine)(void));
 
-int pthread_rwlockattr_init(pthread_rwlockattr_t* __attr);
-int pthread_rwlockattr_destroy(pthread_rwlockattr_t* __attr);
-int pthread_rwlockattr_getpshared(const pthread_rwlockattr_t* __attr, int* __shared);
-int pthread_rwlockattr_setpshared(pthread_rwlockattr_t* __attr, int __shared);
-int pthread_rwlockattr_getkind_np(const pthread_rwlockattr_t* __attr, int* __kind)
+int pthread_rwlockattr_init(pthread_rwlockattr_t* _Nonnull __attr);
+int pthread_rwlockattr_destroy(pthread_rwlockattr_t* _Nonnull __attr);
+int pthread_rwlockattr_getpshared(const pthread_rwlockattr_t* _Nonnull __attr, int* _Nonnull __shared);
+int pthread_rwlockattr_setpshared(pthread_rwlockattr_t* _Nonnull __attr, int __shared);
+int pthread_rwlockattr_getkind_np(const pthread_rwlockattr_t* _Nonnull __attr, int* _Nonnull __kind)
   __INTRODUCED_IN(23);
-int pthread_rwlockattr_setkind_np(pthread_rwlockattr_t* __attr, int __kind) __INTRODUCED_IN(23);
+int pthread_rwlockattr_setkind_np(pthread_rwlockattr_t* _Nonnull __attr, int __kind) __INTRODUCED_IN(23);
 
-int pthread_rwlock_clockrdlock(pthread_rwlock_t* __rwlock, clockid_t __clock,
-                               const struct timespec* __timeout) __INTRODUCED_IN(30);
-int pthread_rwlock_clockwrlock(pthread_rwlock_t* __rwlock, clockid_t __clock,
-                               const struct timespec* __timeout) __INTRODUCED_IN(30);
-int pthread_rwlock_destroy(pthread_rwlock_t* __rwlock);
-int pthread_rwlock_init(pthread_rwlock_t* __rwlock, const pthread_rwlockattr_t* __attr);
-int pthread_rwlock_rdlock(pthread_rwlock_t* __rwlock);
-int pthread_rwlock_timedrdlock(pthread_rwlock_t* __rwlock, const struct timespec* __timeout);
+int pthread_rwlock_clockrdlock(pthread_rwlock_t* _Nonnull __rwlock, clockid_t __clock,
+                               const struct timespec* _Nullable __timeout) __INTRODUCED_IN(30);
+int pthread_rwlock_clockwrlock(pthread_rwlock_t* _Nonnull __rwlock, clockid_t __clock,
+                               const struct timespec* _Nullable __timeout) __INTRODUCED_IN(30);
+int pthread_rwlock_destroy(pthread_rwlock_t* _Nonnull __rwlock);
+int pthread_rwlock_init(pthread_rwlock_t* _Nonnull __rwlock, const pthread_rwlockattr_t* _Nullable __attr);
+int pthread_rwlock_rdlock(pthread_rwlock_t* _Nonnull __rwlock);
+int pthread_rwlock_timedrdlock(pthread_rwlock_t* _Nonnull __rwlock, const struct timespec* _Nullable __timeout);
 /* See the comment on pthread_mutex_timedlock_monotonic_np for usage of this function. */
-int pthread_rwlock_timedrdlock_monotonic_np(pthread_rwlock_t* __rwlock,
-                                            const struct timespec* __timeout) __INTRODUCED_IN(28);
-int pthread_rwlock_timedwrlock(pthread_rwlock_t* __rwlock, const struct timespec* __timeout);
+int pthread_rwlock_timedrdlock_monotonic_np(pthread_rwlock_t* _Nonnull __rwlock,
+                                            const struct timespec* _Nullable __timeout) __INTRODUCED_IN(28);
+int pthread_rwlock_timedwrlock(pthread_rwlock_t* _Nonnull __rwlock, const struct timespec* _Nullable __timeout);
 /* See the comment on pthread_mutex_timedlock_monotonic_np for usage of this function. */
-int pthread_rwlock_timedwrlock_monotonic_np(pthread_rwlock_t* __rwlock,
-                                            const struct timespec* __timeout) __INTRODUCED_IN(28);
-int pthread_rwlock_tryrdlock(pthread_rwlock_t* __rwlock);
-int pthread_rwlock_trywrlock(pthread_rwlock_t* __rwlock);
-int pthread_rwlock_unlock(pthread_rwlock_t* __rwlock);
-int pthread_rwlock_wrlock(pthread_rwlock_t* __rwlock);
+int pthread_rwlock_timedwrlock_monotonic_np(pthread_rwlock_t* _Nonnull __rwlock,
+                                            const struct timespec* _Nullable __timeout) __INTRODUCED_IN(28);
+int pthread_rwlock_tryrdlock(pthread_rwlock_t* _Nonnull __rwlock);
+int pthread_rwlock_trywrlock(pthread_rwlock_t* _Nonnull __rwlock);
+int pthread_rwlock_unlock(pthread_rwlock_t* _Nonnull __rwlock);
+int pthread_rwlock_wrlock(pthread_rwlock_t* _Nonnull __rwlock);
 
 #if __ANDROID_API__ >= 24
-int pthread_barrierattr_init(pthread_barrierattr_t* __attr) __INTRODUCED_IN(24);
-int pthread_barrierattr_destroy(pthread_barrierattr_t* __attr) __INTRODUCED_IN(24);
-int pthread_barrierattr_getpshared(const pthread_barrierattr_t* __attr, int* __shared) __INTRODUCED_IN(24);
-int pthread_barrierattr_setpshared(pthread_barrierattr_t* __attr, int __shared) __INTRODUCED_IN(24);
+int pthread_barrierattr_init(pthread_barrierattr_t* _Nonnull __attr) __INTRODUCED_IN(24);
+int pthread_barrierattr_destroy(pthread_barrierattr_t* _Nonnull __attr) __INTRODUCED_IN(24);
+int pthread_barrierattr_getpshared(const pthread_barrierattr_t* _Nonnull __attr, int* _Nonnull __shared) __INTRODUCED_IN(24);
+int pthread_barrierattr_setpshared(pthread_barrierattr_t* _Nonnull __attr, int __shared) __INTRODUCED_IN(24);
 #endif
 
 #if __ANDROID_API__ >= 24
-int pthread_barrier_init(pthread_barrier_t* __barrier, const pthread_barrierattr_t* __attr, unsigned __count) __INTRODUCED_IN(24);
-int pthread_barrier_destroy(pthread_barrier_t* __barrier) __INTRODUCED_IN(24);
-int pthread_barrier_wait(pthread_barrier_t* __barrier) __INTRODUCED_IN(24);
+int pthread_barrier_init(pthread_barrier_t* _Nonnull __barrier, const pthread_barrierattr_t* _Nullable __attr, unsigned __count) __INTRODUCED_IN(24);
+int pthread_barrier_destroy(pthread_barrier_t* _Nonnull __barrier) __INTRODUCED_IN(24);
+int pthread_barrier_wait(pthread_barrier_t* _Nonnull __barrier) __INTRODUCED_IN(24);
 #endif
 
 #if __ANDROID_API__ >= 24
-int pthread_spin_destroy(pthread_spinlock_t* __spinlock) __INTRODUCED_IN(24);
-int pthread_spin_init(pthread_spinlock_t* __spinlock, int __shared) __INTRODUCED_IN(24);
-int pthread_spin_lock(pthread_spinlock_t* __spinlock) __INTRODUCED_IN(24);
-int pthread_spin_trylock(pthread_spinlock_t* __spinlock) __INTRODUCED_IN(24);
-int pthread_spin_unlock(pthread_spinlock_t* __spinlock) __INTRODUCED_IN(24);
+int pthread_spin_destroy(pthread_spinlock_t* _Nonnull __spinlock) __INTRODUCED_IN(24);
+int pthread_spin_init(pthread_spinlock_t* _Nonnull __spinlock, int __shared) __INTRODUCED_IN(24);
+int pthread_spin_lock(pthread_spinlock_t* _Nonnull __spinlock) __INTRODUCED_IN(24);
+int pthread_spin_trylock(pthread_spinlock_t* _Nonnull __spinlock) __INTRODUCED_IN(24);
+int pthread_spin_unlock(pthread_spinlock_t* _Nonnull __spinlock) __INTRODUCED_IN(24);
 #endif
 
 pthread_t pthread_self(void) __attribute_const__;
 
 #if defined(__USE_GNU)
-int pthread_getname_np(pthread_t __pthread, char* __buf, size_t __n) __INTRODUCED_IN(26);
+int pthread_getname_np(pthread_t __pthread, char* _Nonnull __buf, size_t __n) __INTRODUCED_IN(26);
 #endif
 /* TODO: this should be __USE_GNU too. */
-int pthread_setname_np(pthread_t __pthread, const char* __name);
+int pthread_setname_np(pthread_t __pthread, const char* _Nonnull __name);
 
 /**
  * [pthread_setschedparam(3)](https://man7.org/linux/man-pages/man3/pthread_setschedparam.3.html)
@@ -277,7 +277,7 @@
  *
  * Returns 0 on success and returns an error number on failure.
  */
-int pthread_setschedparam(pthread_t __pthread, int __policy, const struct sched_param* __param);
+int pthread_setschedparam(pthread_t __pthread, int __policy, const struct sched_param* _Nonnull __param);
 
 /**
  * [pthread_getschedparam(3)](https://man7.org/linux/man-pages/man3/pthread_getschedparam.3.html)
@@ -285,7 +285,7 @@
  *
  * Returns 0 on success and returns an error number on failure.
  */
-int pthread_getschedparam(pthread_t __pthread, int* __policy, struct sched_param* __param);
+int pthread_getschedparam(pthread_t __pthread, int* _Nonnull __policy, struct sched_param* _Nonnull __param);
 
 /**
  * [pthread_setschedprio(3)](https://man7.org/linux/man-pages/man3/pthread_setschedprio.3.html)
@@ -302,18 +302,18 @@
  */
 int pthread_setschedprio(pthread_t __pthread, int __priority) __INTRODUCED_IN(28);
 
-int pthread_setspecific(pthread_key_t __key, const void* __value);
+int pthread_setspecific(pthread_key_t __key, const void* _Nullable __value);
 
-typedef void (*__pthread_cleanup_func_t)(void*);
+typedef void (* _Nullable __pthread_cleanup_func_t)(void* _Nullable);
 
 typedef struct __pthread_cleanup_t {
-  struct __pthread_cleanup_t*   __cleanup_prev;
-  __pthread_cleanup_func_t      __cleanup_routine;
-  void*                         __cleanup_arg;
+  struct __pthread_cleanup_t*   _Nullable __cleanup_prev;
+  __pthread_cleanup_func_t      _Nullable __cleanup_routine;
+  void*                         _Nullable __cleanup_arg;
 } __pthread_cleanup_t;
 
-void __pthread_cleanup_push(__pthread_cleanup_t* c, __pthread_cleanup_func_t, void*);
-void __pthread_cleanup_pop(__pthread_cleanup_t*, int);
+void __pthread_cleanup_push(__pthread_cleanup_t* _Nonnull c, __pthread_cleanup_func_t _Nullable, void* _Nullable);
+void __pthread_cleanup_pop(__pthread_cleanup_t* _Nonnull, int);
 
 /* Believe or not, the definitions of pthread_cleanup_push and
  * pthread_cleanup_pop below are correct. Posix states that these
diff --git a/libc/include/pwd.h b/libc/include/pwd.h
index d481aac..2b17fbf 100644
--- a/libc/include/pwd.h
+++ b/libc/include/pwd.h
@@ -66,31 +66,31 @@
 __BEGIN_DECLS
 
 struct passwd {
-  char* pw_name;
-  char* pw_passwd;
+  char* _Nullable pw_name;
+  char* _Nullable pw_passwd;
   uid_t pw_uid;
   gid_t pw_gid;
 #ifdef __LP64__
-  char* pw_gecos;
+  char* _Nullable pw_gecos;
 #else
   /* Note: On LP32, we define pw_gecos to pw_passwd since they're both NULL. */
 # define pw_gecos pw_passwd
 #endif
-  char* pw_dir;
-  char* pw_shell;
+  char* _Nullable pw_dir;
+  char* _Nullable pw_shell;
 };
 
-struct passwd* getpwnam(const char* __name);
-struct passwd* getpwuid(uid_t __uid);
+struct passwd* _Nullable getpwnam(const char* _Nonnull __name);
+struct passwd* _Nullable getpwuid(uid_t __uid);
 
 /* Note: Android has thousands and thousands of ids to iterate through */
-struct passwd* getpwent(void) __INTRODUCED_IN(26);
+struct passwd* _Nullable getpwent(void) __INTRODUCED_IN(26);
 
 void setpwent(void) __INTRODUCED_IN(26);
 void endpwent(void) __INTRODUCED_IN(26);
 
-int getpwnam_r(const char* __name, struct passwd* __pwd, char* __buf, size_t __n, struct passwd** __result);
-int getpwuid_r(uid_t __uid, struct passwd* __pwd, char* __buf, size_t __n, struct passwd** __result);
+int getpwnam_r(const char* _Nonnull __name, struct passwd* _Nonnull __pwd, char* _Nonnull __buf, size_t __n, struct passwd* _Nullable * _Nonnull __result);
+int getpwuid_r(uid_t __uid, struct passwd* _Nonnull __pwd, char* _Nonnull __buf, size_t __n, struct passwd* _Nullable * _Nonnull __result);
 
 __END_DECLS
 
diff --git a/libc/include/sched.h b/libc/include/sched.h
index 364ca10..26bc742 100644
--- a/libc/include/sched.h
+++ b/libc/include/sched.h
@@ -104,7 +104,7 @@
  *
  * Returns 0 on success and returns -1 and sets `errno` on failure.
  */
-int sched_setscheduler(pid_t __pid, int __policy, const struct sched_param* __param);
+int sched_setscheduler(pid_t __pid, int __policy, const struct sched_param* _Nonnull __param);
 
 /**
  * [sched_getscheduler(2)](http://man7.org/linux/man-pages/man2/sched_getcpu.2.html)
@@ -145,7 +145,7 @@
  *
  * Returns 0 on success and returns -1 and sets `errno` on failure.
  */
-int sched_setparam(pid_t __pid, const struct sched_param* __param);
+int sched_setparam(pid_t __pid, const struct sched_param* _Nonnull __param);
 
 /**
  * [sched_getparam(2)](http://man7.org/linux/man-pages/man2/sched_getparam.2.html)
@@ -153,7 +153,7 @@
  *
  * Returns 0 on success and returns -1 and sets `errno` on failure.
  */
-int sched_getparam(pid_t __pid, struct sched_param* __param);
+int sched_getparam(pid_t __pid, struct sched_param* _Nonnull __param);
 
 /**
  * [sched_rr_get_interval(2)](http://man7.org/linux/man-pages/man2/sched_rr_get_interval.2.html)
@@ -161,7 +161,7 @@
  *
  * Returns 0 on success and returns -1 and sets `errno` on failure.
  */
-int sched_rr_get_interval(pid_t __pid, struct timespec* __quantum);
+int sched_rr_get_interval(pid_t __pid, struct timespec* _Nonnull __quantum);
 
 #if defined(__USE_GNU)
 
@@ -172,7 +172,7 @@
  * Returns the pid of the child to the caller on success and
  * returns -1 and sets `errno` on failure.
  */
-int clone(int (*__fn)(void*), void* __child_stack, int __flags, void* __arg, ...) __INTRODUCED_IN_ARM(9) __INTRODUCED_IN_X86(17);
+int clone(int (* __BIONIC_COMPLICATED_NULLNESS __fn)(void* __BIONIC_COMPLICATED_NULLNESS ), void* __BIONIC_COMPLICATED_NULLNESS __child_stack, int __flags, void* _Nullable __arg, ...) __INTRODUCED_IN_ARM(9) __INTRODUCED_IN_X86(17);
 
 /**
  * [unshare(2)](http://man7.org/linux/man-pages/man2/unshare.2.html)
@@ -228,7 +228,7 @@
  *
  * Returns 0 on success and returns -1 and sets `errno` on failure.
  */
-int sched_setaffinity(pid_t __pid, size_t __set_size, const cpu_set_t* __set);
+int sched_setaffinity(pid_t __pid, size_t __set_size, const cpu_set_t* _Nonnull __set);
 
 /**
  * [sched_getaffinity(2)](http://man7.org/linux/man-pages/man2/sched_getaffinity.2.html)
@@ -236,7 +236,7 @@
  *
  * Returns 0 on success and returns -1 and sets `errno` on failure.
  */
-int sched_getaffinity(pid_t __pid, size_t __set_size, cpu_set_t* __set);
+int sched_getaffinity(pid_t __pid, size_t __set_size, cpu_set_t* _Nonnull __set);
 
 /**
  * [CPU_ZERO](https://man7.org/linux/man-pages/man3/CPU_SET.3.html) clears all
@@ -308,7 +308,7 @@
  * how many bits are set in a dynamic CPU set allocated by `CPU_ALLOC`.
  */
 #define CPU_COUNT_S(setsize, set)  __sched_cpucount((setsize), (set))
-int __sched_cpucount(size_t __set_size, const cpu_set_t* __set);
+int __sched_cpucount(size_t __set_size, const cpu_set_t* _Nonnull __set);
 
 /**
  * [CPU_EQUAL](https://man7.org/linux/man-pages/man3/CPU_SET.3.html) tests
@@ -379,14 +379,14 @@
  * allocates a CPU set large enough for CPUs in the range 0..count-1.
  */
 #define CPU_ALLOC(count)  __sched_cpualloc((count))
-cpu_set_t* __sched_cpualloc(size_t __count);
+cpu_set_t* _Nullable __sched_cpualloc(size_t __count);
 
 /**
  * [CPU_FREE](https://man7.org/linux/man-pages/man3/CPU_SET.3.html)
  * deallocates a CPU set allocated by `CPU_ALLOC`.
  */
 #define CPU_FREE(set)     __sched_cpufree((set))
-void __sched_cpufree(cpu_set_t* __set);
+void __sched_cpufree(cpu_set_t* _Nonnull __set);
 
 #endif /* __USE_GNU */
 
diff --git a/libc/include/search.h b/libc/include/search.h
index 7c4989a..00deef1 100644
--- a/libc/include/search.h
+++ b/libc/include/search.h
@@ -25,9 +25,9 @@
 /** See hsearch()/hsearch_r(). */
 typedef struct entry {
   /** The string key. */
-  char* key;
+  char* _Nullable key;
   /** The associated data. */
-  void* data;
+  void* _Nullable data;
 } ENTRY;
 
 /**
@@ -57,7 +57,7 @@
 #if defined(__USE_BSD) || defined(__USE_GNU)
 /** The hash table type for hcreate_r()/hdestroy_r()/hsearch_r(). */
 struct hsearch_data {
-  struct __hsearch* __hsearch;
+  struct __hsearch* _Nullable __hsearch;
 };
 #endif
 
@@ -69,7 +69,7 @@
  *
  * Available since API level 21.
  */
-void insque(void* __element, void* __previous) __INTRODUCED_IN(21);
+void insque(void* _Nonnull __element, void* _Nullable __previous) __INTRODUCED_IN(21);
 
 /**
  * [remque(3)](http://man7.org/linux/man-pages/man3/remque.3.html) removes
@@ -77,7 +77,7 @@
  *
  * Available since API level 21.
  */
-void remque(void* __element) __INTRODUCED_IN(21);
+void remque(void* _Nonnull __element) __INTRODUCED_IN(21);
 
 /**
  * [hcreate(3)](http://man7.org/linux/man-pages/man3/hcreate.3.html)
@@ -112,7 +112,7 @@
  *
  * Available since API level 28.
  */
-ENTRY* hsearch(ENTRY __entry, ACTION __action) __INTRODUCED_IN(28);
+ENTRY* _Nullable hsearch(ENTRY __entry, ACTION __action) __INTRODUCED_IN(28);
 
 #if defined(__USE_BSD) || defined(__USE_GNU)
 
@@ -124,7 +124,7 @@
  *
  * Available since API level 28.
  */
-int hcreate_r(size_t __n, struct hsearch_data* __table) __INTRODUCED_IN(28);
+int hcreate_r(size_t __n, struct hsearch_data* _Nonnull __table) __INTRODUCED_IN(28);
 
 /**
  * [hdestroy_r(3)](http://man7.org/linux/man-pages/man3/hdestroy_r.3.html) destroys
@@ -132,7 +132,7 @@
  *
  * Available since API level 28.
  */
-void hdestroy_r(struct hsearch_data* __table) __INTRODUCED_IN(28);
+void hdestroy_r(struct hsearch_data* _Nonnull __table) __INTRODUCED_IN(28);
 
 /**
  * [hsearch_r(3)](http://man7.org/linux/man-pages/man3/hsearch_r.3.html) finds or
@@ -143,7 +143,7 @@
  *
  * Available since API level 28.
  */
-int hsearch_r(ENTRY __entry, ACTION __action, ENTRY** __result, struct hsearch_data* __table) __INTRODUCED_IN(28);
+int hsearch_r(ENTRY __entry, ACTION __action, ENTRY* _Nullable * _Nonnull __result, struct hsearch_data* _Nonnull __table) __INTRODUCED_IN(28);
 
 #endif
 
@@ -158,7 +158,7 @@
  *
  * Available since API level 21.
  */
-void* lfind(const void* __key, const void* __array, size_t* __count, size_t __size, int (*__comparator)(const void*, const void*)) __INTRODUCED_IN(21);
+void* _Nullable lfind(const void* _Nonnull __key, const void* _Nonnull __array, size_t* _Nonnull __count, size_t __size, int (* _Nonnull __comparator)(const void* _Nonnull, const void* _Nonnull)) __INTRODUCED_IN(21);
 
 /**
  * [lsearch(3)](http://man7.org/linux/man-pages/man3/lsearch.3.html) brute-force
@@ -173,7 +173,7 @@
  *
  * Available since API level 21.
  */
-void* lsearch(const void* __key, void* __array, size_t* __count, size_t __size, int (*__comparator)(const void*, const void*)) __INTRODUCED_IN(21);
+void* _Nonnull lsearch(const void* _Nonnull __key, void* _Nonnull __array, size_t* _Nonnull __count, size_t __size, int (* _Nonnull __comparator)(const void* _Nonnull, const void* _Nonnull)) __INTRODUCED_IN(21);
 
 /**
  * [tdelete(3)](http://man7.org/linux/man-pages/man3/tdelete.3.html) searches
@@ -182,13 +182,13 @@
  *
  * Returns a pointer to the parent of the deleted node, or NULL on failure.
  */
-void* tdelete(const void* __key, void** __root_ptr, int (*__comparator)(const void*, const void*));
+void* _Nullable tdelete(const void* _Nonnull __key, void* _Nullable * _Nullable __root_ptr, int (* _Nonnull __comparator)(const void* _Nonnull, const void* _Nonnull));
 
 /**
  * [tdestroy(3)](http://man7.org/linux/man-pages/man3/tdestroy.3.html) destroys
  * the hash table `__root` using `__free_fn` on each node.
  */
-void tdestroy(void* __root, void (*__free_fn)(void*));
+void tdestroy(void* _Nullable __root, void (* _Nullable __free_fn)(void* _Nullable));
 
 /**
  * [tfind(3)](http://man7.org/linux/man-pages/man3/tfind.3.html) searches
@@ -197,7 +197,7 @@
  *
  * Returns a pointer to the matching node, or NULL on failure.
  */
-void* tfind(const void* __key, void* const* __root_ptr, int (*__comparator)(const void*, const void*));
+void* _Nullable tfind(const void* _Nonnull __key, void* _Nullable const* _Nullable __root_ptr, int (* _Nonnull __comparator)(const void* _Nonnull, const void* _Nonnull));
 
 /**
  * [tsearch(3)](http://man7.org/linux/man-pages/man3/tsearch.3.html) searches
@@ -208,12 +208,12 @@
  *
  * Returns a pointer to the matching node, or to the newly-added node.
  */
-void* tsearch(const void* __key, void** __root_ptr, int (*__comparator)(const void*, const void*));
+void* _Nullable tsearch(const void* _Nonnull __key, void* _Nullable * _Nullable __root_ptr, int (* _Nonnull __comparator)(const void* _Nonnull, const void* _Nonnull));
 
 /**
  * [twalk(3)](http://man7.org/linux/man-pages/man3/twalk.3.html) calls
  * `__visitor` on every node in the tree.
  */
-void twalk(const void* __root, void (*__visitor)(const void*, VISIT, int)) __INTRODUCED_IN(21);
+void twalk(const void* _Nullable __root, void (* _Nullable __visitor)(const void* _Nullable, VISIT, int)) __INTRODUCED_IN(21);
 
 __END_DECLS
diff --git a/libc/include/semaphore.h b/libc/include/semaphore.h
index 5d66f7e..6ad9ea3 100644
--- a/libc/include/semaphore.h
+++ b/libc/include/semaphore.h
@@ -45,12 +45,12 @@
 
 #define SEM_FAILED __BIONIC_CAST(reinterpret_cast, sem_t*, 0)
 
-int sem_clockwait(sem_t* __sem, clockid_t __clock, const struct timespec* __ts) __INTRODUCED_IN(30);
-int sem_destroy(sem_t* __sem);
-int sem_getvalue(sem_t* __sem, int* __value);
-int sem_init(sem_t* __sem, int __shared, unsigned int __value);
-int sem_post(sem_t* __sem);
-int sem_timedwait(sem_t* __sem, const struct timespec* __ts);
+int sem_clockwait(sem_t* _Nonnull __sem, clockid_t __clock, const struct timespec* _Nonnull __ts) __INTRODUCED_IN(30);
+int sem_destroy(sem_t* _Nonnull __sem);
+int sem_getvalue(sem_t* _Nonnull __sem, int* _Nonnull __value);
+int sem_init(sem_t* _Nonnull __sem, int __shared, unsigned int __value);
+int sem_post(sem_t* _Nonnull __sem);
+int sem_timedwait(sem_t* _Nonnull __sem, const struct timespec* _Nonnull __ts);
 /*
  * POSIX historically only supported using sem_timedwait() with CLOCK_REALTIME, however that is
  * typically inappropriate, since that clock can change dramatically, causing the timeout to either
@@ -59,14 +59,14 @@
  * Note that sem_clockwait() allows specifying an arbitrary clock and has superseded this
  * function.
  */
-int sem_timedwait_monotonic_np(sem_t* __sem, const struct timespec* __ts) __INTRODUCED_IN(28);
-int sem_trywait(sem_t* __sem);
-int sem_wait(sem_t* __sem);
+int sem_timedwait_monotonic_np(sem_t* _Nonnull __sem, const struct timespec* _Nonnull __ts) __INTRODUCED_IN(28);
+int sem_trywait(sem_t* _Nonnull __sem);
+int sem_wait(sem_t* _Nonnull __sem);
 
 /* These aren't actually implemented. */
-sem_t* sem_open(const char* __name, int _flags, ...);
-int sem_close(sem_t* __sem);
-int sem_unlink(const char* __name);
+sem_t* _Nullable sem_open(const char* _Nonnull __name, int _flags, ...);
+int sem_close(sem_t* _Nonnull __sem);
+int sem_unlink(const char* _Nonnull __name);
 
 __END_DECLS
 
diff --git a/libc/include/setjmp.h b/libc/include/setjmp.h
index a3de9c7..6d047ae 100644
--- a/libc/include/setjmp.h
+++ b/libc/include/setjmp.h
@@ -47,14 +47,33 @@
 #include <sys/cdefs.h>
 
 #if defined(__aarch64__)
+/**
+ * The size in words of an arm64 jmp_buf. Room for callee-saved registers,
+ * including floating point, stack pointer and program counter, various
+ * internal implementation details, and leaving some free space.
+ *
+ * Coincidentally matches OpenBSD, though they also save/restore the
+ * floating point status register too.
+ */
 #define _JBLEN 32
 #elif defined(__arm__)
+/** The size in words of an arm32 jmp_buf. Inherited from OpenBSD. */
 #define _JBLEN 64
 #elif defined(__i386__)
+/** The size in words of an x86 jmp_buf. Inherited from OpenBSD. */
 #define _JBLEN 10
 #elif defined(__riscv)
-#define _JBLEN 29
+/**
+ * The size in words of a riscv64 jmp_buf. Room for callee-saved registers,
+ * including floating point, stack pointer and program counter, various
+ * internal implementation details, and leaving some free space.
+ *
+ * Coincidentally matches OpenBSD, though they also save/restore the
+ * floating point status register too.
+ */
+#define _JBLEN 32
 #elif defined(__x86_64__)
+/** The size in words of an x86-64 jmp_buf. Inherited from OpenBSD. */
 #define _JBLEN 11
 #endif
 
diff --git a/libc/include/spawn.h b/libc/include/spawn.h
index e445453..6c34b98 100644
--- a/libc/include/spawn.h
+++ b/libc/include/spawn.h
@@ -52,40 +52,43 @@
 typedef struct __posix_spawnattr* posix_spawnattr_t;
 typedef struct __posix_spawn_file_actions* posix_spawn_file_actions_t;
 
-int posix_spawn(pid_t* __pid, const char* __path, const posix_spawn_file_actions_t* __actions, const posix_spawnattr_t* __attr, char* const __argv[], char* const __env[]) __INTRODUCED_IN(28);
-int posix_spawnp(pid_t* __pid, const char* __file, const posix_spawn_file_actions_t* __actions, const posix_spawnattr_t* __attr, char* const __argv[], char* const __env[]) __INTRODUCED_IN(28);
+int posix_spawn(pid_t* _Nullable __pid, const char* _Nonnull __path, const posix_spawn_file_actions_t _Nullable * _Nullable __actions, const posix_spawnattr_t _Nullable * _Nullable __attr, char* const _Nonnull __argv[_Nonnull], char* const _Nullable __env[_Nullable]) __INTRODUCED_IN(28);
+int posix_spawnp(pid_t* _Nullable __pid, const char* _Nonnull __file, const posix_spawn_file_actions_t _Nullable * _Nullable __actions, const posix_spawnattr_t _Nullable * _Nullable __attr, char* const _Nonnull __argv[_Nonnull], char* const _Nullable __env[_Nullable]) __INTRODUCED_IN(28);
 
-int posix_spawnattr_init(posix_spawnattr_t* __attr) __INTRODUCED_IN(28);
-int posix_spawnattr_destroy(posix_spawnattr_t* __attr) __INTRODUCED_IN(28);
+int posix_spawnattr_init(posix_spawnattr_t _Nonnull * _Nonnull __attr) __INTRODUCED_IN(28);
+int posix_spawnattr_destroy(posix_spawnattr_t _Nonnull * _Nonnull __attr) __INTRODUCED_IN(28);
 
-int posix_spawnattr_setflags(posix_spawnattr_t* __attr, short __flags) __INTRODUCED_IN(28);
-int posix_spawnattr_getflags(const posix_spawnattr_t* __attr, short* __flags) __INTRODUCED_IN(28);
+int posix_spawnattr_setflags(posix_spawnattr_t _Nonnull * _Nonnull __attr, short __flags) __INTRODUCED_IN(28);
+int posix_spawnattr_getflags(const posix_spawnattr_t _Nonnull * _Nonnull __attr, short* _Nonnull __flags) __INTRODUCED_IN(28);
 
-int posix_spawnattr_setpgroup(posix_spawnattr_t* __attr, pid_t __pgroup) __INTRODUCED_IN(28);
-int posix_spawnattr_getpgroup(const posix_spawnattr_t* __attr, pid_t* __pgroup) __INTRODUCED_IN(28);
+int posix_spawnattr_setpgroup(posix_spawnattr_t _Nonnull * _Nonnull __attr, pid_t __pgroup) __INTRODUCED_IN(28);
+int posix_spawnattr_getpgroup(const posix_spawnattr_t _Nonnull * _Nonnull __attr, pid_t* _Nonnull __pgroup) __INTRODUCED_IN(28);
 
-int posix_spawnattr_setsigmask(posix_spawnattr_t* __attr, const sigset_t* __mask) __INTRODUCED_IN(28);
-int posix_spawnattr_setsigmask64(posix_spawnattr_t* __attr, const sigset64_t* __mask) __INTRODUCED_IN(28);
-int posix_spawnattr_getsigmask(const posix_spawnattr_t* __attr, sigset_t* __mask) __INTRODUCED_IN(28);
-int posix_spawnattr_getsigmask64(const posix_spawnattr_t* __attr, sigset64_t* __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_setsigmask(posix_spawnattr_t _Nonnull * _Nonnull __attr, const sigset_t* _Nonnull __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_setsigmask64(posix_spawnattr_t _Nonnull * _Nonnull __attr, const sigset64_t* _Nonnull __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_getsigmask(const posix_spawnattr_t _Nonnull * _Nonnull __attr, sigset_t* _Nonnull __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_getsigmask64(const posix_spawnattr_t _Nonnull * _Nonnull __attr, sigset64_t* _Nonnull __mask) __INTRODUCED_IN(28);
 
-int posix_spawnattr_setsigdefault(posix_spawnattr_t* __attr, const sigset_t* __mask) __INTRODUCED_IN(28);
-int posix_spawnattr_setsigdefault64(posix_spawnattr_t* __attr, const sigset64_t* __mask) __INTRODUCED_IN(28);
-int posix_spawnattr_getsigdefault(const posix_spawnattr_t* __attr, sigset_t* __mask) __INTRODUCED_IN(28);
-int posix_spawnattr_getsigdefault64(const posix_spawnattr_t* __attr, sigset64_t* __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_setsigdefault(posix_spawnattr_t _Nonnull * _Nonnull __attr, const sigset_t* _Nonnull __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_setsigdefault64(posix_spawnattr_t _Nonnull * _Nonnull __attr, const sigset64_t* _Nonnull __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_getsigdefault(const posix_spawnattr_t _Nonnull * _Nonnull __attr, sigset_t* _Nonnull __mask) __INTRODUCED_IN(28);
+int posix_spawnattr_getsigdefault64(const posix_spawnattr_t _Nonnull * _Nonnull __attr, sigset64_t* _Nonnull __mask) __INTRODUCED_IN(28);
 
-int posix_spawnattr_setschedparam(posix_spawnattr_t* __attr, const struct sched_param* __param) __INTRODUCED_IN(28);
-int posix_spawnattr_getschedparam(const posix_spawnattr_t* __attr, struct sched_param* __param) __INTRODUCED_IN(28);
+int posix_spawnattr_setschedparam(posix_spawnattr_t _Nonnull * _Nonnull __attr, const struct sched_param* _Nonnull __param) __INTRODUCED_IN(28);
+int posix_spawnattr_getschedparam(const posix_spawnattr_t _Nonnull * _Nonnull __attr, struct sched_param* _Nonnull __param) __INTRODUCED_IN(28);
 
-int posix_spawnattr_setschedpolicy(posix_spawnattr_t* __attr, int __policy) __INTRODUCED_IN(28);
-int posix_spawnattr_getschedpolicy(const posix_spawnattr_t* __attr, int* __policy) __INTRODUCED_IN(28);
+int posix_spawnattr_setschedpolicy(posix_spawnattr_t _Nonnull * _Nonnull __attr, int __policy) __INTRODUCED_IN(28);
+int posix_spawnattr_getschedpolicy(const posix_spawnattr_t _Nonnull * _Nonnull __attr, int* _Nonnull __policy) __INTRODUCED_IN(28);
 
-int posix_spawn_file_actions_init(posix_spawn_file_actions_t* __actions) __INTRODUCED_IN(28);
-int posix_spawn_file_actions_destroy(posix_spawn_file_actions_t* __actions) __INTRODUCED_IN(28);
+int posix_spawn_file_actions_init(posix_spawn_file_actions_t _Nonnull * _Nonnull __actions) __INTRODUCED_IN(28);
+int posix_spawn_file_actions_destroy(posix_spawn_file_actions_t _Nonnull * _Nonnull __actions) __INTRODUCED_IN(28);
 
-int posix_spawn_file_actions_addopen(posix_spawn_file_actions_t* __actions, int __fd, const char* __path, int __flags, mode_t __mode) __INTRODUCED_IN(28);
-int posix_spawn_file_actions_addclose(posix_spawn_file_actions_t* __actions, int __fd) __INTRODUCED_IN(28);
-int posix_spawn_file_actions_adddup2(posix_spawn_file_actions_t* __actions, int __fd, int __new_fd) __INTRODUCED_IN(28);
+int posix_spawn_file_actions_addopen(posix_spawn_file_actions_t _Nonnull * _Nonnull __actions, int __fd, const char* _Nonnull __path, int __flags, mode_t __mode) __INTRODUCED_IN(28);
+int posix_spawn_file_actions_addclose(posix_spawn_file_actions_t _Nonnull * _Nonnull __actions, int __fd) __INTRODUCED_IN(28);
+int posix_spawn_file_actions_adddup2(posix_spawn_file_actions_t _Nonnull * _Nonnull __actions, int __fd, int __new_fd) __INTRODUCED_IN(28);
+
+int posix_spawn_file_actions_addchdir_np(posix_spawn_file_actions_t _Nonnull * _Nonnull __actions, const char* _Nonnull __path) __INTRODUCED_IN(34);
+int posix_spawn_file_actions_addfchdir_np(posix_spawn_file_actions_t _Nonnull * _Nonnull __actions, int __fd) __INTRODUCED_IN(34);
 
 __END_DECLS
 
diff --git a/libc/include/stdio.h b/libc/include/stdio.h
index e748faa..d7b65e4 100644
--- a/libc/include/stdio.h
+++ b/libc/include/stdio.h
@@ -143,9 +143,9 @@
     (defined(__cplusplus) && __cplusplus <= 201103L)
 char* _Nullable gets(char* _Nonnull __buf) __attribute__((deprecated("gets is unsafe, use fgets instead")));
 #endif
-int sprintf(char* _Nonnull __s, const char* _Nonnull __fmt, ...)
+int sprintf(char* __BIONIC_COMPLICATED_NULLNESS __s, const char* _Nonnull __fmt, ...)
     __printflike(2, 3) __warnattr_strict("sprintf is often misused; please use snprintf");
-int vsprintf(char* _Nonnull __s, const char* _Nonnull __fmt, va_list __args)
+int vsprintf(char* __BIONIC_COMPLICATED_NULLNESS __s, const char* _Nonnull __fmt, va_list __args)
     __printflike(2, 0) __warnattr_strict("vsprintf is often misused; please use vsnprintf");
 char* _Nullable tmpnam(char* _Nullable __s)
     __warnattr("tmpnam is unsafe, use mkstemp or tmpfile instead");
@@ -251,10 +251,10 @@
 FILE* _Nullable tmpfile(void);
 FILE* _Nullable tmpfile64(void) __INTRODUCED_IN(24);
 
-int snprintf(char* _Nullable __buf, size_t __size, const char* _Nonnull __fmt, ...) __printflike(3, 4);
+int snprintf(char* __BIONIC_COMPLICATED_NULLNESS __buf, size_t __size, const char* _Nonnull __fmt, ...) __printflike(3, 4);
 int vfscanf(FILE* _Nonnull __fp, const char* _Nonnull __fmt, va_list __args) __scanflike(2, 0);
 int vscanf(const char* _Nonnull __fmt , va_list __args) __scanflike(1, 0);
-int vsnprintf(char* _Nullable __buf, size_t __size, const char* _Nonnull __fmt, va_list __args) __printflike(3, 0);
+int vsnprintf(char* __BIONIC_COMPLICATED_NULLNESS __buf, size_t __size, const char* _Nonnull __fmt, va_list __args) __printflike(3, 0);
 int vsscanf(const char* _Nonnull __s, const char* _Nonnull __fmt, va_list __args) __scanflike(2, 0);
 
 #define L_ctermid 1024 /* size for ctermid() */
diff --git a/libc/include/stdlib.h b/libc/include/stdlib.h
index b416f62..2bcb870 100644
--- a/libc/include/stdlib.h
+++ b/libc/include/stdlib.h
@@ -91,7 +91,7 @@
 
 void* _Nullable bsearch(const void* _Nonnull __key, const void* _Nullable __base, size_t __nmemb, size_t __size, int (* _Nonnull __comparator)(const void* _Nonnull __lhs, const void* _Nonnull __rhs));
 
-void qsort(void* _Nullable __base, size_t __nmemb, size_t __size, int (* _Nonnull __comparator)(const void* _Nonnull __lhs, const void* _Nonnull __rhs));
+void qsort(void* _Nullable __base, size_t __nmemb, size_t __size, int (* _Nonnull __comparator)(const void* _Nullable __lhs, const void* _Nullable __rhs));
 
 uint32_t arc4random(void);
 uint32_t arc4random_uniform(uint32_t __upper_bound);
diff --git a/libc/include/sys/capability.h b/libc/include/sys/capability.h
index 4cb698f..b43bbf0 100644
--- a/libc/include/sys/capability.h
+++ b/libc/include/sys/capability.h
@@ -44,7 +44,7 @@
  *
  * Returns 0 on success, and returns -1 and sets `errno` on failure.
  */
-int capget(cap_user_header_t __hdr_ptr, cap_user_data_t __data_ptr);
+int capget(cap_user_header_t _Nonnull __hdr_ptr, cap_user_data_t _Nullable __data_ptr);
 
 /**
  * [capset(2)](http://man7.org/linux/man-pages/man2/capset.2.html) sets the calling
@@ -52,6 +52,6 @@
  *
  * Returns 0 on success, and returns -1 and sets `errno` on failure.
  */
-int capset(cap_user_header_t __hdr_ptr, const cap_user_data_t __data_ptr);
+int capset(cap_user_header_t _Nonnull __hdr_ptr, const cap_user_data_t _Nullable __data_ptr);
 
 __END_DECLS
diff --git a/libc/include/sys/inotify.h b/libc/include/sys/inotify.h
index c3cdc85..e834d07 100644
--- a/libc/include/sys/inotify.h
+++ b/libc/include/sys/inotify.h
@@ -42,7 +42,7 @@
 
 int inotify_init(void);
 int inotify_init1(int __flags) __INTRODUCED_IN(21);
-int inotify_add_watch(int __fd, const char* __path, uint32_t __mask);
+int inotify_add_watch(int __fd, const char* _Nonnull __path, uint32_t __mask);
 int inotify_rm_watch(int __fd, uint32_t __watch_descriptor);
 
 __END_DECLS
diff --git a/libc/include/sys/ipc.h b/libc/include/sys/ipc.h
index c81ec1a..2e2b8cf 100644
--- a/libc/include/sys/ipc.h
+++ b/libc/include/sys/ipc.h
@@ -52,6 +52,6 @@
  *
  * Returns a key on success, and returns -1 and sets `errno` on failure.
  */
-key_t ftok(const char* __path, int __id);
+key_t ftok(const char* _Nonnull __path, int __id);
 
 __END_DECLS
diff --git a/libc/include/sys/mount.h b/libc/include/sys/mount.h
index 4db1ac1..aace205 100644
--- a/libc/include/sys/mount.h
+++ b/libc/include/sys/mount.h
@@ -55,7 +55,7 @@
  *
  * Returns 0 on success, and returns -1 and sets `errno` on failure.
  */
-int mount(const char* __source, const char* __target, const char* __fs_type, unsigned long __flags, const void* __data);
+int mount(const char* __BIONIC_COMPLICATED_NULLNESS __source, const char* _Nonnull __target, const char* __BIONIC_COMPLICATED_NULLNESS __fs_type, unsigned long __flags, const void* _Nullable __data);
 
 /**
  * [umount(2)](http://man7.org/linux/man-pages/man2/umount.2.html) unmounts the filesystem at
@@ -63,7 +63,7 @@
  *
  * Returns 0 on success, and returns -1 and sets `errno` on failure.
  */
-int umount(const char* __target);
+int umount(const char* _Nonnull __target);
 
 /**
  * [umount2(2)](http://man7.org/linux/man-pages/man2/umount2.2.html) unmounts the filesystem at
@@ -71,6 +71,6 @@
  *
  * Returns 0 on success, and returns -1 and sets `errno` on failure.
  */
-int umount2(const char* __target, int __flags);
+int umount2(const char* _Nonnull __target, int __flags);
 
 __END_DECLS
diff --git a/libc/include/sys/msg.h b/libc/include/sys/msg.h
index e19452c..ad481a0 100644
--- a/libc/include/sys/msg.h
+++ b/libc/include/sys/msg.h
@@ -46,12 +46,12 @@
 typedef __kernel_ulong_t msglen_t;
 
 /** Not useful on Android; disallowed by SELinux. */
-int msgctl(int __msg_id, int __cmd, struct msqid_ds* __buf) __INTRODUCED_IN(26);
+int msgctl(int __msg_id, int __cmd, struct msqid_ds* _Nullable __buf) __INTRODUCED_IN(26);
 /** Not useful on Android; disallowed by SELinux. */
 int msgget(key_t __key, int __flags) __INTRODUCED_IN(26);
 /** Not useful on Android; disallowed by SELinux. */
-ssize_t msgrcv(int __msg_id, void* __msgbuf_ptr, size_t __size, long __type, int __flags) __INTRODUCED_IN(26);
+ssize_t msgrcv(int __msg_id, void* _Nonnull __msgbuf_ptr, size_t __size, long __type, int __flags) __INTRODUCED_IN(26);
 /** Not useful on Android; disallowed by SELinux. */
-int msgsnd(int __msg_id, const void* __msgbuf_ptr, size_t __size, int __flags) __INTRODUCED_IN(26);
+int msgsnd(int __msg_id, const void* _Nonnull __msgbuf_ptr, size_t __size, int __flags) __INTRODUCED_IN(26);
 
 __END_DECLS
diff --git a/libc/include/sys/random.h b/libc/include/sys/random.h
index be52bd9..0251176 100644
--- a/libc/include/sys/random.h
+++ b/libc/include/sys/random.h
@@ -50,7 +50,7 @@
  *
  * See also arc4random_buf() which is available in all API levels.
  */
-int getentropy(void* __buffer, size_t __buffer_size) __wur __INTRODUCED_IN(28);
+int getentropy(void* _Nonnull __buffer, size_t __buffer_size) __wur __INTRODUCED_IN(28);
 
 /**
  * [getrandom(2)](http://man7.org/linux/man-pages/man2/getrandom.2.html) fills the given buffer
@@ -62,6 +62,6 @@
  *
  * See also arc4random_buf() which is available in all API levels.
  */
-ssize_t getrandom(void* __buffer, size_t __buffer_size, unsigned int __flags) __wur __INTRODUCED_IN(28);
+ssize_t getrandom(void* _Nonnull __buffer, size_t __buffer_size, unsigned int __flags) __wur __INTRODUCED_IN(28);
 
 __END_DECLS
diff --git a/libc/include/sys/resource.h b/libc/include/sys/resource.h
index ccb267d..0b540de 100644
--- a/libc/include/sys/resource.h
+++ b/libc/include/sys/resource.h
@@ -43,19 +43,19 @@
 typedef unsigned long rlim_t;
 typedef unsigned long long rlim64_t;
 
-int getrlimit(int __resource, struct rlimit* __limit);
-int setrlimit(int __resource, const struct rlimit* __limit);
+int getrlimit(int __resource, struct rlimit* _Nonnull __limit);
+int setrlimit(int __resource, const struct rlimit* _Nonnull __limit);
 
-int getrlimit64(int __resource, struct rlimit64* __limit) __INTRODUCED_IN(21);
-int setrlimit64(int __resource, const struct rlimit64* __limit) __INTRODUCED_IN(21);
+int getrlimit64(int __resource, struct rlimit64* _Nonnull __limit) __INTRODUCED_IN(21);
+int setrlimit64(int __resource, const struct rlimit64* _Nonnull __limit) __INTRODUCED_IN(21);
 
 int getpriority(int __which, id_t __who);
 int setpriority(int __which, id_t __who, int __priority);
 
-int getrusage(int __who, struct rusage* __usage);
+int getrusage(int __who, struct rusage* _Nonnull __usage);
 
-int prlimit(pid_t __pid, int __resource, const struct rlimit* __new_limit, struct rlimit* __old_limit) __INTRODUCED_IN_32(24) __INTRODUCED_IN_64(21);
-int prlimit64(pid_t __pid, int __resource, const struct rlimit64* __new_limit, struct rlimit64* __old_limit) __INTRODUCED_IN(21);
+int prlimit(pid_t __pid, int __resource, const struct rlimit* _Nullable __new_limit, struct rlimit* _Nullable __old_limit) __INTRODUCED_IN_32(24) __INTRODUCED_IN_64(21);
+int prlimit64(pid_t __pid, int __resource, const struct rlimit64* _Nullable __new_limit, struct rlimit64* _Nullable __old_limit) __INTRODUCED_IN(21);
 
 __END_DECLS
 
diff --git a/libc/include/sys/select.h b/libc/include/sys/select.h
index 06914a6..8c6c2ff 100644
--- a/libc/include/sys/select.h
+++ b/libc/include/sys/select.h
@@ -71,9 +71,9 @@
     } \
   } while (0)
 
-void __FD_CLR_chk(int, fd_set*, size_t) __INTRODUCED_IN(21);
-void __FD_SET_chk(int, fd_set*, size_t) __INTRODUCED_IN(21);
-int __FD_ISSET_chk(int, const fd_set*, size_t) __INTRODUCED_IN(21);
+void __FD_CLR_chk(int, fd_set* _Nonnull , size_t) __INTRODUCED_IN(21);
+void __FD_SET_chk(int, fd_set* _Nonnull, size_t) __INTRODUCED_IN(21);
+int __FD_ISSET_chk(int, const fd_set* _Nonnull, size_t) __INTRODUCED_IN(21);
 
 #define __FD_CLR(fd, set) (__FDS_BITS(fd_set*,set)[__FDELT(fd)] &= ~__FDMASK(fd))
 #define __FD_SET(fd, set) (__FDS_BITS(fd_set*,set)[__FDELT(fd)] |= __FDMASK(fd))
@@ -95,7 +95,7 @@
  * Returns the number of ready file descriptors on success, 0 for timeout,
  * and returns -1 and sets `errno` on failure.
  */
-int select(int __max_fd_plus_one, fd_set* __read_fds, fd_set* __write_fds, fd_set* __exception_fds, struct timeval* __timeout);
+int select(int __max_fd_plus_one, fd_set* _Nullable __read_fds, fd_set* _Nullable __write_fds, fd_set* _Nullable __exception_fds, struct timeval* _Nullable __timeout);
 
 /**
  * [pselect(2)](http://man7.org/linux/man-pages/man2/select.2.html) waits on a
@@ -106,7 +106,7 @@
  * Returns the number of ready file descriptors on success, 0 for timeout,
  * and returns -1 and sets `errno` on failure.
  */
-int pselect(int __max_fd_plus_one, fd_set* __read_fds, fd_set* __write_fds, fd_set* __exception_fds, const struct timespec* __timeout, const sigset_t* __mask);
+int pselect(int __max_fd_plus_one, fd_set* _Nullable __read_fds, fd_set* _Nullable __write_fds, fd_set* _Nullable __exception_fds, const struct timespec* _Nullable __timeout, const sigset_t* _Nullable __mask);
 
 /**
  * [pselect64(2)](http://man7.org/linux/man-pages/man2/select.2.html) waits on a
@@ -119,6 +119,6 @@
  *
  * Available since API level 28.
  */
-int pselect64(int __max_fd_plus_one, fd_set* __read_fds, fd_set* __write_fds, fd_set* __exception_fds, const struct timespec* __timeout, const sigset64_t* __mask) __INTRODUCED_IN(28);
+int pselect64(int __max_fd_plus_one, fd_set* _Nullable __read_fds, fd_set* _Nullable __write_fds, fd_set* _Nullable __exception_fds, const struct timespec* _Nullable __timeout, const sigset64_t* _Nullable __mask) __INTRODUCED_IN(28);
 
 __END_DECLS
diff --git a/libc/include/sys/sem.h b/libc/include/sys/sem.h
index cd62242..f4256e2 100644
--- a/libc/include/sys/sem.h
+++ b/libc/include/sys/sem.h
@@ -45,18 +45,18 @@
 
 union semun {
   int val;
-  struct semid_ds* buf;
-  unsigned short* array;
-  struct seminfo* __buf;
-  void* __pad;
+  struct semid_ds* _Nullable buf;
+  unsigned short* _Nullable array;
+  struct seminfo* _Nullable __buf;
+  void* _Nullable __pad;
 };
 
 int semctl(int __sem_id, int __sem_num, int __cmd, ...) __INTRODUCED_IN(26);
 int semget(key_t __key, int __sem_count, int __flags) __INTRODUCED_IN(26);
-int semop(int __sem_id, struct sembuf* __ops, size_t __op_count) __INTRODUCED_IN(26);
+int semop(int __sem_id, struct sembuf* _Nonnull __ops, size_t __op_count) __INTRODUCED_IN(26);
 
 #if defined(__USE_GNU)
-int semtimedop(int __sem_id, struct sembuf* __ops, size_t __op_count, const struct timespec* __timeout) __INTRODUCED_IN(26);
+int semtimedop(int __sem_id, struct sembuf* _Nonnull __ops, size_t __op_count, const struct timespec* _Nullable __timeout) __INTRODUCED_IN(26);
 #endif
 
 __END_DECLS
diff --git a/libc/include/sys/sendfile.h b/libc/include/sys/sendfile.h
index 60bbde8..4b00d5d 100644
--- a/libc/include/sys/sendfile.h
+++ b/libc/include/sys/sendfile.h
@@ -40,7 +40,7 @@
 
 /* See https://android.googlesource.com/platform/bionic/+/master/docs/32-bit-abi.md */
 #if defined(__USE_FILE_OFFSET64)
-ssize_t sendfile(int __out_fd, int __in_fd, off_t* __offset, size_t __count) __RENAME(sendfile64) __INTRODUCED_IN(21);
+ssize_t sendfile(int __out_fd, int __in_fd, off_t* _Nullable __offset, size_t __count) __RENAME(sendfile64) __INTRODUCED_IN(21);
 #else
 /**
  * [sendfile(2)](http://man7.org/linux/man-pages/man2/sendfile.2.html) copies data directly
@@ -50,13 +50,13 @@
  *
  * Available since API level 21.
  */
-ssize_t sendfile(int __out_fd, int __in_fd, off_t* __offset, size_t __count);
+ssize_t sendfile(int __out_fd, int __in_fd, off_t* _Nullable __offset, size_t __count);
 #endif
 
 /**
  * Like sendfile() but allows using a 64-bit offset
  * even from a 32-bit process without `__FILE_OFFSET_BITS=64`.
  */
-ssize_t sendfile64(int __out_fd, int __in_fd, off64_t* __offset, size_t __count) __INTRODUCED_IN(21);
+ssize_t sendfile64(int __out_fd, int __in_fd, off64_t* _Nullable __offset, size_t __count) __INTRODUCED_IN(21);
 
 __END_DECLS
diff --git a/libc/include/sys/statvfs.h b/libc/include/sys/statvfs.h
index 793ee13..d81f836 100644
--- a/libc/include/sys/statvfs.h
+++ b/libc/include/sys/statvfs.h
@@ -96,7 +96,7 @@
  *
  * Available since API level 19.
  */
-int statvfs(const char* __path, struct statvfs* __buf) __INTRODUCED_IN(19);
+int statvfs(const char* _Nonnull __path, struct statvfs* _Nonnull __buf) __INTRODUCED_IN(19);
 
 /**
  * [fstatvfs(3)](http://man7.org/linux/man-pages/man3/fstatvfs.3.html)
@@ -106,12 +106,12 @@
  *
  * Available since API level 19.
  */
-int fstatvfs(int __fd, struct statvfs* __buf) __INTRODUCED_IN(19);
+int fstatvfs(int __fd, struct statvfs* _Nonnull __buf) __INTRODUCED_IN(19);
 
 /** Equivalent to statvfs() . */
-int statvfs64(const char* __path, struct statvfs64* __buf) __INTRODUCED_IN(21);
+int statvfs64(const char* _Nonnull __path, struct statvfs64* _Nonnull __buf) __INTRODUCED_IN(21);
 
 /** Equivalent to fstatvfs(). */
-int fstatvfs64(int __fd, struct statvfs64* __buf) __INTRODUCED_IN(21);
+int fstatvfs64(int __fd, struct statvfs64* _Nonnull __buf) __INTRODUCED_IN(21);
 
 __END_DECLS
diff --git a/libc/include/sys/time.h b/libc/include/sys/time.h
index 45190c3..6ba7a37 100644
--- a/libc/include/sys/time.h
+++ b/libc/include/sys/time.h
@@ -38,21 +38,34 @@
 
 __BEGIN_DECLS
 
-int gettimeofday(struct timeval* __tv, struct timezone* __tz);
-int settimeofday(const struct timeval* __tv, const struct timezone* __tz);
+int gettimeofday(struct timeval* _Nullable __tv, struct timezone* _Nullable __tz);
+int settimeofday(const struct timeval* _Nullable __tv, const struct timezone* _Nullable __tz);
 
-int getitimer(int __which, struct itimerval* __current_value);
-int setitimer(int __which, const struct itimerval* __new_value, struct itimerval* __old_value);
+int getitimer(int __which, struct itimerval* _Nonnull __current_value);
+int setitimer(int __which, const struct itimerval* _Nonnull __new_value, struct itimerval* _Nullable __old_value);
 
-int utimes(const char* __path, const struct timeval __times[2]);
+int utimes(const char* _Nonnull __path, const struct timeval __times[_Nullable 2]);
 
 #if defined(__USE_BSD)
-int futimes(int __fd, const struct timeval __times[2]) __INTRODUCED_IN(26);
-int lutimes(const char* __path, const struct timeval __times[2]) __INTRODUCED_IN(26);
+int futimes(int __fd, const struct timeval __times[_Nullable 2]) __INTRODUCED_IN(26);
+int lutimes(const char* _Nonnull __path, const struct timeval __times[_Nullable 2]) __INTRODUCED_IN(26);
 #endif
 
 #if defined(__USE_GNU)
-int futimesat(int __dir_fd, const char* __path, const struct timeval __times[2]) __INTRODUCED_IN(26);
+/**
+ * [futimesat(2)](https://man7.org/linux/man-pages/man2/futimesat.2.html) sets
+ * file timestamps.
+ *
+ * Note: Linux supports `__path` being NULL (in which case `__dir_fd` need not
+ * be a directory), allowing futimensat() to be implemented with utimensat().
+ * Most callers should just use utimensat() directly, especially on Android
+ * where utimensat() has been available for longer than futimesat().
+ *
+ * Returns 0 on success and -1 and sets `errno` on failure.
+ *
+ * Available since API level 26.
+ */
+int futimesat(int __dir_fd, const char* __BIONIC_COMPLICATED_NULLNESS __path, const struct timeval __times[_Nullable 2]) __INTRODUCED_IN(26);
 #endif
 
 #define timerclear(a)   \
diff --git a/libc/include/sys/timerfd.h b/libc/include/sys/timerfd.h
index b89941b..aafcef2 100644
--- a/libc/include/sys/timerfd.h
+++ b/libc/include/sys/timerfd.h
@@ -68,7 +68,7 @@
  *
  * Available since API level 19.
  */
-int timerfd_settime(int __fd, int __flags, const struct itimerspec* __new_value, struct itimerspec* __old_value) __INTRODUCED_IN(19);
+int timerfd_settime(int __fd, int __flags, const struct itimerspec* _Nonnull __new_value, struct itimerspec* _Nullable __old_value) __INTRODUCED_IN(19);
 
 /**
  * [timerfd_gettime(2)](http://man7.org/linux/man-pages/man2/timerfd_gettime.2.html) queries the
@@ -78,6 +78,6 @@
  *
  * Available since API level 19.
  */
-int timerfd_gettime(int __fd, struct itimerspec* __current_value) __INTRODUCED_IN(19);
+int timerfd_gettime(int __fd, struct itimerspec* _Nonnull __current_value) __INTRODUCED_IN(19);
 
 __END_DECLS
diff --git a/libc/include/sys/times.h b/libc/include/sys/times.h
index 25d03e3..8b6e91d 100644
--- a/libc/include/sys/times.h
+++ b/libc/include/sys/times.h
@@ -46,6 +46,6 @@
  * Returns a (possibly overflowed) absolute time on success,
  * and returns -1 and sets `errno` on failure.
  */
-clock_t times(struct tms* __buf);
+clock_t times(struct tms* _Nullable __buf);
 
 __END_DECLS
diff --git a/libc/include/sys/timex.h b/libc/include/sys/timex.h
index 52db5dc..4823edf 100644
--- a/libc/include/sys/timex.h
+++ b/libc/include/sys/timex.h
@@ -46,7 +46,7 @@
  *
  * Available since API level 24.
  */
-int adjtimex(struct timex* __buf) __INTRODUCED_IN(24);
+int adjtimex(struct timex* _Nonnull __buf) __INTRODUCED_IN(24);
 
 /**
  * clock_adjtime adjusts a specific kernel clock.
@@ -55,6 +55,6 @@
  *
  * Available since API level 24.
  */
-int clock_adjtime(clockid_t __clock, struct timex* __tx) __INTRODUCED_IN(24);
+int clock_adjtime(clockid_t __clock, struct timex* _Nonnull __tx) __INTRODUCED_IN(24);
 
 __END_DECLS
diff --git a/libc/include/sys/ucontext.h b/libc/include/sys/ucontext.h
index cefe177..4f4d5ce 100644
--- a/libc/include/sys/ucontext.h
+++ b/libc/include/sys/ucontext.h
@@ -318,12 +318,20 @@
 
 #if defined(__USE_GNU)
 
-#define REG_PC 0
-#define REG_RA 1
-#define REG_SP 2
-#define REG_TP 4
-#define REG_S0 8
-#define REG_A0 10
+enum {
+  REG_PC = 0,
+#define REG_PC REG_PC
+  REG_RA = 1,
+#define REG_RA REG_RA
+  REG_SP = 2,
+#define REG_SP REG_SP
+  REG_TP = 4,
+#define REG_TP REG_TP
+  REG_S0 = 8,
+#define REG_S0 REG_S0
+  REG_A0 = 10,
+#define REG_A0 REG_A0
+};
 
 #endif // defined(__USE_GNU)
 
@@ -366,9 +374,9 @@
 
 /* This matches the kernel <asm/ucontext.h> but using mcontext_t. */
 
-typedef struct ucontext_t {
+typedef struct ucontext {
   unsigned long uc_flags;
-  struct ucontext_t* uc_link;
+  struct ucontext* uc_link;
   stack_t uc_stack;
   union {
     sigset_t uc_sigmask;
diff --git a/libc/include/sys/uio.h b/libc/include/sys/uio.h
index 583cfc6..c8c64ae 100644
--- a/libc/include/sys/uio.h
+++ b/libc/include/sys/uio.h
@@ -46,7 +46,7 @@
  * Returns the number of bytes read on success,
  * and returns -1 and sets `errno` on failure.
  */
-ssize_t readv(int __fd, const struct iovec* __iov, int __count);
+ssize_t readv(int __fd, const struct iovec* _Nonnull __iov, int __count);
 
 /**
  * [writev(2)](http://man7.org/linux/man-pages/man2/writev.2.html) writes
@@ -55,7 +55,7 @@
  * Returns the number of bytes written on success,
  * and returns -1 and sets `errno` on failure.
  */
-ssize_t writev(int __fd, const struct iovec* __iov, int __count);
+ssize_t writev(int __fd, const struct iovec* _Nonnull __iov, int __count);
 
 #if defined(__USE_GNU)
 
@@ -69,7 +69,7 @@
  *
  * Available since API level 24.
  */
-ssize_t preadv(int __fd, const struct iovec* __iov, int __count, off_t __offset) __RENAME_IF_FILE_OFFSET64(preadv64) __INTRODUCED_IN(24);
+ssize_t preadv(int __fd, const struct iovec* _Nonnull __iov, int __count, off_t __offset) __RENAME_IF_FILE_OFFSET64(preadv64) __INTRODUCED_IN(24);
 
 /**
  * [pwritev(2)](http://man7.org/linux/man-pages/man2/pwritev.2.html) writes
@@ -81,21 +81,21 @@
  *
  * Available since API level 24.
  */
-ssize_t pwritev(int __fd, const struct iovec* __iov, int __count, off_t __offset) __RENAME_IF_FILE_OFFSET64(pwritev64) __INTRODUCED_IN(24);
+ssize_t pwritev(int __fd, const struct iovec* _Nonnull __iov, int __count, off_t __offset) __RENAME_IF_FILE_OFFSET64(pwritev64) __INTRODUCED_IN(24);
 
 /**
  * Like preadv() but with a 64-bit offset even in a 32-bit process.
  *
  * Available since API level 24.
  */
-ssize_t preadv64(int __fd, const struct iovec* __iov, int __count, off64_t __offset) __INTRODUCED_IN(24);
+ssize_t preadv64(int __fd, const struct iovec* _Nonnull __iov, int __count, off64_t __offset) __INTRODUCED_IN(24);
 
 /**
  * Like pwritev() but with a 64-bit offset even in a 32-bit process.
  *
  * Available since API level 24.
  */
-ssize_t pwritev64(int __fd, const struct iovec* __iov, int __count, off64_t __offset) __INTRODUCED_IN(24);
+ssize_t pwritev64(int __fd, const struct iovec* _Nonnull __iov, int __count, off64_t __offset) __INTRODUCED_IN(24);
 
 /**
  * [preadv2(2)](http://man7.org/linux/man-pages/man2/preadv2.2.html) reads
@@ -107,7 +107,7 @@
  *
  * Available since API level 33.
  */
-ssize_t preadv2(int __fd, const struct iovec* __iov, int __count, off_t __offset, int __flags) __RENAME_IF_FILE_OFFSET64(preadv64v2) __INTRODUCED_IN(33);
+ssize_t preadv2(int __fd, const struct iovec* _Nonnull __iov, int __count, off_t __offset, int __flags) __RENAME_IF_FILE_OFFSET64(preadv64v2) __INTRODUCED_IN(33);
 
 /**
  * [pwritev2(2)](http://man7.org/linux/man-pages/man2/pwritev2.2.html) writes
@@ -119,21 +119,21 @@
  *
  * Available since API level 33.
  */
-ssize_t pwritev2(int __fd, const struct iovec* __iov, int __count, off_t __offset, int __flags) __RENAME_IF_FILE_OFFSET64(pwritev64v2) __INTRODUCED_IN(33);
+ssize_t pwritev2(int __fd, const struct iovec* _Nonnull __iov, int __count, off_t __offset, int __flags) __RENAME_IF_FILE_OFFSET64(pwritev64v2) __INTRODUCED_IN(33);
 
 /**
  * Like preadv2() but with a 64-bit offset even in a 32-bit process.
  *
  * Available since API level 33.
  */
-ssize_t preadv64v2(int __fd, const struct iovec* __iov, int __count, off64_t __offset, int __flags) __INTRODUCED_IN(33);
+ssize_t preadv64v2(int __fd, const struct iovec* _Nonnull __iov, int __count, off64_t __offset, int __flags) __INTRODUCED_IN(33);
 
 /**
  * Like pwritev2() but with a 64-bit offset even in a 32-bit process.
  *
  * Available since API level 33.
  */
-ssize_t pwritev64v2(int __fd, const struct iovec* __iov, int __count, off64_t __offset, int __flags) __INTRODUCED_IN(33);
+ssize_t pwritev64v2(int __fd, const struct iovec* _Nonnull __iov, int __count, off64_t __offset, int __flags) __INTRODUCED_IN(33);
 
 /**
  * [process_vm_readv(2)](http://man7.org/linux/man-pages/man2/process_vm_readv.2.html)
@@ -144,7 +144,7 @@
  *
  * Available since API level 23.
  */
-ssize_t process_vm_readv(pid_t __pid, const struct iovec* __local_iov, unsigned long __local_iov_count, const struct iovec* __remote_iov, unsigned long __remote_iov_count, unsigned long __flags) __INTRODUCED_IN(23);
+ssize_t process_vm_readv(pid_t __pid, const struct iovec* __BIONIC_COMPLICATED_NULLNESS __local_iov, unsigned long __local_iov_count, const struct iovec* __BIONIC_COMPLICATED_NULLNESS __remote_iov, unsigned long __remote_iov_count, unsigned long __flags) __INTRODUCED_IN(23);
 
 /**
  * [process_vm_writev(2)](http://man7.org/linux/man-pages/man2/process_vm_writev.2.html)
@@ -155,7 +155,7 @@
  *
  * Available since API level 23.
  */
-ssize_t process_vm_writev(pid_t __pid, const struct iovec* __local_iov, unsigned long __local_iov_count, const struct iovec* __remote_iov, unsigned long __remote_iov_count, unsigned long __flags) __INTRODUCED_IN(23);
+ssize_t process_vm_writev(pid_t __pid, const struct iovec* __BIONIC_COMPLICATED_NULLNESS __local_iov, unsigned long __local_iov_count, const struct iovec* __BIONIC_COMPLICATED_NULLNESS __remote_iov, unsigned long __remote_iov_count, unsigned long __flags) __INTRODUCED_IN(23);
 
 #endif
 
diff --git a/libc/include/sys/wait.h b/libc/include/sys/wait.h
index 96974a2..e6fb855 100644
--- a/libc/include/sys/wait.h
+++ b/libc/include/sys/wait.h
@@ -37,9 +37,9 @@
 
 __BEGIN_DECLS
 
-pid_t wait(int* __status);
-pid_t waitpid(pid_t __pid, int* __status, int __options);
-pid_t wait4(pid_t __pid, int* __status, int __options, struct rusage* __rusage) __INTRODUCED_IN(18);
+pid_t wait(int* _Nullable __status);
+pid_t waitpid(pid_t __pid, int* _Nullable __status, int __options);
+pid_t wait4(pid_t __pid, int* _Nullable __status, int __options, struct rusage* _Nullable __rusage) __INTRODUCED_IN(18);
 
 /* Posix states that idtype_t should be an enumeration type, but
  * the kernel headers define P_ALL, P_PID and P_PGID as constant macros
@@ -47,6 +47,6 @@
  */
 typedef int idtype_t;
 
-int waitid(idtype_t __type, id_t __id, siginfo_t* __info, int __options);
+int waitid(idtype_t __type, id_t __id, siginfo_t* _Nullable __info, int __options);
 
 __END_DECLS
diff --git a/libc/include/syslog.h b/libc/include/syslog.h
index d89d769..90ea76e 100644
--- a/libc/include/syslog.h
+++ b/libc/include/syslog.h
@@ -112,17 +112,21 @@
  */
 #define LOG_UPTO(pri) ((1 << ((pri)+1)) - 1)
 
-/** openlog() options are currently ignored on Android. */
+/** openlog() option ignored on Android. */
 #define LOG_PID    0x01
-/** openlog() options are currently ignored on Android. */
+/** openlog() option ignored on Android. */
 #define LOG_CONS   0x02
-/** openlog() options are currently ignored on Android. */
+/** openlog() option ignored on Android. */
 #define LOG_ODELAY 0x04
-/** openlog() options are currently ignored on Android. */
+/** openlog() option ignored on Android. */
 #define LOG_NDELAY 0x08
-/** openlog() options are currently ignored on Android. */
+/** openlog() option ignored on Android. */
 #define LOG_NOWAIT 0x10
-/** openlog() options are currently ignored on Android. */
+/**
+ * openlog() option to log to stderr as well as the system log.
+ *
+ * Available since API level 34 (ignored before then).
+ */
 #define LOG_PERROR 0x20
 
 /**
diff --git a/libc/include/time.h b/libc/include/time.h
index 5339540..1c3ae4b 100644
--- a/libc/include/time.h
+++ b/libc/include/time.h
@@ -26,8 +26,7 @@
  * SUCH DAMAGE.
  */
 
-#ifndef _TIME_H_
-#define _TIME_H_
+#pragma once
 
 #include <sys/cdefs.h>
 #include <sys/time.h>
@@ -105,9 +104,52 @@
 time_t timelocal(struct tm* _Nonnull __tm);
 time_t timegm(struct tm* _Nonnull __tm);
 
-#define TIME_UTC 1
+/**
+ * The timebase for timespec_get() and timespec_getres() corresponding to CLOCK_REALTIME.
+ *
+ * Available since API level 29.
+ */
+#define TIME_UTC (CLOCK_REALTIME+1)
+
+/**
+ * The timebase for timespec_get() and timespec_getres() corresponding to CLOCK_MONOTONIC.
+ *
+ * Available since API level 35.
+ */
+#define TIME_MONOTONIC (CLOCK_MONOTONIC+1)
+
+/**
+ * The timebase for timespec_get() and timespec_getres() corresponding to CLOCK_PROCESS_CPUTIME_ID.
+ *
+ * Available since API level 35.
+ */
+#define TIME_ACTIVE (CLOCK_PROCESS_CPUTIME_ID+1)
+
+/**
+ * The timebase for timespec_get() and timespec_getres() corresponding to CLOCK_THREAD_CPUTIME_ID.
+ *
+ * Available since API level 35.
+ */
+#define TIME_THREAD_ACTIVE (CLOCK_THREAD_CPUTIME_ID+1)
+
+/**
+ * timespec_get(3) is equivalent to clock_gettime() for the clock corresponding to the given base.
+ *
+ * Returns the base on success and returns 0 on failure.
+ *
+ * Available since API level 29 for TIME_UTC; other bases arrived later.
+ * Code for Android should prefer clock_gettime().
+ */
 int timespec_get(struct timespec* _Nonnull __ts, int __base) __INTRODUCED_IN(29);
 
-__END_DECLS
+/**
+ * timespec_getres(3) is equivalent to clock_getres() for the clock corresponding to the given base.
+ *
+ * Returns the base on success and returns 0 on failure.
+ *
+ * Available since API level 35.
+ * Code for Android should prefer clock_gettime().
+ */
+int timespec_getres(struct timespec* _Nonnull __ts, int __base) __INTRODUCED_IN(35);
 
-#endif
+__END_DECLS
diff --git a/libc/include/utmp.h b/libc/include/utmp.h
index 7aa5718..d249f8a 100644
--- a/libc/include/utmp.h
+++ b/libc/include/utmp.h
@@ -30,7 +30,7 @@
 
 /**
  * @file utmp.h
- * @brief POSIX login records.
+ * @brief No-op implementation of non-POSIX login records. See <utmpx.h> for the POSIX equivalents.
  */
 
 #include <sys/cdefs.h>
@@ -69,12 +69,12 @@
 };
 
 struct exit_status {
-  short int e_termination;
-  short int e_exit;
+  short e_termination;
+  short e_exit;
 };
 
 struct utmp {
-  short int ut_type;
+  short ut_type;
   pid_t ut_pid;
   char ut_line[UT_LINESIZE];
   char ut_id[4];
@@ -83,7 +83,7 @@
 
   struct exit_status ut_exit;
 
-  long int ut_session;
+  long ut_session;
   struct timeval ut_tv;
 
   int32_t ut_addr_v6[4];
@@ -97,21 +97,25 @@
 __BEGIN_DECLS
 
 /**
- * Does nothing.
+ * Returns -1 and sets errno to ENOTSUP.
  */
 int utmpname(const char* _Nonnull __path);
+
 /**
  * Does nothing.
  */
 void setutent(void);
+
 /**
- * Does nothing.
+ * Does nothing and returns null.
  */
 struct utmp* _Nullable getutent(void);
+
 /**
- * Does nothing.
+ * Does nothing and returns null.
  */
 struct utmp* _Nullable pututline(const struct utmp* _Nonnull __entry);
+
 /**
  * Does nothing.
  */
diff --git a/libc/include/utmpx.h b/libc/include/utmpx.h
new file mode 100644
index 0000000..5ed8e1a
--- /dev/null
+++ b/libc/include/utmpx.h
@@ -0,0 +1,103 @@
+/*
+ * Copyright (C) 2023 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#pragma once
+
+/**
+ * @file utmpx.h
+ * @brief No-op implementation of POSIX login records.
+ */
+
+#include <sys/cdefs.h>
+#include <sys/types.h>
+#include <time.h>
+
+#define EMPTY         0
+#define RUN_LVL       1
+#define BOOT_TIME     2
+#define NEW_TIME      3
+#define OLD_TIME      4
+#define INIT_PROCESS  5
+#define LOGIN_PROCESS 6
+#define USER_PROCESS  7
+#define DEAD_PROCESS  8
+#define ACCOUNTING    9
+
+struct utmpx {
+  short ut_type;
+  pid_t ut_pid;
+  char ut_line[32];
+  char ut_id[4];
+  char ut_user[32];
+  char ut_host[256];
+
+  struct {
+    short e_termination;
+    short e_exit;
+  } ut_exit;
+
+  long ut_session;
+  struct timeval ut_tv;
+
+  int32_t ut_addr_v6[4];
+  char unused[20];
+};
+
+__BEGIN_DECLS
+
+/**
+ * Does nothing.
+ */
+void setutxent(void) __RENAME(setutent);
+
+/**
+ * Does nothing and returns null.
+ */
+struct utmpx* _Nullable getutxent(void) __RENAME(getutent);
+
+/**
+ * Does nothing and returns null.
+ */
+struct utmpx* _Nullable getutxid(const struct utmpx* _Nonnull __entry) __RENAME(getutent);
+
+/**
+ * Does nothing and returns null.
+ */
+struct utmpx* _Nullable getutxline(const struct utmpx* _Nonnull __entry) __RENAME(getutent);
+
+/**
+ * Does nothing and returns null.
+ */
+struct utmpx* _Nullable pututxline(const struct utmpx* _Nonnull __entry) __RENAME(pututline);
+
+/**
+ * Does nothing.
+ */
+void endutxent(void) __RENAME(endutent);
+
+__END_DECLS
diff --git a/libc/include/wchar.h b/libc/include/wchar.h
index add3606..39f9374 100644
--- a/libc/include/wchar.h
+++ b/libc/include/wchar.h
@@ -44,97 +44,96 @@
 __BEGIN_DECLS
 
 wint_t btowc(int __ch);
-int fwprintf(FILE* __fp, const wchar_t* __fmt, ...);
-int fwscanf(FILE* __fp, const wchar_t* __fmt, ...);
-wint_t fgetwc(FILE* __fp);
-wchar_t* fgetws(wchar_t* __buf, int __size, FILE* __fp);
-wint_t fputwc(wchar_t __wc, FILE* __fp);
-int fputws(const wchar_t* __s, FILE* __fp);
-int fwide(FILE* __fp, int __mode);
-wint_t getwc(FILE* __fp);
+int fwprintf(FILE* _Nonnull __fp, const wchar_t* _Nonnull __fmt, ...);
+int fwscanf(FILE* _Nonnull __fp, const wchar_t* _Nonnull __fmt, ...);
+wint_t fgetwc(FILE* _Nonnull __fp);
+wchar_t* _Nullable fgetws(wchar_t* _Nonnull __buf, int __size, FILE* _Nonnull __fp);
+wint_t fputwc(wchar_t __wc, FILE* _Nonnull __fp);
+int fputws(const wchar_t* _Nonnull __s, FILE* _Nonnull __fp);
+int fwide(FILE* _Nonnull __fp, int __mode);
+wint_t getwc(FILE* _Nonnull __fp);
 wint_t getwchar(void);
-int mbsinit(const mbstate_t* __ps);
-size_t mbrlen(const char* __s, size_t __n, mbstate_t* __ps);
-size_t mbrtowc(wchar_t* __buf, const char* __s, size_t __n, mbstate_t* __ps);
-size_t mbsrtowcs(wchar_t* __dst, const char** __src, size_t __dst_n, mbstate_t* __ps);
-size_t mbsnrtowcs(wchar_t* __dst, const char** __src, size_t __src_n, size_t __dst_n, mbstate_t* __ps) __INTRODUCED_IN(21);
-wint_t putwc(wchar_t __wc, FILE* __fp);
+int mbsinit(const mbstate_t* _Nullable __ps);
+size_t mbrlen(const char* _Nullable __s, size_t __n, mbstate_t* _Nullable __ps);
+size_t mbrtowc(wchar_t* _Nullable __buf, const char* _Nullable __s, size_t __n, mbstate_t* _Nullable __ps);
+size_t mbsrtowcs(wchar_t* _Nullable __dst, const char* _Nullable * _Nonnull __src, size_t __dst_n, mbstate_t* _Nullable __ps);
+size_t mbsnrtowcs(wchar_t* _Nullable __dst, const char* _Nullable * _Nullable  __src, size_t __src_n, size_t __dst_n, mbstate_t* _Nullable __ps) __INTRODUCED_IN(21);
+wint_t putwc(wchar_t __wc, FILE* _Nonnull __fp);
 wint_t putwchar(wchar_t __wc);
-int swprintf(wchar_t* __buf, size_t __n, const wchar_t* __fmt, ...);
-int swscanf(const wchar_t* __s, const wchar_t* __fmt, ...);
-wint_t ungetwc(wint_t __wc, FILE* __fp);
-int vfwprintf(FILE* __fp, const wchar_t* __fmt, va_list __args);
-int vfwscanf(FILE* __fp, const wchar_t* __fmt, va_list __args) __INTRODUCED_IN(21);
-int vswprintf(wchar_t* __buf, size_t __n, const wchar_t* __fmt, va_list __args);
-int vswscanf(const wchar_t* __s, const wchar_t* __fmt, va_list __args) __INTRODUCED_IN(21);
-int vwprintf(const wchar_t* __fmt, va_list __args);
-int vwscanf(const wchar_t* __fmt, va_list __args) __INTRODUCED_IN(21);
-wchar_t* wcpcpy(wchar_t* __dst, const wchar_t* __src);
-wchar_t* wcpncpy(wchar_t* __dst, const wchar_t* __src, size_t __n);
-size_t wcrtomb(char* __buf, wchar_t __wc, mbstate_t* __ps);
-int wcscasecmp(const wchar_t* __lhs, const wchar_t* __rhs);
-int wcscasecmp_l(const wchar_t* __lhs, const wchar_t* __rhs, locale_t __l) __INTRODUCED_IN(23);
-wchar_t* wcscat(wchar_t* __dst, const wchar_t* __src);
-wchar_t* wcschr(const wchar_t* __s, wchar_t __wc);
-int wcscmp(const wchar_t* __lhs, const wchar_t* __rhs);
-int wcscoll(const wchar_t* __lhs, const wchar_t* __rhs);
-wchar_t* wcscpy(wchar_t* __dst, const wchar_t* __src);
-size_t wcscspn(const wchar_t* __s, const wchar_t* __accept);
-size_t wcsftime(wchar_t* __buf, size_t __n, const wchar_t* __fmt, const struct tm* __tm);
-size_t wcsftime_l(wchar_t* __buf, size_t __n, const wchar_t* __fmt, const struct tm* __tm, locale_t __l) __INTRODUCED_IN(28);
-size_t wcslen(const wchar_t* __s);
-int wcsncasecmp(const wchar_t* __lhs, const wchar_t* __rhs, size_t __n);
-int wcsncasecmp_l(const wchar_t* __lhs, const wchar_t* __rhs, size_t __n, locale_t __l) __INTRODUCED_IN(23);
-wchar_t* wcsncat(wchar_t* __dst, const wchar_t* __src, size_t __n);
-int wcsncmp(const wchar_t* __lhs, const wchar_t* __rhs, size_t __n);
-wchar_t* wcsncpy(wchar_t* __dst, const wchar_t* __src, size_t __n);
-size_t wcsnrtombs(char* __dst, const wchar_t** __src, size_t __src_n, size_t __dst_n, mbstate_t* __ps) __INTRODUCED_IN(21);
-wchar_t* wcspbrk(const wchar_t* __s, const wchar_t* __accept);
-wchar_t* wcsrchr(const wchar_t* __s, wchar_t __wc);
-size_t wcsrtombs(char* __dst, const wchar_t** __src, size_t __dst_n, mbstate_t* __ps);
-size_t wcsspn(const wchar_t* __s, const wchar_t* __accept);
-wchar_t* wcsstr(const wchar_t* __haystack, const wchar_t* __needle);
-double wcstod(const wchar_t* __s, wchar_t** __end_ptr);
-double wcstod_l(const wchar_t* __s, wchar_t** __end_ptr, locale_t __l) __INTRODUCED_IN(28);
-float wcstof(const wchar_t* __s, wchar_t** __end_ptr) __INTRODUCED_IN(21);
-float wcstof_l(const wchar_t* __s, wchar_t** __end_ptr, locale_t __l) __INTRODUCED_IN(28);
-wchar_t* wcstok(wchar_t* __s, const wchar_t* __delimiter, wchar_t** __ptr);
-long wcstol(const wchar_t* __s, wchar_t** __end_ptr, int __base);
-long wcstol_l(const wchar_t* __s, wchar_t** __end_ptr, int __base, locale_t __l) __INTRODUCED_IN(28);
-long long wcstoll(const wchar_t* __s, wchar_t** __end_ptr, int __base) __INTRODUCED_IN(21);
-long double wcstold(const wchar_t* __s, wchar_t** __end_ptr) __RENAME_LDBL(wcstod, 3, 21);
-unsigned long wcstoul(const wchar_t* __s, wchar_t** __end_ptr, int __base);
-unsigned long wcstoul_l(const wchar_t* __s, wchar_t** __end_ptr, int __base, locale_t __l) __INTRODUCED_IN(28);
-unsigned long long wcstoull(const wchar_t* __s, wchar_t** __end_ptr, int __base) __INTRODUCED_IN(21);
-int wcswidth(const wchar_t* __s, size_t __n);
-size_t wcsxfrm(wchar_t* __dst, const wchar_t* __src, size_t __n);
+int swprintf(wchar_t* _Nonnull __buf, size_t __n, const wchar_t* _Nonnull __fmt, ...);
+int swscanf(const wchar_t* _Nonnull __s, const wchar_t* _Nonnull __fmt, ...);
+wint_t ungetwc(wint_t __wc, FILE* _Nonnull __fp);
+int vfwprintf(FILE* _Nonnull __fp, const wchar_t* _Nonnull __fmt, va_list __args);
+int vfwscanf(FILE* _Nonnull __fp, const wchar_t* _Nonnull __fmt, va_list __args) __INTRODUCED_IN(21);
+int vswprintf(wchar_t* _Nonnull __buf, size_t __n, const wchar_t* _Nonnull __fmt, va_list __args);
+int vswscanf(const wchar_t* _Nonnull __s, const wchar_t* _Nonnull __fmt, va_list __args) __INTRODUCED_IN(21);
+int vwprintf(const wchar_t* _Nonnull __fmt, va_list __args);
+int vwscanf(const wchar_t* _Nonnull __fmt, va_list __args) __INTRODUCED_IN(21);
+wchar_t* _Nonnull wcpcpy(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src);
+wchar_t* _Nonnull wcpncpy(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n);
+size_t wcrtomb(char* _Nullable __buf, wchar_t __wc, mbstate_t* _Nullable __ps);
+int wcscasecmp(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs);
+int wcscasecmp_l(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs, locale_t _Nonnull __l) __INTRODUCED_IN(23);
+wchar_t* _Nonnull wcscat(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src);
+wchar_t* _Nullable wcschr(const wchar_t * _Nonnull __s, wchar_t __wc);
+int wcscmp(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs);
+int wcscoll(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs);
+wchar_t* _Nonnull wcscpy(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src);
+size_t wcscspn(const wchar_t* _Nonnull __s, const wchar_t* _Nonnull __accept);
+size_t wcsftime(wchar_t* _Nonnull __buf, size_t __n, const wchar_t* _Nullable __fmt, const struct tm* _Nonnull __tm);
+size_t wcsftime_l(wchar_t* _Nonnull __buf, size_t __n, const wchar_t* _Nullable __fmt, const struct tm* _Nonnull __tm, locale_t _Nonnull __l) __INTRODUCED_IN(28);
+size_t wcslen(const wchar_t* _Nonnull __s);
+int wcsncasecmp(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs, size_t __n);
+int wcsncasecmp_l(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs, size_t __n, locale_t _Nonnull __l) __INTRODUCED_IN(23);
+wchar_t* _Nonnull wcsncat(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n);
+int wcsncmp(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs, size_t __n);
+wchar_t* _Nonnull wcsncpy(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n);
+size_t wcsnrtombs(char* _Nullable __dst, const wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __src, size_t __src_n, size_t __dst_n, mbstate_t* _Nullable __ps) __INTRODUCED_IN(21);
+wchar_t* _Nullable wcspbrk(const wchar_t* _Nonnull __s, const wchar_t* _Nonnull __accept);
+wchar_t* _Nullable wcsrchr(const wchar_t* _Nonnull __s, wchar_t __wc);
+size_t wcsrtombs(char* _Nullable __dst, const wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __src, size_t __dst_n, mbstate_t* _Nullable __ps);
+size_t wcsspn(const wchar_t* _Nonnull __s, const wchar_t* _Nonnull __accept);
+wchar_t* _Nullable wcsstr(const wchar_t* _Nonnull __haystack, const wchar_t* _Nonnull __needle);
+double wcstod(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr);
+double wcstod_l(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, locale_t _Nonnull __l) __INTRODUCED_IN(28);
+float wcstof(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr) __INTRODUCED_IN(21);
+float wcstof_l(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, locale_t _Nonnull __l) __INTRODUCED_IN(28);
+wchar_t* _Nullable wcstok(wchar_t* _Nullable __s, const wchar_t* _Nonnull __delimiter, wchar_t* _Nonnull * _Nonnull __ptr);
+long wcstol(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, int __base);
+long wcstol_l(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, int __base, locale_t _Nonnull __l) __INTRODUCED_IN(28);
+long long wcstoll(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, int __base) __INTRODUCED_IN(21);
+long double wcstold(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr) __RENAME_LDBL(wcstod, 3, 21);
+unsigned long wcstoul(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, int __base);
+unsigned long wcstoul_l(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, int __base, locale_t _Nonnull __l) __INTRODUCED_IN(28);
+unsigned long long wcstoull(const wchar_t* _Nonnull __s, wchar_t* __BIONIC_COMPLICATED_NULLNESS * _Nullable __end_ptr, int __base) __INTRODUCED_IN(21);
+int wcswidth(const wchar_t* _Nonnull __s, size_t __n);
+size_t wcsxfrm(wchar_t* __BIONIC_COMPLICATED_NULLNESS __dst, const wchar_t* _Nonnull __src, size_t __n);
 int wctob(wint_t __wc);
 int wcwidth(wchar_t __wc);
-wchar_t* wmemchr(const wchar_t* __src, wchar_t __wc, size_t __n);
-int wmemcmp(const wchar_t* __lhs, const wchar_t* __rhs, size_t __n);
-wchar_t* wmemcpy(wchar_t* __dst, const wchar_t* __src, size_t __n);
+wchar_t* _Nullable wmemchr(const wchar_t* _Nonnull __src, wchar_t __wc, size_t __n);
+int wmemcmp(const wchar_t* _Nullable __lhs, const wchar_t* _Nullable __rhs, size_t __n);
+wchar_t* _Nonnull wmemcpy(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n);
 #if defined(__USE_GNU)
-wchar_t* wmempcpy(wchar_t* __dst, const wchar_t* __src, size_t __n) __INTRODUCED_IN(23);
+wchar_t* _Nonnull wmempcpy(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n) __INTRODUCED_IN(23);
 #endif
-wchar_t* wmemmove(wchar_t* __dst, const wchar_t* __src, size_t __n);
-wchar_t* wmemset(wchar_t* __dst, wchar_t __wc, size_t __n);
-int wprintf(const wchar_t* __fmt, ...);
-int wscanf(const wchar_t* __fmt, ...);
+wchar_t* _Nonnull wmemmove(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n);
+wchar_t* _Nonnull wmemset(wchar_t* _Nonnull __dst, wchar_t __wc, size_t __n);
+int wprintf(const wchar_t* _Nonnull __fmt, ...);
+int wscanf(const wchar_t* _Nonnull __fmt, ...);
 
-long long wcstoll_l(const wchar_t* __s, wchar_t** __end_ptr, int __base, locale_t __l) __INTRODUCED_IN(21);
-unsigned long long wcstoull_l(const wchar_t* __s, wchar_t** __end_ptr, int __base, locale_t __l) __INTRODUCED_IN(21);
-long double wcstold_l(const wchar_t* __s, wchar_t** __end_ptr, locale_t __l) __INTRODUCED_IN(21);
+long long wcstoll_l(const wchar_t* _Nonnull __s, wchar_t* _Nullable * _Nullable __end_ptr, int __base, locale_t _Nonnull __l) __INTRODUCED_IN(21);
+unsigned long long wcstoull_l(const wchar_t* _Nonnull __s, wchar_t* _Nullable * _Nullable __end_ptr, int __base, locale_t _Nonnull __l) __INTRODUCED_IN(21);
+long double wcstold_l(const wchar_t* _Nonnull __s, wchar_t* _Nullable * _Nullable __end_ptr, locale_t _Nonnull __l) __INTRODUCED_IN(21);
 
-int wcscoll_l(const wchar_t* __lhs, const wchar_t* __rhs, locale_t __l) __attribute_pure__
+int wcscoll_l(const wchar_t* _Nonnull __lhs, const wchar_t* _Nonnull __rhs, locale_t _Nonnull __l) __attribute_pure__
     __INTRODUCED_IN(21);
-size_t wcsxfrm_l(wchar_t* __dst, const wchar_t* __src, size_t __n, locale_t __l) __INTRODUCED_IN(21);
+size_t wcsxfrm_l(wchar_t* __BIONIC_COMPLICATED_NULLNESS __dst, const wchar_t* _Nonnull __src, size_t __n, locale_t _Nonnull __l) __INTRODUCED_IN(21);
+size_t wcslcat(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n);
+size_t wcslcpy(wchar_t* _Nonnull __dst, const wchar_t* _Nonnull __src, size_t __n);
 
-size_t wcslcat(wchar_t* __dst, const wchar_t* __src, size_t __n);
-size_t wcslcpy(wchar_t* __dst, const wchar_t* __src, size_t __n);
-
-FILE* open_wmemstream(wchar_t** __ptr, size_t* __size_ptr) __INTRODUCED_IN(23);
-wchar_t* wcsdup(const wchar_t* __s);
-size_t wcsnlen(const wchar_t* __s, size_t __n);
+FILE* _Nullable open_wmemstream(wchar_t* _Nonnull * _Nonnull __ptr, size_t* _Nonnull  __size_ptr) __INTRODUCED_IN(23);
+wchar_t* _Nullable wcsdup(const wchar_t* _Nonnull __s);
+size_t wcsnlen(const wchar_t* _Nonnull __s, size_t __n);
 
 __END_DECLS
 
diff --git a/libc/kernel/android/scsi/scsi/sg.h b/libc/kernel/android/scsi/scsi/sg.h
index 6911b16..9ba6cd6 100644
--- a/libc/kernel/android/scsi/scsi/sg.h
+++ b/libc/kernel/android/scsi/scsi/sg.h
@@ -20,7 +20,7 @@
 #define _SCSI_GENERIC_H
 #include <linux/compiler.h>
 typedef struct sg_iovec {
-  void __user * iov_base;
+  void  * iov_base;
   size_t iov_len;
 } sg_iovec_t;
 typedef struct sg_io_hdr {
@@ -30,13 +30,13 @@
   unsigned char mx_sb_len;
   unsigned short iovec_count;
   unsigned int dxfer_len;
-  void __user * dxferp;
-  unsigned char __user * cmdp;
-  void __user * sbp;
+  void  * dxferp;
+  unsigned char  * cmdp;
+  void  * sbp;
   unsigned int timeout;
   unsigned int flags;
   int pack_id;
-  void __user * usr_ptr;
+  void  * usr_ptr;
   unsigned char status;
   unsigned char masked_status;
   unsigned char msg_status;
@@ -96,7 +96,7 @@
   char sg_io_owned;
   char problem;
   int pack_id;
-  void __user * usr_ptr;
+  void  * usr_ptr;
   unsigned int duration;
   int unused;
 } sg_req_info_t;
diff --git a/libc/kernel/android/uapi/linux/compiler.h b/libc/kernel/android/uapi/linux/compiler.h
index 8e89655..42d59aa 100644
--- a/libc/kernel/android/uapi/linux/compiler.h
+++ b/libc/kernel/android/uapi/linux/compiler.h
@@ -1,18 +1,11 @@
-#ifndef _UAPI_LINUX_COMPILER_H
-#define _UAPI_LINUX_COMPILER_H
+#pragma once
 
 /*
- * This file is not currently in the Linux kernel tree.
- * Upstream uapi headers refer to <linux/compiler.h> but there is
- * no such uapi file. We've sent this upstream, and are optimistically
- * adding it to bionic in the meantime. This should be replaced by
- * a scrubbed header from external/kernel-headers when possible.
+ * There is no `include/uapi/linux/compiler.h`, just `include/linux/compiler.h`.
  *
- * An alternative to this file is to check in a symbolic link to the
- * non-uapi <linux/compiler.h>. That's fine for building bionic too.
+ * We don't need anything _in_ this file, but we do need this file.
+ * The two #defines are for backwards compatibility.
  */
 
-#define __user
 #define __force
-
-#endif /* _UAPI_LINUX_COMPILER_H */
+#define __user
diff --git a/libc/kernel/android/uapi/linux/compiler_types.h b/libc/kernel/android/uapi/linux/compiler_types.h
index 94f4fbe..859ae05 100644
--- a/libc/kernel/android/uapi/linux/compiler_types.h
+++ b/libc/kernel/android/uapi/linux/compiler_types.h
@@ -1,5 +1,11 @@
+#pragma once
+
 /*
- * The compiler.h file has been split into compiler.h and compiler_types.h.
- * However, to compile bionic we only need the compiler.h.
+ * There is no `include/uapi/linux/compiler_types.h`, just
+ * `include/linux/compiler_types.h`.
+ *
+ * We don't need anything _in_ this file, but we do need this file.
+ * The #include is for backwards compatibility.
  */
+
 #include <linux/compiler.h>
diff --git a/libc/kernel/tools/defaults.py b/libc/kernel/tools/defaults.py
index d0fe157..91d26ce 100644
--- a/libc/kernel/tools/defaults.py
+++ b/libc/kernel/tools/defaults.py
@@ -1,9 +1,4 @@
-# this module contains all the defaults used by the generation of cleaned-up headers
-# for the Bionic C library
-#
-
-import time, os, sys
-from utils import *
+# All the defaults used to generate the cleaned-up uapi headers for bionic.
 
 # the list of include directories that belong to the kernel
 # tree. used when looking for sources...
@@ -48,6 +43,7 @@
     "in_addr": False,
     "ip_mreq_source": False,
     "ip_msfilter": False,
+    "timespec": False,
     }
 
 # define to true if you want to remove all defined(CONFIG_FOO) tests
@@ -97,6 +93,9 @@
     # Replace __packed with __attribute__((__packed__)) to avoid depending
     # on sys/cdefs.h
     "__packed": "__attribute__((__packed__))",
+    # Remove unused macros (http://b/262917450).
+    "__force": "",
+    "__user": "",
     }
 
 
diff --git a/libc/kernel/tools/update_all.py b/libc/kernel/tools/update_all.py
index abc72a4..ae89a80 100755
--- a/libc/kernel/tools/update_all.py
+++ b/libc/kernel/tools/update_all.py
@@ -92,6 +92,7 @@
                      'kernel/uapi/asm-arm/asm/unistd.h',
                      'kernel/uapi/asm-arm/asm/unistd-eabi.h',
                      'kernel/uapi/asm-arm/asm/unistd-oabi.h',
+                     'kernel/uapi/asm-riscv/asm/unistd.h',
                      'kernel/uapi/asm-x86/asm/unistd_32.h',
                      'kernel/uapi/asm-x86/asm/unistd_64.h',
                      'kernel/uapi/asm-x86/asm/unistd_x32.h']:
diff --git a/libc/kernel/uapi/asm-arm/asm/signal.h b/libc/kernel/uapi/asm-arm/asm/signal.h
index 0424380..90cb8d6 100644
--- a/libc/kernel/uapi/asm-arm/asm/signal.h
+++ b/libc/kernel/uapi/asm-arm/asm/signal.h
@@ -76,7 +76,7 @@
 #define sa_handler _u._sa_handler
 #define sa_sigaction _u._sa_sigaction
 typedef struct sigaltstack {
-  void __user * ss_sp;
+  void  * ss_sp;
   int ss_flags;
   __kernel_size_t ss_size;
 } stack_t;
diff --git a/libc/kernel/uapi/asm-arm64/asm/hwcap.h b/libc/kernel/uapi/asm-arm64/asm/hwcap.h
index bb592e4..3ec1354 100644
--- a/libc/kernel/uapi/asm-arm64/asm/hwcap.h
+++ b/libc/kernel/uapi/asm-arm64/asm/hwcap.h
@@ -87,4 +87,10 @@
 #define HWCAP2_CSSC (1UL << 34)
 #define HWCAP2_RPRFM (1UL << 35)
 #define HWCAP2_SVE2P1 (1UL << 36)
+#define HWCAP2_SME2 (1UL << 37)
+#define HWCAP2_SME2P1 (1UL << 38)
+#define HWCAP2_SME_I16I32 (1UL << 39)
+#define HWCAP2_SME_BI32I32 (1UL << 40)
+#define HWCAP2_SME_B16B16 (1UL << 41)
+#define HWCAP2_SME_F16F16 (1UL << 42)
 #endif
diff --git a/libc/kernel/uapi/asm-arm64/asm/kvm.h b/libc/kernel/uapi/asm-arm64/asm/kvm.h
index ecc2e01..a413b36 100644
--- a/libc/kernel/uapi/asm-arm64/asm/kvm.h
+++ b/libc/kernel/uapi/asm-arm64/asm/kvm.h
@@ -74,6 +74,7 @@
 #define KVM_ARM_VCPU_SVE 4
 #define KVM_ARM_VCPU_PTRAUTH_ADDRESS 5
 #define KVM_ARM_VCPU_PTRAUTH_GENERIC 6
+#define KVM_ARM_VCPU_HAS_EL2 7
 struct kvm_vcpu_init {
   __u32 target;
   __u32 features[7];
@@ -121,7 +122,7 @@
 struct kvm_arm_copy_mte_tags {
   __u64 guest_ipa;
   __u64 length;
-  void __user * addr;
+  void  * addr;
   __u64 flags;
   __u64 reserved[2];
 };
diff --git a/libc/kernel/uapi/asm-arm64/asm/sigcontext.h b/libc/kernel/uapi/asm-arm64/asm/sigcontext.h
index 04aa593..84cd16d 100644
--- a/libc/kernel/uapi/asm-arm64/asm/sigcontext.h
+++ b/libc/kernel/uapi/asm-arm64/asm/sigcontext.h
@@ -59,12 +59,23 @@
   __u16 __reserved[2];
 };
 #define SVE_SIG_FLAG_SM 0x1
+#define TPIDR2_MAGIC 0x54504902
+struct tpidr2_context {
+  struct _aarch64_ctx head;
+  __u64 tpidr2;
+};
 #define ZA_MAGIC 0x54366345
 struct za_context {
   struct _aarch64_ctx head;
   __u16 vl;
   __u16 __reserved[3];
 };
+#define ZT_MAGIC 0x5a544e01
+struct zt_context {
+  struct _aarch64_ctx head;
+  __u16 nregs;
+  __u16 __reserved[3];
+};
 #endif
 #include <asm/sve_context.h>
 #define SVE_VQ_BYTES __SVE_VQ_BYTES
@@ -94,4 +105,9 @@
 #define ZA_SIG_REGS_SIZE(vq) ((vq * __SVE_VQ_BYTES) * (vq * __SVE_VQ_BYTES))
 #define ZA_SIG_ZAV_OFFSET(vq,n) (ZA_SIG_REGS_OFFSET + (SVE_SIG_ZREG_SIZE(vq) * n))
 #define ZA_SIG_CONTEXT_SIZE(vq) (ZA_SIG_REGS_OFFSET + ZA_SIG_REGS_SIZE(vq))
+#define ZT_SIG_REG_SIZE 512
+#define ZT_SIG_REG_BYTES (ZT_SIG_REG_SIZE / 8)
+#define ZT_SIG_REGS_OFFSET sizeof(struct zt_context)
+#define ZT_SIG_REGS_SIZE(n) (ZT_SIG_REG_BYTES * n)
+#define ZT_SIG_CONTEXT_SIZE(n) (sizeof(struct zt_context) + ZT_SIG_REGS_SIZE(n))
 #endif
diff --git a/libc/kernel/uapi/asm-generic/poll.h b/libc/kernel/uapi/asm-generic/poll.h
index 372bc77..ba6f2e9 100644
--- a/libc/kernel/uapi/asm-generic/poll.h
+++ b/libc/kernel/uapi/asm-generic/poll.h
@@ -41,8 +41,8 @@
 #ifndef POLLRDHUP
 #define POLLRDHUP 0x2000
 #endif
-#define POLLFREE (__force __poll_t) 0x4000
-#define POLL_BUSY_LOOP (__force __poll_t) 0x8000
+#define POLLFREE ( __poll_t) 0x4000
+#define POLL_BUSY_LOOP ( __poll_t) 0x8000
 struct pollfd {
   int fd;
   short events;
diff --git a/libc/kernel/uapi/asm-generic/siginfo.h b/libc/kernel/uapi/asm-generic/siginfo.h
index c5e4178..90393ba 100644
--- a/libc/kernel/uapi/asm-generic/siginfo.h
+++ b/libc/kernel/uapi/asm-generic/siginfo.h
@@ -22,7 +22,7 @@
 #include <linux/types.h>
 typedef union sigval {
   int sival_int;
-  void __user * sival_ptr;
+  void  * sival_ptr;
 } sigval_t;
 #define SI_MAX_SIZE 128
 #ifndef __ARCH_SI_BAND_T
@@ -58,7 +58,7 @@
     __ARCH_SI_CLOCK_T _stime;
   } _sigchld;
   struct {
-    void __user * _addr;
+    void  * _addr;
 #ifdef __ia64__
     int _imm;
     unsigned int _flags;
@@ -70,8 +70,8 @@
       short _addr_lsb;
       struct {
         char _dummy_bnd[__ADDR_BND_PKEY_PAD];
-        void __user * _lower;
-        void __user * _upper;
+        void  * _lower;
+        void  * _upper;
       } _addr_bnd;
       struct {
         char _dummy_pkey[__ADDR_BND_PKEY_PAD];
@@ -89,7 +89,7 @@
     int _fd;
   } _sigpoll;
   struct {
-    void __user * _call_addr;
+    void  * _call_addr;
     int _syscall;
     unsigned int _arch;
   } _sigsys;
diff --git a/libc/kernel/uapi/asm-generic/signal-defs.h b/libc/kernel/uapi/asm-generic/signal-defs.h
index c7e9504..dea8fbc 100644
--- a/libc/kernel/uapi/asm-generic/signal-defs.h
+++ b/libc/kernel/uapi/asm-generic/signal-defs.h
@@ -55,11 +55,11 @@
 #endif
 #ifndef __ASSEMBLY__
 typedef void __signalfn_t(int);
-typedef __signalfn_t __user * __sighandler_t;
+typedef __signalfn_t  * __sighandler_t;
 typedef void __restorefn_t(void);
-typedef __restorefn_t __user * __sigrestore_t;
-#define SIG_DFL ((__force __sighandler_t) 0)
-#define SIG_IGN ((__force __sighandler_t) 1)
-#define SIG_ERR ((__force __sighandler_t) - 1)
+typedef __restorefn_t  * __sigrestore_t;
+#define SIG_DFL (( __sighandler_t) 0)
+#define SIG_IGN (( __sighandler_t) 1)
+#define SIG_ERR (( __sighandler_t) - 1)
 #endif
 #endif
diff --git a/libc/kernel/uapi/asm-generic/signal.h b/libc/kernel/uapi/asm-generic/signal.h
index 5cb1dce..9cf393f 100644
--- a/libc/kernel/uapi/asm-generic/signal.h
+++ b/libc/kernel/uapi/asm-generic/signal.h
@@ -82,7 +82,7 @@
   sigset_t sa_mask;
 };
 typedef struct sigaltstack {
-  void __user * ss_sp;
+  void  * ss_sp;
   int ss_flags;
   __kernel_size_t ss_size;
 } stack_t;
diff --git a/libc/kernel/uapi/asm-riscv/asm/setup.h b/libc/kernel/uapi/asm-riscv/asm/setup.h
index 940c4db..faac9a6 100644
--- a/libc/kernel/uapi/asm-riscv/asm/setup.h
+++ b/libc/kernel/uapi/asm-riscv/asm/setup.h
@@ -16,4 +16,7 @@
  ***
  ****************************************************************************
  ****************************************************************************/
-#include <asm-generic/setup.h>
+#ifndef _UAPI_ASM_RISCV_SETUP_H
+#define _UAPI_ASM_RISCV_SETUP_H
+#define COMMAND_LINE_SIZE 1024
+#endif
diff --git a/libc/kernel/uapi/asm-x86/asm/kvm.h b/libc/kernel/uapi/asm-x86/asm/kvm.h
index 77d35fc..5c8f5a6 100644
--- a/libc/kernel/uapi/asm-x86/asm/kvm.h
+++ b/libc/kernel/uapi/asm-x86/asm/kvm.h
@@ -20,6 +20,7 @@
 #define _ASM_X86_KVM_H
 #include <linux/types.h>
 #include <linux/ioctl.h>
+#include <linux/stddef.h>
 #define KVM_PIO_PAGE_OFFSET 1
 #define KVM_COALESCED_MMIO_PAGE_OFFSET 2
 #define KVM_DIRTY_LOG_PAGE_OFFSET 64
@@ -395,8 +396,8 @@
     __u8 pad[120];
   } hdr;
   union {
-    struct kvm_vmx_nested_state_data vmx[0];
-    struct kvm_svm_nested_state_data svm[0];
+    __DECLARE_FLEX_ARRAY(struct kvm_vmx_nested_state_data, vmx);
+    __DECLARE_FLEX_ARRAY(struct kvm_svm_nested_state_data, svm);
   } data;
 };
 struct kvm_pmu_event_filter {
@@ -409,6 +410,14 @@
 };
 #define KVM_PMU_EVENT_ALLOW 0
 #define KVM_PMU_EVENT_DENY 1
+#define KVM_PMU_EVENT_FLAG_MASKED_EVENTS BIT(0)
+#define KVM_PMU_EVENT_FLAGS_VALID_MASK (KVM_PMU_EVENT_FLAG_MASKED_EVENTS)
+#define KVM_PMU_ENCODE_MASKED_ENTRY(event_select,mask,match,exclude) (((event_select) & 0xFFULL) | (((event_select) & 0XF00ULL) << 24) | (((mask) & 0xFFULL) << 56) | (((match) & 0xFFULL) << 8) | ((__u64) (! ! (exclude)) << 55))
+#define KVM_PMU_MASKED_ENTRY_EVENT_SELECT (GENMASK_ULL(7, 0) | GENMASK_ULL(35, 32))
+#define KVM_PMU_MASKED_ENTRY_UMASK_MASK (GENMASK_ULL(63, 56))
+#define KVM_PMU_MASKED_ENTRY_UMASK_MATCH (GENMASK_ULL(15, 8))
+#define KVM_PMU_MASKED_ENTRY_EXCLUDE (BIT_ULL(55))
+#define KVM_PMU_MASKED_ENTRY_UMASK_MASK_SHIFT (56)
 #define KVM_VCPU_TSC_CTRL 0
 #define KVM_VCPU_TSC_OFFSET 0
 #endif
diff --git a/libc/kernel/uapi/asm-x86/asm/sigcontext.h b/libc/kernel/uapi/asm-x86/asm/sigcontext.h
index 7d5b4d4..c790950 100644
--- a/libc/kernel/uapi/asm-x86/asm/sigcontext.h
+++ b/libc/kernel/uapi/asm-x86/asm/sigcontext.h
@@ -180,7 +180,7 @@
   __u32 eflags;
   __u32 esp_at_signal;
   __u16 ss, __ssh;
-  struct _fpstate __user * fpstate;
+  struct _fpstate  * fpstate;
   __u32 oldmask;
   __u32 cr2;
 };
@@ -215,7 +215,7 @@
   __u64 trapno;
   __u64 oldmask;
   __u64 cr2;
-  struct _fpstate __user * fpstate;
+  struct _fpstate  * fpstate;
 #ifdef __ILP32__
   __u32 __fpstate_pad;
 #endif
diff --git a/libc/kernel/uapi/asm-x86/asm/signal.h b/libc/kernel/uapi/asm-x86/asm/signal.h
index cbeeac4..37dce50 100644
--- a/libc/kernel/uapi/asm-x86/asm/signal.h
+++ b/libc/kernel/uapi/asm-x86/asm/signal.h
@@ -88,7 +88,7 @@
 };
 #endif
 typedef struct sigaltstack {
-  void __user * ss_sp;
+  void  * ss_sp;
   int ss_flags;
   __kernel_size_t ss_size;
 } stack_t;
diff --git a/libc/kernel/uapi/drm/amdgpu_drm.h b/libc/kernel/uapi/drm/amdgpu_drm.h
index fcd5ab8..8d0d0b0 100644
--- a/libc/kernel/uapi/drm/amdgpu_drm.h
+++ b/libc/kernel/uapi/drm/amdgpu_drm.h
@@ -428,6 +428,7 @@
 #define AMDGPU_IDS_FLAGS_FUSION 0x1
 #define AMDGPU_IDS_FLAGS_PREEMPTION 0x2
 #define AMDGPU_IDS_FLAGS_TMZ 0x4
+#define AMDGPU_IDS_FLAGS_CONFORMANT_TRUNC_COORD 0x8
 #define AMDGPU_INFO_ACCEL_WORKING 0x00
 #define AMDGPU_INFO_CRTC_FROM_ID 0x01
 #define AMDGPU_INFO_HW_IP_INFO 0x02
@@ -486,6 +487,8 @@
 #define AMDGPU_INFO_SENSOR_VDDGFX 0x7
 #define AMDGPU_INFO_SENSOR_STABLE_PSTATE_GFX_SCLK 0x8
 #define AMDGPU_INFO_SENSOR_STABLE_PSTATE_GFX_MCLK 0x9
+#define AMDGPU_INFO_SENSOR_PEAK_PSTATE_GFX_SCLK 0xa
+#define AMDGPU_INFO_SENSOR_PEAK_PSTATE_GFX_MCLK 0xb
 #define AMDGPU_INFO_NUM_VRAM_CPU_PAGE_FAULTS 0x1E
 #define AMDGPU_INFO_VRAM_LOST_COUNTER 0x1F
 #define AMDGPU_INFO_RAS_ENABLED_FEATURES 0x20
@@ -616,7 +619,7 @@
   __u32 enabled_rb_pipes_mask;
   __u32 num_rb_pipes;
   __u32 num_hw_gfx_contexts;
-  __u32 _pad;
+  __u32 pcie_gen;
   __u64 ids_flags;
   __u64 virtual_address_offset;
   __u64 virtual_address_max;
@@ -643,12 +646,22 @@
   __u32 gs_vgt_table_depth;
   __u32 gs_prim_buffer_depth;
   __u32 max_gs_waves_per_vgt;
-  __u32 _pad1;
+  __u32 pcie_num_lanes;
   __u32 cu_ao_bitmap[4][4];
   __u64 high_va_offset;
   __u64 high_va_max;
   __u32 pa_sc_tile_steering_override;
   __u64 tcc_disabled_mask;
+  __u64 min_engine_clock;
+  __u64 min_memory_clock;
+  __u32 tcp_cache_size;
+  __u32 num_sqc_per_wgp;
+  __u32 sqc_data_cache_size;
+  __u32 sqc_inst_cache_size;
+  __u32 gl1c_cache_size;
+  __u32 gl2c_cache_size;
+  __u64 mall_size;
+  __u32 enabled_rb_pipes_mask_hi;
 };
 struct drm_amdgpu_info_hw_ip {
   __u32 hw_ip_version_major;
diff --git a/libc/kernel/uapi/drm/drm.h b/libc/kernel/uapi/drm/drm.h
index 878e899..1954452 100644
--- a/libc/kernel/uapi/drm/drm.h
+++ b/libc/kernel/uapi/drm/drm.h
@@ -78,19 +78,19 @@
   int version_minor;
   int version_patchlevel;
   __kernel_size_t name_len;
-  char __user * name;
+  char  * name;
   __kernel_size_t date_len;
-  char __user * date;
+  char  * date;
   __kernel_size_t desc_len;
-  char __user * desc;
+  char  * desc;
 };
 struct drm_unique {
   __kernel_size_t unique_len;
-  char __user * unique;
+  char  * unique;
 };
 struct drm_list {
   int count;
-  struct drm_version __user * version;
+  struct drm_version  * version;
 };
 struct drm_block {
   int unused;
@@ -202,37 +202,37 @@
 };
 struct drm_buf_info {
   int count;
-  struct drm_buf_desc __user * list;
+  struct drm_buf_desc  * list;
 };
 struct drm_buf_free {
   int count;
-  int __user * list;
+  int  * list;
 };
 struct drm_buf_pub {
   int idx;
   int total;
   int used;
-  void __user * address;
+  void  * address;
 };
 struct drm_buf_map {
   int count;
 #ifdef __cplusplus
-  void __user * virt;
+  void  * virt;
 #else
-  void __user * __linux_virtual;
+  void  * __linux_virtual;
 #endif
-  struct drm_buf_pub __user * list;
+  struct drm_buf_pub  * list;
 };
 struct drm_dma {
   int context;
   int send_count;
-  int __user * send_indices;
-  int __user * send_sizes;
+  int  * send_indices;
+  int  * send_sizes;
   enum drm_dma_flags flags;
   int request_count;
   int request_size;
-  int __user * request_indices;
-  int __user * request_sizes;
+  int  * request_indices;
+  int  * request_sizes;
   int granted_count;
 };
 enum drm_ctx_flags {
@@ -245,7 +245,7 @@
 };
 struct drm_ctx_res {
   int count;
-  struct drm_ctx __user * contexts;
+  struct drm_ctx  * contexts;
 };
 struct drm_draw {
   drm_drawable_t handle;
diff --git a/libc/kernel/uapi/misc/habanalabs.h b/libc/kernel/uapi/drm/habanalabs_accel.h
similarity index 98%
rename from libc/kernel/uapi/misc/habanalabs.h
rename to libc/kernel/uapi/drm/habanalabs_accel.h
index b25c833..d7dccef 100644
--- a/libc/kernel/uapi/misc/habanalabs.h
+++ b/libc/kernel/uapi/drm/habanalabs_accel.h
@@ -662,6 +662,7 @@
 #define HL_INFO_ENGINE_STATUS 32
 #define HL_INFO_PAGE_FAULT_EVENT 33
 #define HL_INFO_USER_MAPPINGS 34
+#define HL_INFO_FW_GENERIC_REQ 35
 #define HL_INFO_VERSION_MAX_LEN 128
 #define HL_INFO_CARD_NAME_MAX_LEN 16
 #define HL_ENGINES_DATA_MAX_SIZE SZ_1M
@@ -872,6 +873,7 @@
     __u32 user_buffer_actual_size;
     __u32 sec_attest_nonce;
     __u32 array_size;
+    __u32 fw_sub_opcode;
   };
   __u32 pad;
 };
@@ -935,6 +937,7 @@
 #define HL_CS_FLAGS_RESERVE_SIGNALS_ONLY 0x1000
 #define HL_CS_FLAGS_UNRESERVE_SIGNALS_ONLY 0x2000
 #define HL_CS_FLAGS_ENGINE_CORE_COMMAND 0x4000
+#define HL_CS_FLAGS_FLUSH_PCI_HBW_WRITES 0x8000
 #define HL_CS_STATUS_SUCCESS 0
 #define HL_MAX_JOBS_PER_CS 512
 #define HL_ENGINE_CORE_HALT (1 << 0)
@@ -1072,8 +1075,9 @@
       __u64 device_virt_addr;
     } unmap;
     struct {
-      __u64 handle;
+      __u64 addr;
       __u64 mem_size;
+      __u64 offset;
     } export_dmabuf_fd;
   };
   __u32 op;
diff --git a/libc/kernel/uapi/drm/i810_drm.h b/libc/kernel/uapi/drm/i810_drm.h
deleted file mode 100644
index e33387d..0000000
--- a/libc/kernel/uapi/drm/i810_drm.h
+++ /dev/null
@@ -1,220 +0,0 @@
-/****************************************************************************
- ****************************************************************************
- ***
- ***   This header was automatically generated from a Linux kernel header
- ***   of the same name, to make information necessary for userspace to
- ***   call into the kernel available to libc.  It contains only constants,
- ***   structures, and macros generated from the original header, and thus,
- ***   contains no copyrightable information.
- ***
- ***   To edit the content of this header, modify the corresponding
- ***   source file (e.g. under external/kernel-headers/original/) then
- ***   run bionic/libc/kernel/tools/update_all.py
- ***
- ***   Any manual change here will be lost the next time this script will
- ***   be run. You've been warned!
- ***
- ****************************************************************************
- ****************************************************************************/
-#ifndef _I810_DRM_H_
-#define _I810_DRM_H_
-#include "drm.h"
-#ifdef __cplusplus
-extern "C" {
-#endif
-#ifndef _I810_DEFINES_
-#define _I810_DEFINES_
-#define I810_DMA_BUF_ORDER 12
-#define I810_DMA_BUF_SZ (1 << I810_DMA_BUF_ORDER)
-#define I810_DMA_BUF_NR 256
-#define I810_NR_SAREA_CLIPRECTS 8
-#define I810_NR_TEX_REGIONS 64
-#define I810_LOG_MIN_TEX_REGION_SIZE 16
-#endif
-#define I810_UPLOAD_TEX0IMAGE 0x1
-#define I810_UPLOAD_TEX1IMAGE 0x2
-#define I810_UPLOAD_CTX 0x4
-#define I810_UPLOAD_BUFFERS 0x8
-#define I810_UPLOAD_TEX0 0x10
-#define I810_UPLOAD_TEX1 0x20
-#define I810_UPLOAD_CLIPRECTS 0x40
-#define I810_DESTREG_DI0 0
-#define I810_DESTREG_DI1 1
-#define I810_DESTREG_DV0 2
-#define I810_DESTREG_DV1 3
-#define I810_DESTREG_DR0 4
-#define I810_DESTREG_DR1 5
-#define I810_DESTREG_DR2 6
-#define I810_DESTREG_DR3 7
-#define I810_DESTREG_DR4 8
-#define I810_DEST_SETUP_SIZE 10
-#define I810_CTXREG_CF0 0
-#define I810_CTXREG_CF1 1
-#define I810_CTXREG_ST0 2
-#define I810_CTXREG_ST1 3
-#define I810_CTXREG_VF 4
-#define I810_CTXREG_MT 5
-#define I810_CTXREG_MC0 6
-#define I810_CTXREG_MC1 7
-#define I810_CTXREG_MC2 8
-#define I810_CTXREG_MA0 9
-#define I810_CTXREG_MA1 10
-#define I810_CTXREG_MA2 11
-#define I810_CTXREG_SDM 12
-#define I810_CTXREG_FOG 13
-#define I810_CTXREG_B1 14
-#define I810_CTXREG_B2 15
-#define I810_CTXREG_LCS 16
-#define I810_CTXREG_PV 17
-#define I810_CTXREG_ZA 18
-#define I810_CTXREG_AA 19
-#define I810_CTX_SETUP_SIZE 20
-#define I810_TEXREG_MI0 0
-#define I810_TEXREG_MI1 1
-#define I810_TEXREG_MI2 2
-#define I810_TEXREG_MI3 3
-#define I810_TEXREG_MF 4
-#define I810_TEXREG_MLC 5
-#define I810_TEXREG_MLL 6
-#define I810_TEXREG_MCS 7
-#define I810_TEX_SETUP_SIZE 8
-#define I810_FRONT 0x1
-#define I810_BACK 0x2
-#define I810_DEPTH 0x4
-typedef enum _drm_i810_init_func {
-  I810_INIT_DMA = 0x01,
-  I810_CLEANUP_DMA = 0x02,
-  I810_INIT_DMA_1_4 = 0x03
-} drm_i810_init_func_t;
-typedef struct _drm_i810_init {
-  drm_i810_init_func_t func;
-  unsigned int mmio_offset;
-  unsigned int buffers_offset;
-  int sarea_priv_offset;
-  unsigned int ring_start;
-  unsigned int ring_end;
-  unsigned int ring_size;
-  unsigned int front_offset;
-  unsigned int back_offset;
-  unsigned int depth_offset;
-  unsigned int overlay_offset;
-  unsigned int overlay_physical;
-  unsigned int w;
-  unsigned int h;
-  unsigned int pitch;
-  unsigned int pitch_bits;
-} drm_i810_init_t;
-typedef struct _drm_i810_pre12_init {
-  drm_i810_init_func_t func;
-  unsigned int mmio_offset;
-  unsigned int buffers_offset;
-  int sarea_priv_offset;
-  unsigned int ring_start;
-  unsigned int ring_end;
-  unsigned int ring_size;
-  unsigned int front_offset;
-  unsigned int back_offset;
-  unsigned int depth_offset;
-  unsigned int w;
-  unsigned int h;
-  unsigned int pitch;
-  unsigned int pitch_bits;
-} drm_i810_pre12_init_t;
-typedef struct _drm_i810_tex_region {
-  unsigned char next, prev;
-  unsigned char in_use;
-  int age;
-} drm_i810_tex_region_t;
-typedef struct _drm_i810_sarea {
-  unsigned int ContextState[I810_CTX_SETUP_SIZE];
-  unsigned int BufferState[I810_DEST_SETUP_SIZE];
-  unsigned int TexState[2][I810_TEX_SETUP_SIZE];
-  unsigned int dirty;
-  unsigned int nbox;
-  struct drm_clip_rect boxes[I810_NR_SAREA_CLIPRECTS];
-  drm_i810_tex_region_t texList[I810_NR_TEX_REGIONS + 1];
-  int texAge;
-  int last_enqueue;
-  int last_dispatch;
-  int last_quiescent;
-  int ctxOwner;
-  int vertex_prim;
-  int pf_enabled;
-  int pf_active;
-  int pf_current_page;
-} drm_i810_sarea_t;
-#define DRM_I810_INIT 0x00
-#define DRM_I810_VERTEX 0x01
-#define DRM_I810_CLEAR 0x02
-#define DRM_I810_FLUSH 0x03
-#define DRM_I810_GETAGE 0x04
-#define DRM_I810_GETBUF 0x05
-#define DRM_I810_SWAP 0x06
-#define DRM_I810_COPY 0x07
-#define DRM_I810_DOCOPY 0x08
-#define DRM_I810_OV0INFO 0x09
-#define DRM_I810_FSTATUS 0x0a
-#define DRM_I810_OV0FLIP 0x0b
-#define DRM_I810_MC 0x0c
-#define DRM_I810_RSTATUS 0x0d
-#define DRM_I810_FLIP 0x0e
-#define DRM_IOCTL_I810_INIT DRM_IOW(DRM_COMMAND_BASE + DRM_I810_INIT, drm_i810_init_t)
-#define DRM_IOCTL_I810_VERTEX DRM_IOW(DRM_COMMAND_BASE + DRM_I810_VERTEX, drm_i810_vertex_t)
-#define DRM_IOCTL_I810_CLEAR DRM_IOW(DRM_COMMAND_BASE + DRM_I810_CLEAR, drm_i810_clear_t)
-#define DRM_IOCTL_I810_FLUSH DRM_IO(DRM_COMMAND_BASE + DRM_I810_FLUSH)
-#define DRM_IOCTL_I810_GETAGE DRM_IO(DRM_COMMAND_BASE + DRM_I810_GETAGE)
-#define DRM_IOCTL_I810_GETBUF DRM_IOWR(DRM_COMMAND_BASE + DRM_I810_GETBUF, drm_i810_dma_t)
-#define DRM_IOCTL_I810_SWAP DRM_IO(DRM_COMMAND_BASE + DRM_I810_SWAP)
-#define DRM_IOCTL_I810_COPY DRM_IOW(DRM_COMMAND_BASE + DRM_I810_COPY, drm_i810_copy_t)
-#define DRM_IOCTL_I810_DOCOPY DRM_IO(DRM_COMMAND_BASE + DRM_I810_DOCOPY)
-#define DRM_IOCTL_I810_OV0INFO DRM_IOR(DRM_COMMAND_BASE + DRM_I810_OV0INFO, drm_i810_overlay_t)
-#define DRM_IOCTL_I810_FSTATUS DRM_IO(DRM_COMMAND_BASE + DRM_I810_FSTATUS)
-#define DRM_IOCTL_I810_OV0FLIP DRM_IO(DRM_COMMAND_BASE + DRM_I810_OV0FLIP)
-#define DRM_IOCTL_I810_MC DRM_IOW(DRM_COMMAND_BASE + DRM_I810_MC, drm_i810_mc_t)
-#define DRM_IOCTL_I810_RSTATUS DRM_IO(DRM_COMMAND_BASE + DRM_I810_RSTATUS)
-#define DRM_IOCTL_I810_FLIP DRM_IO(DRM_COMMAND_BASE + DRM_I810_FLIP)
-typedef struct _drm_i810_clear {
-  int clear_color;
-  int clear_depth;
-  int flags;
-} drm_i810_clear_t;
-typedef struct _drm_i810_vertex {
-  int idx;
-  int used;
-  int discard;
-} drm_i810_vertex_t;
-typedef struct _drm_i810_copy_t {
-  int idx;
-  int used;
-  void * address;
-} drm_i810_copy_t;
-#define PR_TRIANGLES (0x0 << 18)
-#define PR_TRISTRIP_0 (0x1 << 18)
-#define PR_TRISTRIP_1 (0x2 << 18)
-#define PR_TRIFAN (0x3 << 18)
-#define PR_POLYGON (0x4 << 18)
-#define PR_LINES (0x5 << 18)
-#define PR_LINESTRIP (0x6 << 18)
-#define PR_RECTS (0x7 << 18)
-#define PR_MASK (0x7 << 18)
-typedef struct drm_i810_dma {
-  void * __linux_virtual;
-  int request_idx;
-  int request_size;
-  int granted;
-} drm_i810_dma_t;
-typedef struct _drm_i810_overlay_t {
-  unsigned int offset;
-  unsigned int physical;
-} drm_i810_overlay_t;
-typedef struct _drm_i810_mc {
-  int idx;
-  int used;
-  int num_blocks;
-  int * length;
-  unsigned int last_render;
-} drm_i810_mc_t;
-#ifdef __cplusplus
-}
-#endif
-#endif
diff --git a/libc/kernel/uapi/drm/i915_drm.h b/libc/kernel/uapi/drm/i915_drm.h
index a8982bf..794e784 100644
--- a/libc/kernel/uapi/drm/i915_drm.h
+++ b/libc/kernel/uapi/drm/i915_drm.h
@@ -287,18 +287,18 @@
   int DR1;
   int DR4;
   int num_cliprects;
-  struct drm_clip_rect __user * cliprects;
+  struct drm_clip_rect  * cliprects;
 } drm_i915_batchbuffer_t;
 typedef struct _drm_i915_cmdbuffer {
-  char __user * buf;
+  char  * buf;
   int sz;
   int DR1;
   int DR4;
   int num_cliprects;
-  struct drm_clip_rect __user * cliprects;
+  struct drm_clip_rect  * cliprects;
 } drm_i915_cmdbuffer_t;
 typedef struct drm_i915_irq_emit {
-  int __user * irq_seq;
+  int  * irq_seq;
 } drm_i915_irq_emit_t;
 typedef struct drm_i915_irq_wait {
   int irq_seq;
@@ -371,7 +371,7 @@
 #define I915_PARAM_OA_TIMESTAMP_FREQUENCY 57
 struct drm_i915_getparam {
   __s32 param;
-  int __user * value;
+  int  * value;
 };
 typedef struct drm_i915_getparam drm_i915_getparam_t;
 #define I915_SETPARAM_USE_MI_BATCHBUFFER_START 1
@@ -387,7 +387,7 @@
   int region;
   int alignment;
   int size;
-  int __user * region_offset;
+  int  * region_offset;
 } drm_i915_mem_alloc_t;
 typedef struct drm_i915_mem_free {
   int region;
diff --git a/libc/kernel/uapi/drm/ivpu_accel.h b/libc/kernel/uapi/drm/ivpu_accel.h
new file mode 100644
index 0000000..e148a5b
--- /dev/null
+++ b/libc/kernel/uapi/drm/ivpu_accel.h
@@ -0,0 +1,102 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ ***   This header was automatically generated from a Linux kernel header
+ ***   of the same name, to make information necessary for userspace to
+ ***   call into the kernel available to libc.  It contains only constants,
+ ***   structures, and macros generated from the original header, and thus,
+ ***   contains no copyrightable information.
+ ***
+ ***   To edit the content of this header, modify the corresponding
+ ***   source file (e.g. under external/kernel-headers/original/) then
+ ***   run bionic/libc/kernel/tools/update_all.py
+ ***
+ ***   Any manual change here will be lost the next time this script will
+ ***   be run. You've been warned!
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef __UAPI_IVPU_DRM_H__
+#define __UAPI_IVPU_DRM_H__
+#include "drm.h"
+#ifdef __cplusplus
+extern "C" {
+#endif
+#define DRM_IVPU_DRIVER_MAJOR 1
+#define DRM_IVPU_DRIVER_MINOR 0
+#define DRM_IVPU_GET_PARAM 0x00
+#define DRM_IVPU_SET_PARAM 0x01
+#define DRM_IVPU_BO_CREATE 0x02
+#define DRM_IVPU_BO_INFO 0x03
+#define DRM_IVPU_SUBMIT 0x05
+#define DRM_IVPU_BO_WAIT 0x06
+#define DRM_IOCTL_IVPU_GET_PARAM DRM_IOWR(DRM_COMMAND_BASE + DRM_IVPU_GET_PARAM, struct drm_ivpu_param)
+#define DRM_IOCTL_IVPU_SET_PARAM DRM_IOW(DRM_COMMAND_BASE + DRM_IVPU_SET_PARAM, struct drm_ivpu_param)
+#define DRM_IOCTL_IVPU_BO_CREATE DRM_IOWR(DRM_COMMAND_BASE + DRM_IVPU_BO_CREATE, struct drm_ivpu_bo_create)
+#define DRM_IOCTL_IVPU_BO_INFO DRM_IOWR(DRM_COMMAND_BASE + DRM_IVPU_BO_INFO, struct drm_ivpu_bo_info)
+#define DRM_IOCTL_IVPU_SUBMIT DRM_IOW(DRM_COMMAND_BASE + DRM_IVPU_SUBMIT, struct drm_ivpu_submit)
+#define DRM_IOCTL_IVPU_BO_WAIT DRM_IOWR(DRM_COMMAND_BASE + DRM_IVPU_BO_WAIT, struct drm_ivpu_bo_wait)
+#define DRM_IVPU_PARAM_DEVICE_ID 0
+#define DRM_IVPU_PARAM_DEVICE_REVISION 1
+#define DRM_IVPU_PARAM_PLATFORM_TYPE 2
+#define DRM_IVPU_PARAM_CORE_CLOCK_RATE 3
+#define DRM_IVPU_PARAM_NUM_CONTEXTS 4
+#define DRM_IVPU_PARAM_CONTEXT_BASE_ADDRESS 5
+#define DRM_IVPU_PARAM_CONTEXT_PRIORITY 6
+#define DRM_IVPU_PARAM_CONTEXT_ID 7
+#define DRM_IVPU_PARAM_FW_API_VERSION 8
+#define DRM_IVPU_PARAM_ENGINE_HEARTBEAT 9
+#define DRM_IVPU_PARAM_UNIQUE_INFERENCE_ID 10
+#define DRM_IVPU_PARAM_TILE_CONFIG 11
+#define DRM_IVPU_PARAM_SKU 12
+#define DRM_IVPU_PLATFORM_TYPE_SILICON 0
+#define DRM_IVPU_CONTEXT_PRIORITY_IDLE 0
+#define DRM_IVPU_CONTEXT_PRIORITY_NORMAL 1
+#define DRM_IVPU_CONTEXT_PRIORITY_FOCUS 2
+#define DRM_IVPU_CONTEXT_PRIORITY_REALTIME 3
+struct drm_ivpu_param {
+  __u32 param;
+  __u32 index;
+  __u64 value;
+};
+#define DRM_IVPU_BO_HIGH_MEM 0x00000001
+#define DRM_IVPU_BO_MAPPABLE 0x00000002
+#define DRM_IVPU_BO_CACHED 0x00000000
+#define DRM_IVPU_BO_UNCACHED 0x00010000
+#define DRM_IVPU_BO_WC 0x00020000
+#define DRM_IVPU_BO_CACHE_MASK 0x00030000
+#define DRM_IVPU_BO_FLAGS (DRM_IVPU_BO_HIGH_MEM | DRM_IVPU_BO_MAPPABLE | DRM_IVPU_BO_CACHE_MASK)
+struct drm_ivpu_bo_create {
+  __u64 size;
+  __u32 flags;
+  __u32 handle;
+  __u64 vpu_addr;
+};
+struct drm_ivpu_bo_info {
+  __u32 handle;
+  __u32 flags;
+  __u64 vpu_addr;
+  __u64 mmap_offset;
+  __u64 size;
+};
+#define DRM_IVPU_ENGINE_COMPUTE 0
+#define DRM_IVPU_ENGINE_COPY 1
+struct drm_ivpu_submit {
+  __u64 buffers_ptr;
+  __u32 buffer_count;
+  __u32 engine;
+  __u32 flags;
+  __u32 commands_offset;
+};
+#define DRM_IVPU_JOB_STATUS_SUCCESS 0
+struct drm_ivpu_bo_wait {
+  __u32 handle;
+  __u32 flags;
+  __s64 timeout_ns;
+  __u32 job_status;
+  __u32 pad;
+};
+#ifdef __cplusplus
+}
+#endif
+#endif
diff --git a/libc/kernel/uapi/drm/mga_drm.h b/libc/kernel/uapi/drm/mga_drm.h
deleted file mode 100644
index dc62961..0000000
--- a/libc/kernel/uapi/drm/mga_drm.h
+++ /dev/null
@@ -1,247 +0,0 @@
-/****************************************************************************
- ****************************************************************************
- ***
- ***   This header was automatically generated from a Linux kernel header
- ***   of the same name, to make information necessary for userspace to
- ***   call into the kernel available to libc.  It contains only constants,
- ***   structures, and macros generated from the original header, and thus,
- ***   contains no copyrightable information.
- ***
- ***   To edit the content of this header, modify the corresponding
- ***   source file (e.g. under external/kernel-headers/original/) then
- ***   run bionic/libc/kernel/tools/update_all.py
- ***
- ***   Any manual change here will be lost the next time this script will
- ***   be run. You've been warned!
- ***
- ****************************************************************************
- ****************************************************************************/
-#ifndef __MGA_DRM_H__
-#define __MGA_DRM_H__
-#include "drm.h"
-#ifdef __cplusplus
-extern "C" {
-#endif
-#ifndef __MGA_SAREA_DEFINES__
-#define __MGA_SAREA_DEFINES__
-#define MGA_F 0x1
-#define MGA_A 0x2
-#define MGA_S 0x4
-#define MGA_T2 0x8
-#define MGA_WARP_TGZ 0
-#define MGA_WARP_TGZF (MGA_F)
-#define MGA_WARP_TGZA (MGA_A)
-#define MGA_WARP_TGZAF (MGA_F | MGA_A)
-#define MGA_WARP_TGZS (MGA_S)
-#define MGA_WARP_TGZSF (MGA_S | MGA_F)
-#define MGA_WARP_TGZSA (MGA_S | MGA_A)
-#define MGA_WARP_TGZSAF (MGA_S | MGA_F | MGA_A)
-#define MGA_WARP_T2GZ (MGA_T2)
-#define MGA_WARP_T2GZF (MGA_T2 | MGA_F)
-#define MGA_WARP_T2GZA (MGA_T2 | MGA_A)
-#define MGA_WARP_T2GZAF (MGA_T2 | MGA_A | MGA_F)
-#define MGA_WARP_T2GZS (MGA_T2 | MGA_S)
-#define MGA_WARP_T2GZSF (MGA_T2 | MGA_S | MGA_F)
-#define MGA_WARP_T2GZSA (MGA_T2 | MGA_S | MGA_A)
-#define MGA_WARP_T2GZSAF (MGA_T2 | MGA_S | MGA_F | MGA_A)
-#define MGA_MAX_G200_PIPES 8
-#define MGA_MAX_G400_PIPES 16
-#define MGA_MAX_WARP_PIPES MGA_MAX_G400_PIPES
-#define MGA_WARP_UCODE_SIZE 32768
-#define MGA_CARD_TYPE_G200 1
-#define MGA_CARD_TYPE_G400 2
-#define MGA_CARD_TYPE_G450 3
-#define MGA_CARD_TYPE_G550 4
-#define MGA_FRONT 0x1
-#define MGA_BACK 0x2
-#define MGA_DEPTH 0x4
-#define MGA_UPLOAD_CONTEXT 0x1
-#define MGA_UPLOAD_TEX0 0x2
-#define MGA_UPLOAD_TEX1 0x4
-#define MGA_UPLOAD_PIPE 0x8
-#define MGA_UPLOAD_TEX0IMAGE 0x10
-#define MGA_UPLOAD_TEX1IMAGE 0x20
-#define MGA_UPLOAD_2D 0x40
-#define MGA_WAIT_AGE 0x80
-#define MGA_UPLOAD_CLIPRECTS 0x100
-#define MGA_BUFFER_SIZE (1 << 16)
-#define MGA_NUM_BUFFERS 128
-#define MGA_NR_SAREA_CLIPRECTS 8
-#define MGA_CARD_HEAP 0
-#define MGA_AGP_HEAP 1
-#define MGA_NR_TEX_HEAPS 2
-#define MGA_NR_TEX_REGIONS 16
-#define MGA_LOG_MIN_TEX_REGION_SIZE 16
-#define DRM_MGA_IDLE_RETRY 2048
-#endif
-typedef struct {
-  unsigned int dstorg;
-  unsigned int maccess;
-  unsigned int plnwt;
-  unsigned int dwgctl;
-  unsigned int alphactrl;
-  unsigned int fogcolor;
-  unsigned int wflag;
-  unsigned int tdualstage0;
-  unsigned int tdualstage1;
-  unsigned int fcol;
-  unsigned int stencil;
-  unsigned int stencilctl;
-} drm_mga_context_regs_t;
-typedef struct {
-  unsigned int pitch;
-} drm_mga_server_regs_t;
-typedef struct {
-  unsigned int texctl;
-  unsigned int texctl2;
-  unsigned int texfilter;
-  unsigned int texbordercol;
-  unsigned int texorg;
-  unsigned int texwidth;
-  unsigned int texheight;
-  unsigned int texorg1;
-  unsigned int texorg2;
-  unsigned int texorg3;
-  unsigned int texorg4;
-} drm_mga_texture_regs_t;
-typedef struct {
-  unsigned int head;
-  unsigned int wrap;
-} drm_mga_age_t;
-typedef struct _drm_mga_sarea {
-  drm_mga_context_regs_t context_state;
-  drm_mga_server_regs_t server_state;
-  drm_mga_texture_regs_t tex_state[2];
-  unsigned int warp_pipe;
-  unsigned int dirty;
-  unsigned int vertsize;
-  struct drm_clip_rect boxes[MGA_NR_SAREA_CLIPRECTS];
-  unsigned int nbox;
-  unsigned int req_drawable;
-  unsigned int req_draw_buffer;
-  unsigned int exported_drawable;
-  unsigned int exported_index;
-  unsigned int exported_stamp;
-  unsigned int exported_buffers;
-  unsigned int exported_nfront;
-  unsigned int exported_nback;
-  int exported_back_x, exported_front_x, exported_w;
-  int exported_back_y, exported_front_y, exported_h;
-  struct drm_clip_rect exported_boxes[MGA_NR_SAREA_CLIPRECTS];
-  unsigned int status[4];
-  unsigned int last_wrap;
-  drm_mga_age_t last_frame;
-  unsigned int last_enqueue;
-  unsigned int last_dispatch;
-  unsigned int last_quiescent;
-  struct drm_tex_region texList[MGA_NR_TEX_HEAPS][MGA_NR_TEX_REGIONS + 1];
-  unsigned int texAge[MGA_NR_TEX_HEAPS];
-  int ctxOwner;
-} drm_mga_sarea_t;
-#define DRM_MGA_INIT 0x00
-#define DRM_MGA_FLUSH 0x01
-#define DRM_MGA_RESET 0x02
-#define DRM_MGA_SWAP 0x03
-#define DRM_MGA_CLEAR 0x04
-#define DRM_MGA_VERTEX 0x05
-#define DRM_MGA_INDICES 0x06
-#define DRM_MGA_ILOAD 0x07
-#define DRM_MGA_BLIT 0x08
-#define DRM_MGA_GETPARAM 0x09
-#define DRM_MGA_SET_FENCE 0x0a
-#define DRM_MGA_WAIT_FENCE 0x0b
-#define DRM_MGA_DMA_BOOTSTRAP 0x0c
-#define DRM_IOCTL_MGA_INIT DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_INIT, drm_mga_init_t)
-#define DRM_IOCTL_MGA_FLUSH DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_FLUSH, struct drm_lock)
-#define DRM_IOCTL_MGA_RESET DRM_IO(DRM_COMMAND_BASE + DRM_MGA_RESET)
-#define DRM_IOCTL_MGA_SWAP DRM_IO(DRM_COMMAND_BASE + DRM_MGA_SWAP)
-#define DRM_IOCTL_MGA_CLEAR DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_CLEAR, drm_mga_clear_t)
-#define DRM_IOCTL_MGA_VERTEX DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_VERTEX, drm_mga_vertex_t)
-#define DRM_IOCTL_MGA_INDICES DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_INDICES, drm_mga_indices_t)
-#define DRM_IOCTL_MGA_ILOAD DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_ILOAD, drm_mga_iload_t)
-#define DRM_IOCTL_MGA_BLIT DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_BLIT, drm_mga_blit_t)
-#define DRM_IOCTL_MGA_GETPARAM DRM_IOWR(DRM_COMMAND_BASE + DRM_MGA_GETPARAM, drm_mga_getparam_t)
-#define DRM_IOCTL_MGA_SET_FENCE DRM_IOW(DRM_COMMAND_BASE + DRM_MGA_SET_FENCE, __u32)
-#define DRM_IOCTL_MGA_WAIT_FENCE DRM_IOWR(DRM_COMMAND_BASE + DRM_MGA_WAIT_FENCE, __u32)
-#define DRM_IOCTL_MGA_DMA_BOOTSTRAP DRM_IOWR(DRM_COMMAND_BASE + DRM_MGA_DMA_BOOTSTRAP, drm_mga_dma_bootstrap_t)
-typedef struct _drm_mga_warp_index {
-  int installed;
-  unsigned long phys_addr;
-  int size;
-} drm_mga_warp_index_t;
-typedef struct drm_mga_init {
-  enum {
-    MGA_INIT_DMA = 0x01,
-    MGA_CLEANUP_DMA = 0x02
-  } func;
-  unsigned long sarea_priv_offset;
-  __struct_group(, always32bit,, int chipset;
-  int sgram;
-  unsigned int maccess;
-  unsigned int fb_cpp;
-  unsigned int front_offset, front_pitch;
-  unsigned int back_offset, back_pitch;
-  unsigned int depth_cpp;
-  unsigned int depth_offset, depth_pitch;
-  unsigned int texture_offset[MGA_NR_TEX_HEAPS];
-  unsigned int texture_size[MGA_NR_TEX_HEAPS];
- );
-  unsigned long fb_offset;
-  unsigned long mmio_offset;
-  unsigned long status_offset;
-  unsigned long warp_offset;
-  unsigned long primary_offset;
-  unsigned long buffers_offset;
-} drm_mga_init_t;
-typedef struct drm_mga_dma_bootstrap {
-  unsigned long texture_handle;
-  __u32 texture_size;
-  __u32 primary_size;
-  __u32 secondary_bin_count;
-  __u32 secondary_bin_size;
-  __u32 agp_mode;
-  __u8 agp_size;
-} drm_mga_dma_bootstrap_t;
-typedef struct drm_mga_clear {
-  unsigned int flags;
-  unsigned int clear_color;
-  unsigned int clear_depth;
-  unsigned int color_mask;
-  unsigned int depth_mask;
-} drm_mga_clear_t;
-typedef struct drm_mga_vertex {
-  int idx;
-  int used;
-  int discard;
-} drm_mga_vertex_t;
-typedef struct drm_mga_indices {
-  int idx;
-  unsigned int start;
-  unsigned int end;
-  int discard;
-} drm_mga_indices_t;
-typedef struct drm_mga_iload {
-  int idx;
-  unsigned int dstorg;
-  unsigned int length;
-} drm_mga_iload_t;
-typedef struct _drm_mga_blit {
-  unsigned int planemask;
-  unsigned int srcorg;
-  unsigned int dstorg;
-  int src_pitch, dst_pitch;
-  int delta_sx, delta_sy;
-  int delta_dx, delta_dy;
-  int height, ydir;
-  int source_pitch, dest_pitch;
-} drm_mga_blit_t;
-#define MGA_PARAM_IRQ_NR 1
-#define MGA_PARAM_CARD_TYPE 2
-typedef struct drm_mga_getparam {
-  int param;
-  void __user * value;
-} drm_mga_getparam_t;
-#ifdef __cplusplus
-}
-#endif
-#endif
diff --git a/libc/kernel/uapi/drm/msm_drm.h b/libc/kernel/uapi/drm/msm_drm.h
index ad3a971..f5a4627 100644
--- a/libc/kernel/uapi/drm/msm_drm.h
+++ b/libc/kernel/uapi/drm/msm_drm.h
@@ -116,7 +116,8 @@
 #define MSM_SUBMIT_BO_READ 0x0001
 #define MSM_SUBMIT_BO_WRITE 0x0002
 #define MSM_SUBMIT_BO_DUMP 0x0004
-#define MSM_SUBMIT_BO_FLAGS (MSM_SUBMIT_BO_READ | MSM_SUBMIT_BO_WRITE | MSM_SUBMIT_BO_DUMP)
+#define MSM_SUBMIT_BO_NO_IMPLICIT 0x0008
+#define MSM_SUBMIT_BO_FLAGS (MSM_SUBMIT_BO_READ | MSM_SUBMIT_BO_WRITE | MSM_SUBMIT_BO_DUMP | MSM_SUBMIT_BO_NO_IMPLICIT)
 struct drm_msm_gem_submit_bo {
   __u32 flags;
   __u32 handle;
diff --git a/libc/kernel/uapi/drm/r128_drm.h b/libc/kernel/uapi/drm/r128_drm.h
deleted file mode 100644
index 618b6dc..0000000
--- a/libc/kernel/uapi/drm/r128_drm.h
+++ /dev/null
@@ -1,235 +0,0 @@
-/****************************************************************************
- ****************************************************************************
- ***
- ***   This header was automatically generated from a Linux kernel header
- ***   of the same name, to make information necessary for userspace to
- ***   call into the kernel available to libc.  It contains only constants,
- ***   structures, and macros generated from the original header, and thus,
- ***   contains no copyrightable information.
- ***
- ***   To edit the content of this header, modify the corresponding
- ***   source file (e.g. under external/kernel-headers/original/) then
- ***   run bionic/libc/kernel/tools/update_all.py
- ***
- ***   Any manual change here will be lost the next time this script will
- ***   be run. You've been warned!
- ***
- ****************************************************************************
- ****************************************************************************/
-#ifndef __R128_DRM_H__
-#define __R128_DRM_H__
-#include "drm.h"
-#ifdef __cplusplus
-extern "C" {
-#endif
-#ifndef __R128_SAREA_DEFINES__
-#define __R128_SAREA_DEFINES__
-#define R128_UPLOAD_CONTEXT 0x001
-#define R128_UPLOAD_SETUP 0x002
-#define R128_UPLOAD_TEX0 0x004
-#define R128_UPLOAD_TEX1 0x008
-#define R128_UPLOAD_TEX0IMAGES 0x010
-#define R128_UPLOAD_TEX1IMAGES 0x020
-#define R128_UPLOAD_CORE 0x040
-#define R128_UPLOAD_MASKS 0x080
-#define R128_UPLOAD_WINDOW 0x100
-#define R128_UPLOAD_CLIPRECTS 0x200
-#define R128_REQUIRE_QUIESCENCE 0x400
-#define R128_UPLOAD_ALL 0x7ff
-#define R128_FRONT 0x1
-#define R128_BACK 0x2
-#define R128_DEPTH 0x4
-#define R128_POINTS 0x1
-#define R128_LINES 0x2
-#define R128_LINE_STRIP 0x3
-#define R128_TRIANGLES 0x4
-#define R128_TRIANGLE_FAN 0x5
-#define R128_TRIANGLE_STRIP 0x6
-#define R128_BUFFER_SIZE 16384
-#define R128_INDEX_PRIM_OFFSET 20
-#define R128_HOSTDATA_BLIT_OFFSET 32
-#define R128_NR_SAREA_CLIPRECTS 12
-#define R128_LOCAL_TEX_HEAP 0
-#define R128_AGP_TEX_HEAP 1
-#define R128_NR_TEX_HEAPS 2
-#define R128_NR_TEX_REGIONS 64
-#define R128_LOG_TEX_GRANULARITY 16
-#define R128_NR_CONTEXT_REGS 12
-#define R128_MAX_TEXTURE_LEVELS 11
-#define R128_MAX_TEXTURE_UNITS 2
-#endif
-typedef struct {
-  unsigned int dst_pitch_offset_c;
-  unsigned int dp_gui_master_cntl_c;
-  unsigned int sc_top_left_c;
-  unsigned int sc_bottom_right_c;
-  unsigned int z_offset_c;
-  unsigned int z_pitch_c;
-  unsigned int z_sten_cntl_c;
-  unsigned int tex_cntl_c;
-  unsigned int misc_3d_state_cntl_reg;
-  unsigned int texture_clr_cmp_clr_c;
-  unsigned int texture_clr_cmp_msk_c;
-  unsigned int fog_color_c;
-  unsigned int tex_size_pitch_c;
-  unsigned int constant_color_c;
-  unsigned int pm4_vc_fpu_setup;
-  unsigned int setup_cntl;
-  unsigned int dp_write_mask;
-  unsigned int sten_ref_mask_c;
-  unsigned int plane_3d_mask_c;
-  unsigned int window_xy_offset;
-  unsigned int scale_3d_cntl;
-} drm_r128_context_regs_t;
-typedef struct {
-  unsigned int tex_cntl;
-  unsigned int tex_combine_cntl;
-  unsigned int tex_size_pitch;
-  unsigned int tex_offset[R128_MAX_TEXTURE_LEVELS];
-  unsigned int tex_border_color;
-} drm_r128_texture_regs_t;
-typedef struct drm_r128_sarea {
-  drm_r128_context_regs_t context_state;
-  drm_r128_texture_regs_t tex_state[R128_MAX_TEXTURE_UNITS];
-  unsigned int dirty;
-  unsigned int vertsize;
-  unsigned int vc_format;
-  struct drm_clip_rect boxes[R128_NR_SAREA_CLIPRECTS];
-  unsigned int nbox;
-  unsigned int last_frame;
-  unsigned int last_dispatch;
-  struct drm_tex_region tex_list[R128_NR_TEX_HEAPS][R128_NR_TEX_REGIONS + 1];
-  unsigned int tex_age[R128_NR_TEX_HEAPS];
-  int ctx_owner;
-  int pfAllowPageFlip;
-  int pfCurrentPage;
-} drm_r128_sarea_t;
-#define DRM_R128_INIT 0x00
-#define DRM_R128_CCE_START 0x01
-#define DRM_R128_CCE_STOP 0x02
-#define DRM_R128_CCE_RESET 0x03
-#define DRM_R128_CCE_IDLE 0x04
-#define DRM_R128_RESET 0x06
-#define DRM_R128_SWAP 0x07
-#define DRM_R128_CLEAR 0x08
-#define DRM_R128_VERTEX 0x09
-#define DRM_R128_INDICES 0x0a
-#define DRM_R128_BLIT 0x0b
-#define DRM_R128_DEPTH 0x0c
-#define DRM_R128_STIPPLE 0x0d
-#define DRM_R128_INDIRECT 0x0f
-#define DRM_R128_FULLSCREEN 0x10
-#define DRM_R128_CLEAR2 0x11
-#define DRM_R128_GETPARAM 0x12
-#define DRM_R128_FLIP 0x13
-#define DRM_IOCTL_R128_INIT DRM_IOW(DRM_COMMAND_BASE + DRM_R128_INIT, drm_r128_init_t)
-#define DRM_IOCTL_R128_CCE_START DRM_IO(DRM_COMMAND_BASE + DRM_R128_CCE_START)
-#define DRM_IOCTL_R128_CCE_STOP DRM_IOW(DRM_COMMAND_BASE + DRM_R128_CCE_STOP, drm_r128_cce_stop_t)
-#define DRM_IOCTL_R128_CCE_RESET DRM_IO(DRM_COMMAND_BASE + DRM_R128_CCE_RESET)
-#define DRM_IOCTL_R128_CCE_IDLE DRM_IO(DRM_COMMAND_BASE + DRM_R128_CCE_IDLE)
-#define DRM_IOCTL_R128_RESET DRM_IO(DRM_COMMAND_BASE + DRM_R128_RESET)
-#define DRM_IOCTL_R128_SWAP DRM_IO(DRM_COMMAND_BASE + DRM_R128_SWAP)
-#define DRM_IOCTL_R128_CLEAR DRM_IOW(DRM_COMMAND_BASE + DRM_R128_CLEAR, drm_r128_clear_t)
-#define DRM_IOCTL_R128_VERTEX DRM_IOW(DRM_COMMAND_BASE + DRM_R128_VERTEX, drm_r128_vertex_t)
-#define DRM_IOCTL_R128_INDICES DRM_IOW(DRM_COMMAND_BASE + DRM_R128_INDICES, drm_r128_indices_t)
-#define DRM_IOCTL_R128_BLIT DRM_IOW(DRM_COMMAND_BASE + DRM_R128_BLIT, drm_r128_blit_t)
-#define DRM_IOCTL_R128_DEPTH DRM_IOW(DRM_COMMAND_BASE + DRM_R128_DEPTH, drm_r128_depth_t)
-#define DRM_IOCTL_R128_STIPPLE DRM_IOW(DRM_COMMAND_BASE + DRM_R128_STIPPLE, drm_r128_stipple_t)
-#define DRM_IOCTL_R128_INDIRECT DRM_IOWR(DRM_COMMAND_BASE + DRM_R128_INDIRECT, drm_r128_indirect_t)
-#define DRM_IOCTL_R128_FULLSCREEN DRM_IOW(DRM_COMMAND_BASE + DRM_R128_FULLSCREEN, drm_r128_fullscreen_t)
-#define DRM_IOCTL_R128_CLEAR2 DRM_IOW(DRM_COMMAND_BASE + DRM_R128_CLEAR2, drm_r128_clear2_t)
-#define DRM_IOCTL_R128_GETPARAM DRM_IOWR(DRM_COMMAND_BASE + DRM_R128_GETPARAM, drm_r128_getparam_t)
-#define DRM_IOCTL_R128_FLIP DRM_IO(DRM_COMMAND_BASE + DRM_R128_FLIP)
-typedef struct drm_r128_init {
-  enum {
-    R128_INIT_CCE = 0x01,
-    R128_CLEANUP_CCE = 0x02
-  } func;
-  unsigned long sarea_priv_offset;
-  int is_pci;
-  int cce_mode;
-  int cce_secure;
-  int ring_size;
-  int usec_timeout;
-  unsigned int fb_bpp;
-  unsigned int front_offset, front_pitch;
-  unsigned int back_offset, back_pitch;
-  unsigned int depth_bpp;
-  unsigned int depth_offset, depth_pitch;
-  unsigned int span_offset;
-  unsigned long fb_offset;
-  unsigned long mmio_offset;
-  unsigned long ring_offset;
-  unsigned long ring_rptr_offset;
-  unsigned long buffers_offset;
-  unsigned long agp_textures_offset;
-} drm_r128_init_t;
-typedef struct drm_r128_cce_stop {
-  int flush;
-  int idle;
-} drm_r128_cce_stop_t;
-typedef struct drm_r128_clear {
-  unsigned int flags;
-  unsigned int clear_color;
-  unsigned int clear_depth;
-  unsigned int color_mask;
-  unsigned int depth_mask;
-} drm_r128_clear_t;
-typedef struct drm_r128_vertex {
-  int prim;
-  int idx;
-  int count;
-  int discard;
-} drm_r128_vertex_t;
-typedef struct drm_r128_indices {
-  int prim;
-  int idx;
-  int start;
-  int end;
-  int discard;
-} drm_r128_indices_t;
-typedef struct drm_r128_blit {
-  int idx;
-  int pitch;
-  int offset;
-  int format;
-  unsigned short x, y;
-  unsigned short width, height;
-} drm_r128_blit_t;
-typedef struct drm_r128_depth {
-  enum {
-    R128_WRITE_SPAN = 0x01,
-    R128_WRITE_PIXELS = 0x02,
-    R128_READ_SPAN = 0x03,
-    R128_READ_PIXELS = 0x04
-  } func;
-  int n;
-  int __user * x;
-  int __user * y;
-  unsigned int __user * buffer;
-  unsigned char __user * mask;
-} drm_r128_depth_t;
-typedef struct drm_r128_stipple {
-  unsigned int __user * mask;
-} drm_r128_stipple_t;
-typedef struct drm_r128_indirect {
-  int idx;
-  int start;
-  int end;
-  int discard;
-} drm_r128_indirect_t;
-typedef struct drm_r128_fullscreen {
-  enum {
-    R128_INIT_FULLSCREEN = 0x01,
-    R128_CLEANUP_FULLSCREEN = 0x02
-  } func;
-} drm_r128_fullscreen_t;
-#define R128_PARAM_IRQ_NR 1
-typedef struct drm_r128_getparam {
-  int param;
-  void __user * value;
-} drm_r128_getparam_t;
-#ifdef __cplusplus
-}
-#endif
-#endif
diff --git a/libc/kernel/uapi/drm/radeon_drm.h b/libc/kernel/uapi/drm/radeon_drm.h
index 9dc69ad..3ec6bb3 100644
--- a/libc/kernel/uapi/drm/radeon_drm.h
+++ b/libc/kernel/uapi/drm/radeon_drm.h
@@ -479,7 +479,7 @@
   unsigned int clear_depth;
   unsigned int color_mask;
   unsigned int depth_mask;
-  drm_radeon_clear_rect_t __user * depth_boxes;
+  drm_radeon_clear_rect_t  * depth_boxes;
 } drm_radeon_clear_t;
 typedef struct drm_radeon_vertex {
   int prim;
@@ -498,20 +498,20 @@
   int idx;
   int discard;
   int nr_states;
-  drm_radeon_state_t __user * state;
+  drm_radeon_state_t  * state;
   int nr_prims;
-  drm_radeon_prim_t __user * prim;
+  drm_radeon_prim_t  * prim;
 } drm_radeon_vertex2_t;
 typedef struct drm_radeon_cmd_buffer {
   int bufsz;
-  char __user * buf;
+  char  * buf;
   int nbox;
-  struct drm_clip_rect __user * boxes;
+  struct drm_clip_rect  * boxes;
 } drm_radeon_cmd_buffer_t;
 typedef struct drm_radeon_tex_image {
   unsigned int x, y;
   unsigned int width, height;
-  const void __user * data;
+  const void  * data;
 } drm_radeon_tex_image_t;
 typedef struct drm_radeon_texture {
   unsigned int offset;
@@ -519,10 +519,10 @@
   int format;
   int width;
   int height;
-  drm_radeon_tex_image_t __user * image;
+  drm_radeon_tex_image_t  * image;
 } drm_radeon_texture_t;
 typedef struct drm_radeon_stipple {
-  unsigned int __user * mask;
+  unsigned int  * mask;
 } drm_radeon_stipple_t;
 typedef struct drm_radeon_indirect {
   int idx;
@@ -552,7 +552,7 @@
 #define RADEON_PARAM_NUM_Z_PIPES 17
 typedef struct drm_radeon_getparam {
   int param;
-  void __user * value;
+  void  * value;
 } drm_radeon_getparam_t;
 #define RADEON_MEM_REGION_GART 1
 #define RADEON_MEM_REGION_FB 2
@@ -560,7 +560,7 @@
   int region;
   int alignment;
   int size;
-  int __user * region_offset;
+  int  * region_offset;
 } drm_radeon_mem_alloc_t;
 typedef struct drm_radeon_mem_free {
   int region;
@@ -572,7 +572,7 @@
   int start;
 } drm_radeon_mem_init_heap_t;
 typedef struct drm_radeon_irq_emit {
-  int __user * irq_seq;
+  int  * irq_seq;
 } drm_radeon_irq_emit_t;
 typedef struct drm_radeon_irq_wait {
   int irq_seq;
diff --git a/libc/kernel/uapi/drm/savage_drm.h b/libc/kernel/uapi/drm/savage_drm.h
deleted file mode 100644
index ae87d21..0000000
--- a/libc/kernel/uapi/drm/savage_drm.h
+++ /dev/null
@@ -1,157 +0,0 @@
-/****************************************************************************
- ****************************************************************************
- ***
- ***   This header was automatically generated from a Linux kernel header
- ***   of the same name, to make information necessary for userspace to
- ***   call into the kernel available to libc.  It contains only constants,
- ***   structures, and macros generated from the original header, and thus,
- ***   contains no copyrightable information.
- ***
- ***   To edit the content of this header, modify the corresponding
- ***   source file (e.g. under external/kernel-headers/original/) then
- ***   run bionic/libc/kernel/tools/update_all.py
- ***
- ***   Any manual change here will be lost the next time this script will
- ***   be run. You've been warned!
- ***
- ****************************************************************************
- ****************************************************************************/
-#ifndef __SAVAGE_DRM_H__
-#define __SAVAGE_DRM_H__
-#include "drm.h"
-#ifdef __cplusplus
-extern "C" {
-#endif
-#ifndef __SAVAGE_SAREA_DEFINES__
-#define __SAVAGE_SAREA_DEFINES__
-#define SAVAGE_CARD_HEAP 0
-#define SAVAGE_AGP_HEAP 1
-#define SAVAGE_NR_TEX_HEAPS 2
-#define SAVAGE_NR_TEX_REGIONS 16
-#define SAVAGE_LOG_MIN_TEX_REGION_SIZE 16
-#endif
-typedef struct _drm_savage_sarea {
-  struct drm_tex_region texList[SAVAGE_NR_TEX_HEAPS][SAVAGE_NR_TEX_REGIONS + 1];
-  unsigned int texAge[SAVAGE_NR_TEX_HEAPS];
-  int ctxOwner;
-} drm_savage_sarea_t, * drm_savage_sarea_ptr;
-#define DRM_SAVAGE_BCI_INIT 0x00
-#define DRM_SAVAGE_BCI_CMDBUF 0x01
-#define DRM_SAVAGE_BCI_EVENT_EMIT 0x02
-#define DRM_SAVAGE_BCI_EVENT_WAIT 0x03
-#define DRM_IOCTL_SAVAGE_BCI_INIT DRM_IOW(DRM_COMMAND_BASE + DRM_SAVAGE_BCI_INIT, drm_savage_init_t)
-#define DRM_IOCTL_SAVAGE_BCI_CMDBUF DRM_IOW(DRM_COMMAND_BASE + DRM_SAVAGE_BCI_CMDBUF, drm_savage_cmdbuf_t)
-#define DRM_IOCTL_SAVAGE_BCI_EVENT_EMIT DRM_IOWR(DRM_COMMAND_BASE + DRM_SAVAGE_BCI_EVENT_EMIT, drm_savage_event_emit_t)
-#define DRM_IOCTL_SAVAGE_BCI_EVENT_WAIT DRM_IOW(DRM_COMMAND_BASE + DRM_SAVAGE_BCI_EVENT_WAIT, drm_savage_event_wait_t)
-#define SAVAGE_DMA_PCI 1
-#define SAVAGE_DMA_AGP 3
-typedef struct drm_savage_init {
-  enum {
-    SAVAGE_INIT_BCI = 1,
-    SAVAGE_CLEANUP_BCI = 2
-  } func;
-  unsigned int sarea_priv_offset;
-  unsigned int cob_size;
-  unsigned int bci_threshold_lo, bci_threshold_hi;
-  unsigned int dma_type;
-  unsigned int fb_bpp;
-  unsigned int front_offset, front_pitch;
-  unsigned int back_offset, back_pitch;
-  unsigned int depth_bpp;
-  unsigned int depth_offset, depth_pitch;
-  unsigned int texture_offset;
-  unsigned int texture_size;
-  unsigned long status_offset;
-  unsigned long buffers_offset;
-  unsigned long agp_textures_offset;
-  unsigned long cmd_dma_offset;
-} drm_savage_init_t;
-typedef union drm_savage_cmd_header drm_savage_cmd_header_t;
-typedef struct drm_savage_cmdbuf {
-  drm_savage_cmd_header_t __user * cmd_addr;
-  unsigned int size;
-  unsigned int dma_idx;
-  int discard;
-  unsigned int __user * vb_addr;
-  unsigned int vb_size;
-  unsigned int vb_stride;
-  struct drm_clip_rect __user * box_addr;
-  unsigned int nbox;
-} drm_savage_cmdbuf_t;
-#define SAVAGE_WAIT_2D 0x1
-#define SAVAGE_WAIT_3D 0x2
-#define SAVAGE_WAIT_IRQ 0x4
-typedef struct drm_savage_event {
-  unsigned int count;
-  unsigned int flags;
-} drm_savage_event_emit_t, drm_savage_event_wait_t;
-#define SAVAGE_CMD_STATE 0
-#define SAVAGE_CMD_DMA_PRIM 1
-#define SAVAGE_CMD_VB_PRIM 2
-#define SAVAGE_CMD_DMA_IDX 3
-#define SAVAGE_CMD_VB_IDX 4
-#define SAVAGE_CMD_CLEAR 5
-#define SAVAGE_CMD_SWAP 6
-#define SAVAGE_PRIM_TRILIST 0
-#define SAVAGE_PRIM_TRISTRIP 1
-#define SAVAGE_PRIM_TRIFAN 2
-#define SAVAGE_PRIM_TRILIST_201 3
-#define SAVAGE_SKIP_Z 0x01
-#define SAVAGE_SKIP_W 0x02
-#define SAVAGE_SKIP_C0 0x04
-#define SAVAGE_SKIP_C1 0x08
-#define SAVAGE_SKIP_S0 0x10
-#define SAVAGE_SKIP_T0 0x20
-#define SAVAGE_SKIP_ST0 0x30
-#define SAVAGE_SKIP_S1 0x40
-#define SAVAGE_SKIP_T1 0x80
-#define SAVAGE_SKIP_ST1 0xc0
-#define SAVAGE_SKIP_ALL_S3D 0x3f
-#define SAVAGE_SKIP_ALL_S4 0xff
-#define SAVAGE_FRONT 0x1
-#define SAVAGE_BACK 0x2
-#define SAVAGE_DEPTH 0x4
-union drm_savage_cmd_header {
-  struct {
-    unsigned char cmd;
-    unsigned char pad0;
-    unsigned short pad1;
-    unsigned short pad2;
-    unsigned short pad3;
-  } cmd;
-  struct {
-    unsigned char cmd;
-    unsigned char global;
-    unsigned short count;
-    unsigned short start;
-    unsigned short pad3;
-  } state;
-  struct {
-    unsigned char cmd;
-    unsigned char prim;
-    unsigned short skip;
-    unsigned short count;
-    unsigned short start;
-  } prim;
-  struct {
-    unsigned char cmd;
-    unsigned char prim;
-    unsigned short skip;
-    unsigned short count;
-    unsigned short pad3;
-  } idx;
-  struct {
-    unsigned char cmd;
-    unsigned char pad0;
-    unsigned short pad1;
-    unsigned int flags;
-  } clear0;
-  struct {
-    unsigned int mask;
-    unsigned int value;
-  } clear1;
-};
-#ifdef __cplusplus
-}
-#endif
-#endif
diff --git a/libc/kernel/uapi/drm/sis_drm.h b/libc/kernel/uapi/drm/sis_drm.h
deleted file mode 100644
index 1606a85..0000000
--- a/libc/kernel/uapi/drm/sis_drm.h
+++ /dev/null
@@ -1,54 +0,0 @@
-/****************************************************************************
- ****************************************************************************
- ***
- ***   This header was automatically generated from a Linux kernel header
- ***   of the same name, to make information necessary for userspace to
- ***   call into the kernel available to libc.  It contains only constants,
- ***   structures, and macros generated from the original header, and thus,
- ***   contains no copyrightable information.
- ***
- ***   To edit the content of this header, modify the corresponding
- ***   source file (e.g. under external/kernel-headers/original/) then
- ***   run bionic/libc/kernel/tools/update_all.py
- ***
- ***   Any manual change here will be lost the next time this script will
- ***   be run. You've been warned!
- ***
- ****************************************************************************
- ****************************************************************************/
-#ifndef __SIS_DRM_H__
-#define __SIS_DRM_H__
-#include "drm.h"
-#ifdef __cplusplus
-extern "C" {
-#endif
-#define NOT_USED_0_3
-#define DRM_SIS_FB_ALLOC 0x04
-#define DRM_SIS_FB_FREE 0x05
-#define NOT_USED_6_12
-#define DRM_SIS_AGP_INIT 0x13
-#define DRM_SIS_AGP_ALLOC 0x14
-#define DRM_SIS_AGP_FREE 0x15
-#define DRM_SIS_FB_INIT 0x16
-#define DRM_IOCTL_SIS_FB_ALLOC DRM_IOWR(DRM_COMMAND_BASE + DRM_SIS_FB_ALLOC, drm_sis_mem_t)
-#define DRM_IOCTL_SIS_FB_FREE DRM_IOW(DRM_COMMAND_BASE + DRM_SIS_FB_FREE, drm_sis_mem_t)
-#define DRM_IOCTL_SIS_AGP_INIT DRM_IOWR(DRM_COMMAND_BASE + DRM_SIS_AGP_INIT, drm_sis_agp_t)
-#define DRM_IOCTL_SIS_AGP_ALLOC DRM_IOWR(DRM_COMMAND_BASE + DRM_SIS_AGP_ALLOC, drm_sis_mem_t)
-#define DRM_IOCTL_SIS_AGP_FREE DRM_IOW(DRM_COMMAND_BASE + DRM_SIS_AGP_FREE, drm_sis_mem_t)
-#define DRM_IOCTL_SIS_FB_INIT DRM_IOW(DRM_COMMAND_BASE + DRM_SIS_FB_INIT, drm_sis_fb_t)
-typedef struct {
-  int context;
-  unsigned long offset;
-  unsigned long size;
-  unsigned long free;
-} drm_sis_mem_t;
-typedef struct {
-  unsigned long offset, size;
-} drm_sis_agp_t;
-typedef struct {
-  unsigned long offset, size;
-} drm_sis_fb_t;
-#ifdef __cplusplus
-}
-#endif
-#endif
diff --git a/libc/kernel/uapi/drm/via_drm.h b/libc/kernel/uapi/drm/via_drm.h
deleted file mode 100644
index 9ef645a..0000000
--- a/libc/kernel/uapi/drm/via_drm.h
+++ /dev/null
@@ -1,202 +0,0 @@
-/****************************************************************************
- ****************************************************************************
- ***
- ***   This header was automatically generated from a Linux kernel header
- ***   of the same name, to make information necessary for userspace to
- ***   call into the kernel available to libc.  It contains only constants,
- ***   structures, and macros generated from the original header, and thus,
- ***   contains no copyrightable information.
- ***
- ***   To edit the content of this header, modify the corresponding
- ***   source file (e.g. under external/kernel-headers/original/) then
- ***   run bionic/libc/kernel/tools/update_all.py
- ***
- ***   Any manual change here will be lost the next time this script will
- ***   be run. You've been warned!
- ***
- ****************************************************************************
- ****************************************************************************/
-#ifndef _VIA_DRM_H_
-#define _VIA_DRM_H_
-#include "drm.h"
-#ifdef __cplusplus
-extern "C" {
-#endif
-#ifndef _VIA_DEFINES_
-#define _VIA_DEFINES_
-#define VIA_NR_SAREA_CLIPRECTS 8
-#define VIA_NR_XVMC_PORTS 10
-#define VIA_NR_XVMC_LOCKS 5
-#define VIA_MAX_CACHELINE_SIZE 64
-#define XVMCLOCKPTR(saPriv,lockNo) ((volatile struct drm_hw_lock *) (((((unsigned long) (saPriv)->XvMCLockArea) + (VIA_MAX_CACHELINE_SIZE - 1)) & ~(VIA_MAX_CACHELINE_SIZE - 1)) + VIA_MAX_CACHELINE_SIZE * (lockNo)))
-#define VIA_NR_TEX_REGIONS 64
-#define VIA_LOG_MIN_TEX_REGION_SIZE 16
-#endif
-#define VIA_UPLOAD_TEX0IMAGE 0x1
-#define VIA_UPLOAD_TEX1IMAGE 0x2
-#define VIA_UPLOAD_CTX 0x4
-#define VIA_UPLOAD_BUFFERS 0x8
-#define VIA_UPLOAD_TEX0 0x10
-#define VIA_UPLOAD_TEX1 0x20
-#define VIA_UPLOAD_CLIPRECTS 0x40
-#define VIA_UPLOAD_ALL 0xff
-#define DRM_VIA_ALLOCMEM 0x00
-#define DRM_VIA_FREEMEM 0x01
-#define DRM_VIA_AGP_INIT 0x02
-#define DRM_VIA_FB_INIT 0x03
-#define DRM_VIA_MAP_INIT 0x04
-#define DRM_VIA_DEC_FUTEX 0x05
-#define NOT_USED
-#define DRM_VIA_DMA_INIT 0x07
-#define DRM_VIA_CMDBUFFER 0x08
-#define DRM_VIA_FLUSH 0x09
-#define DRM_VIA_PCICMD 0x0a
-#define DRM_VIA_CMDBUF_SIZE 0x0b
-#define NOT_USED
-#define DRM_VIA_WAIT_IRQ 0x0d
-#define DRM_VIA_DMA_BLIT 0x0e
-#define DRM_VIA_BLIT_SYNC 0x0f
-#define DRM_IOCTL_VIA_ALLOCMEM DRM_IOWR(DRM_COMMAND_BASE + DRM_VIA_ALLOCMEM, drm_via_mem_t)
-#define DRM_IOCTL_VIA_FREEMEM DRM_IOW(DRM_COMMAND_BASE + DRM_VIA_FREEMEM, drm_via_mem_t)
-#define DRM_IOCTL_VIA_AGP_INIT DRM_IOWR(DRM_COMMAND_BASE + DRM_VIA_AGP_INIT, drm_via_agp_t)
-#define DRM_IOCTL_VIA_FB_INIT DRM_IOWR(DRM_COMMAND_BASE + DRM_VIA_FB_INIT, drm_via_fb_t)
-#define DRM_IOCTL_VIA_MAP_INIT DRM_IOWR(DRM_COMMAND_BASE + DRM_VIA_MAP_INIT, drm_via_init_t)
-#define DRM_IOCTL_VIA_DEC_FUTEX DRM_IOW(DRM_COMMAND_BASE + DRM_VIA_DEC_FUTEX, drm_via_futex_t)
-#define DRM_IOCTL_VIA_DMA_INIT DRM_IOWR(DRM_COMMAND_BASE + DRM_VIA_DMA_INIT, drm_via_dma_init_t)
-#define DRM_IOCTL_VIA_CMDBUFFER DRM_IOW(DRM_COMMAND_BASE + DRM_VIA_CMDBUFFER, drm_via_cmdbuffer_t)
-#define DRM_IOCTL_VIA_FLUSH DRM_IO(DRM_COMMAND_BASE + DRM_VIA_FLUSH)
-#define DRM_IOCTL_VIA_PCICMD DRM_IOW(DRM_COMMAND_BASE + DRM_VIA_PCICMD, drm_via_cmdbuffer_t)
-#define DRM_IOCTL_VIA_CMDBUF_SIZE DRM_IOWR(DRM_COMMAND_BASE + DRM_VIA_CMDBUF_SIZE, drm_via_cmdbuf_size_t)
-#define DRM_IOCTL_VIA_WAIT_IRQ DRM_IOWR(DRM_COMMAND_BASE + DRM_VIA_WAIT_IRQ, drm_via_irqwait_t)
-#define DRM_IOCTL_VIA_DMA_BLIT DRM_IOW(DRM_COMMAND_BASE + DRM_VIA_DMA_BLIT, drm_via_dmablit_t)
-#define DRM_IOCTL_VIA_BLIT_SYNC DRM_IOW(DRM_COMMAND_BASE + DRM_VIA_BLIT_SYNC, drm_via_blitsync_t)
-#define VIA_TEX_SETUP_SIZE 8
-#define VIA_FRONT 0x1
-#define VIA_BACK 0x2
-#define VIA_DEPTH 0x4
-#define VIA_STENCIL 0x8
-#define VIA_MEM_VIDEO 0
-#define VIA_MEM_AGP 1
-#define VIA_MEM_SYSTEM 2
-#define VIA_MEM_MIXED 3
-#define VIA_MEM_UNKNOWN 4
-typedef struct {
-  __u32 offset;
-  __u32 size;
-} drm_via_agp_t;
-typedef struct {
-  __u32 offset;
-  __u32 size;
-} drm_via_fb_t;
-typedef struct {
-  __u32 context;
-  __u32 type;
-  __u32 size;
-  unsigned long index;
-  unsigned long offset;
-} drm_via_mem_t;
-typedef struct _drm_via_init {
-  enum {
-    VIA_INIT_MAP = 0x01,
-    VIA_CLEANUP_MAP = 0x02
-  } func;
-  unsigned long sarea_priv_offset;
-  unsigned long fb_offset;
-  unsigned long mmio_offset;
-  unsigned long agpAddr;
-} drm_via_init_t;
-typedef struct _drm_via_futex {
-  enum {
-    VIA_FUTEX_WAIT = 0x00,
-    VIA_FUTEX_WAKE = 0X01
-  } func;
-  __u32 ms;
-  __u32 lock;
-  __u32 val;
-} drm_via_futex_t;
-typedef struct _drm_via_dma_init {
-  enum {
-    VIA_INIT_DMA = 0x01,
-    VIA_CLEANUP_DMA = 0x02,
-    VIA_DMA_INITIALIZED = 0x03
-  } func;
-  unsigned long offset;
-  unsigned long size;
-  unsigned long reg_pause_addr;
-} drm_via_dma_init_t;
-typedef struct _drm_via_cmdbuffer {
-  char __user * buf;
-  unsigned long size;
-} drm_via_cmdbuffer_t;
-typedef struct _drm_via_tex_region {
-  unsigned char next, prev;
-  unsigned char inUse;
-  int age;
-} drm_via_tex_region_t;
-typedef struct _drm_via_sarea {
-  unsigned int dirty;
-  unsigned int nbox;
-  struct drm_clip_rect boxes[VIA_NR_SAREA_CLIPRECTS];
-  drm_via_tex_region_t texList[VIA_NR_TEX_REGIONS + 1];
-  int texAge;
-  int ctxOwner;
-  int vertexPrim;
-  char XvMCLockArea[VIA_MAX_CACHELINE_SIZE * (VIA_NR_XVMC_LOCKS + 1)];
-  unsigned int XvMCDisplaying[VIA_NR_XVMC_PORTS];
-  unsigned int XvMCSubPicOn[VIA_NR_XVMC_PORTS];
-  unsigned int XvMCCtxNoGrabbed;
-  unsigned int pfCurrentOffset;
-} drm_via_sarea_t;
-typedef struct _drm_via_cmdbuf_size {
-  enum {
-    VIA_CMDBUF_SPACE = 0x01,
-    VIA_CMDBUF_LAG = 0x02
-  } func;
-  int wait;
-  __u32 size;
-} drm_via_cmdbuf_size_t;
-typedef enum {
-  VIA_IRQ_ABSOLUTE = 0x0,
-  VIA_IRQ_RELATIVE = 0x1,
-  VIA_IRQ_SIGNAL = 0x10000000,
-  VIA_IRQ_FORCE_SEQUENCE = 0x20000000
-} via_irq_seq_type_t;
-#define VIA_IRQ_FLAGS_MASK 0xF0000000
-enum drm_via_irqs {
-  drm_via_irq_hqv0 = 0,
-  drm_via_irq_hqv1,
-  drm_via_irq_dma0_dd,
-  drm_via_irq_dma0_td,
-  drm_via_irq_dma1_dd,
-  drm_via_irq_dma1_td,
-  drm_via_irq_num
-};
-struct drm_via_wait_irq_request {
-  unsigned irq;
-  via_irq_seq_type_t type;
-  __u32 sequence;
-  __u32 signal;
-};
-typedef union drm_via_irqwait {
-  struct drm_via_wait_irq_request request;
-  struct drm_wait_vblank_reply reply;
-} drm_via_irqwait_t;
-typedef struct drm_via_blitsync {
-  __u32 sync_handle;
-  unsigned engine;
-} drm_via_blitsync_t;
-typedef struct drm_via_dmablit {
-  __u32 num_lines;
-  __u32 line_length;
-  __u32 fb_addr;
-  __u32 fb_stride;
-  unsigned char * mem_addr;
-  __u32 mem_stride;
-  __u32 flags;
-  int to_fb;
-  drm_via_blitsync_t sync;
-} drm_via_dmablit_t;
-#ifdef __cplusplus
-}
-#endif
-#endif
diff --git a/libc/kernel/uapi/linux/android/binder.h b/libc/kernel/uapi/linux/android/binder.h
index 52f4c6b..0d1f83d 100644
--- a/libc/kernel/uapi/linux/android/binder.h
+++ b/libc/kernel/uapi/linux/android/binder.h
@@ -221,6 +221,7 @@
   BR_FAILED_REPLY = _IO('r', 17),
   BR_FROZEN_REPLY = _IO('r', 18),
   BR_ONEWAY_SPAM_SUSPECT = _IO('r', 19),
+  BR_TRANSACTION_PENDING_FROZEN = _IO('r', 20),
 };
 enum binder_driver_command_protocol {
   BC_TRANSACTION = _IOW('c', 0, struct binder_transaction_data),
diff --git a/libc/kernel/uapi/linux/atm.h b/libc/kernel/uapi/linux/atm.h
index 488fa05..72d329d 100644
--- a/libc/kernel/uapi/linux/atm.h
+++ b/libc/kernel/uapi/linux/atm.h
@@ -140,7 +140,7 @@
 struct atmif_sioc {
   int number;
   int length;
-  void __user * arg;
+  void  * arg;
 };
 typedef unsigned short atm_backend_t;
 #endif
diff --git a/libc/kernel/uapi/linux/atmdev.h b/libc/kernel/uapi/linux/atmdev.h
index 69eb240..74cdfc1 100644
--- a/libc/kernel/uapi/linux/atmdev.h
+++ b/libc/kernel/uapi/linux/atmdev.h
@@ -86,7 +86,7 @@
 #define ATM_LM_RMT_ANALOG __ATM_LM_MKRMT(__ATM_LM_ANALOG)
 struct atm_iobuf {
   int length;
-  void __user * buffer;
+  void  * buffer;
 };
 #define ATM_CI_MAX - 1
 struct atm_cirange {
diff --git a/libc/kernel/uapi/linux/auxvec.h b/libc/kernel/uapi/linux/auxvec.h
index c80c170..3ca56fc 100644
--- a/libc/kernel/uapi/linux/auxvec.h
+++ b/libc/kernel/uapi/linux/auxvec.h
@@ -41,6 +41,8 @@
 #define AT_BASE_PLATFORM 24
 #define AT_RANDOM 25
 #define AT_HWCAP2 26
+#define AT_RSEQ_FEATURE_SIZE 27
+#define AT_RSEQ_ALIGN 28
 #define AT_EXECFN 31
 #ifndef AT_MINSIGSTKSZ
 #define AT_MINSIGSTKSZ 51
diff --git a/libc/kernel/uapi/linux/batadv_packet.h b/libc/kernel/uapi/linux/batadv_packet.h
index ede53cf..9daed82 100644
--- a/libc/kernel/uapi/linux/batadv_packet.h
+++ b/libc/kernel/uapi/linux/batadv_packet.h
@@ -28,6 +28,7 @@
   BATADV_CODED = 0x02,
   BATADV_ELP = 0x03,
   BATADV_OGM2 = 0x04,
+  BATADV_MCAST = 0x05,
 #define BATADV_UNICAST_MIN 0x40
   BATADV_UNICAST = 0x40,
   BATADV_UNICAST_FRAG = 0x41,
diff --git a/libc/kernel/uapi/linux/blkpg.h b/libc/kernel/uapi/linux/blkpg.h
index fdde696..bfe504f 100644
--- a/libc/kernel/uapi/linux/blkpg.h
+++ b/libc/kernel/uapi/linux/blkpg.h
@@ -25,7 +25,7 @@
   int op;
   int flags;
   int datalen;
-  void __user * data;
+  void  * data;
 };
 #define BLKPG_ADD_PARTITION 1
 #define BLKPG_DEL_PARTITION 2
diff --git a/libc/kernel/uapi/linux/bpf.h b/libc/kernel/uapi/linux/bpf.h
index 163dd1e..4131ce4 100644
--- a/libc/kernel/uapi/linux/bpf.h
+++ b/libc/kernel/uapi/linux/bpf.h
@@ -275,6 +275,7 @@
 #define BPF_F_TEST_STATE_FREQ (1U << 3)
 #define BPF_F_SLEEPABLE (1U << 4)
 #define BPF_F_XDP_HAS_FRAGS (1U << 5)
+#define BPF_F_XDP_DEV_BOUND_ONLY (1U << 6)
 #define BPF_F_KPROBE_MULTI_RETURN (1U << 0)
 #define BPF_PSEUDO_MAP_FD 1
 #define BPF_PSEUDO_MAP_IDX 5
@@ -557,6 +558,7 @@
   BPF_F_ZERO_CSUM_TX = (1ULL << 1),
   BPF_F_DONT_FRAGMENT = (1ULL << 2),
   BPF_F_SEQ_NUMBER = (1ULL << 3),
+  BPF_F_NO_TUNNEL_KEY = (1ULL << 4),
 };
 enum {
   BPF_F_TUNINFO_FLAGS = (1ULL << 4),
@@ -583,6 +585,8 @@
   BPF_F_ADJ_ROOM_ENCAP_L4_UDP = (1ULL << 4),
   BPF_F_ADJ_ROOM_NO_CSUM_RESET = (1ULL << 5),
   BPF_F_ADJ_ROOM_ENCAP_L2_ETH = (1ULL << 6),
+  BPF_F_ADJ_ROOM_DECAP_L3_IPV4 = (1ULL << 7),
+  BPF_F_ADJ_ROOM_DECAP_L3_IPV6 = (1ULL << 8),
 };
 enum {
   BPF_ADJ_ROOM_ENCAP_L2_MASK = 0xff,
@@ -1095,6 +1099,7 @@
 enum {
   BPF_FIB_LOOKUP_DIRECT = (1U << 0),
   BPF_FIB_LOOKUP_OUTPUT = (1U << 1),
+  BPF_FIB_LOOKUP_SKIP_NEIGH = (1U << 2),
 };
 enum {
   BPF_FIB_LKUP_RET_SUCCESS,
@@ -1218,6 +1223,15 @@
   __u64 : 64;
   __u64 : 64;
 } __attribute__((aligned(8)));
+struct bpf_rb_root {
+  __u64 : 64;
+  __u64 : 64;
+} __attribute__((aligned(8)));
+struct bpf_rb_node {
+  __u64 : 64;
+  __u64 : 64;
+  __u64 : 64;
+} __attribute__((aligned(8)));
 struct bpf_sysctl {
   __u32 write;
   __u32 file_pos;
diff --git a/libc/kernel/uapi/linux/btrfs.h b/libc/kernel/uapi/linux/btrfs.h
index 8039625..5220647 100644
--- a/libc/kernel/uapi/linux/btrfs.h
+++ b/libc/kernel/uapi/linux/btrfs.h
@@ -79,7 +79,7 @@
   union {
     struct {
       __u64 size;
-      struct btrfs_qgroup_inherit __user * qgroup_inherit;
+      struct btrfs_qgroup_inherit  * qgroup_inherit;
     };
     __u64 unused[4];
   };
@@ -157,7 +157,8 @@
   __u8 uuid[BTRFS_UUID_SIZE];
   __u64 bytes_used;
   __u64 total_bytes;
-  __u64 unused[379];
+  __u8 fsid[BTRFS_UUID_SIZE];
+  __u64 unused[377];
   __u8 path[BTRFS_DEVICE_PATH_NAME_MAX];
 };
 #define BTRFS_FS_INFO_FLAG_CSUM_INFO (1 << 0)
@@ -432,7 +433,7 @@
 struct btrfs_ioctl_send_args {
   __s64 send_fd;
   __u64 clone_sources_count;
-  __u64 __user * clone_sources;
+  __u64  * clone_sources;
   __u64 parent_root;
   __u64 flags;
   __u32 version;
@@ -469,7 +470,7 @@
   __u8 align[7];
 };
 struct btrfs_ioctl_encoded_io_args {
-  const struct iovec __user * iov;
+  const struct iovec  * iov;
   unsigned long iovcnt;
   __s64 offset;
   __u64 flags;
diff --git a/libc/kernel/uapi/linux/byteorder/big_endian.h b/libc/kernel/uapi/linux/byteorder/big_endian.h
index b6c978b..82c5a4c 100644
--- a/libc/kernel/uapi/linux/byteorder/big_endian.h
+++ b/libc/kernel/uapi/linux/byteorder/big_endian.h
@@ -27,34 +27,34 @@
 #include <linux/stddef.h>
 #include <linux/types.h>
 #include <linux/swab.h>
-#define __constant_htonl(x) ((__force __be32) (__u32) (x))
-#define __constant_ntohl(x) ((__force __u32) (__be32) (x))
-#define __constant_htons(x) ((__force __be16) (__u16) (x))
-#define __constant_ntohs(x) ((__force __u16) (__be16) (x))
-#define __constant_cpu_to_le64(x) ((__force __le64) ___constant_swab64((x)))
-#define __constant_le64_to_cpu(x) ___constant_swab64((__force __u64) (__le64) (x))
-#define __constant_cpu_to_le32(x) ((__force __le32) ___constant_swab32((x)))
-#define __constant_le32_to_cpu(x) ___constant_swab32((__force __u32) (__le32) (x))
-#define __constant_cpu_to_le16(x) ((__force __le16) ___constant_swab16((x)))
-#define __constant_le16_to_cpu(x) ___constant_swab16((__force __u16) (__le16) (x))
-#define __constant_cpu_to_be64(x) ((__force __be64) (__u64) (x))
-#define __constant_be64_to_cpu(x) ((__force __u64) (__be64) (x))
-#define __constant_cpu_to_be32(x) ((__force __be32) (__u32) (x))
-#define __constant_be32_to_cpu(x) ((__force __u32) (__be32) (x))
-#define __constant_cpu_to_be16(x) ((__force __be16) (__u16) (x))
-#define __constant_be16_to_cpu(x) ((__force __u16) (__be16) (x))
-#define __cpu_to_le64(x) ((__force __le64) __swab64((x)))
-#define __le64_to_cpu(x) __swab64((__force __u64) (__le64) (x))
-#define __cpu_to_le32(x) ((__force __le32) __swab32((x)))
-#define __le32_to_cpu(x) __swab32((__force __u32) (__le32) (x))
-#define __cpu_to_le16(x) ((__force __le16) __swab16((x)))
-#define __le16_to_cpu(x) __swab16((__force __u16) (__le16) (x))
-#define __cpu_to_be64(x) ((__force __be64) (__u64) (x))
-#define __be64_to_cpu(x) ((__force __u64) (__be64) (x))
-#define __cpu_to_be32(x) ((__force __be32) (__u32) (x))
-#define __be32_to_cpu(x) ((__force __u32) (__be32) (x))
-#define __cpu_to_be16(x) ((__force __be16) (__u16) (x))
-#define __be16_to_cpu(x) ((__force __u16) (__be16) (x))
+#define __constant_htonl(x) (( __be32) (__u32) (x))
+#define __constant_ntohl(x) (( __u32) (__be32) (x))
+#define __constant_htons(x) (( __be16) (__u16) (x))
+#define __constant_ntohs(x) (( __u16) (__be16) (x))
+#define __constant_cpu_to_le64(x) (( __le64) ___constant_swab64((x)))
+#define __constant_le64_to_cpu(x) ___constant_swab64(( __u64) (__le64) (x))
+#define __constant_cpu_to_le32(x) (( __le32) ___constant_swab32((x)))
+#define __constant_le32_to_cpu(x) ___constant_swab32(( __u32) (__le32) (x))
+#define __constant_cpu_to_le16(x) (( __le16) ___constant_swab16((x)))
+#define __constant_le16_to_cpu(x) ___constant_swab16(( __u16) (__le16) (x))
+#define __constant_cpu_to_be64(x) (( __be64) (__u64) (x))
+#define __constant_be64_to_cpu(x) (( __u64) (__be64) (x))
+#define __constant_cpu_to_be32(x) (( __be32) (__u32) (x))
+#define __constant_be32_to_cpu(x) (( __u32) (__be32) (x))
+#define __constant_cpu_to_be16(x) (( __be16) (__u16) (x))
+#define __constant_be16_to_cpu(x) (( __u16) (__be16) (x))
+#define __cpu_to_le64(x) (( __le64) __swab64((x)))
+#define __le64_to_cpu(x) __swab64(( __u64) (__le64) (x))
+#define __cpu_to_le32(x) (( __le32) __swab32((x)))
+#define __le32_to_cpu(x) __swab32(( __u32) (__le32) (x))
+#define __cpu_to_le16(x) (( __le16) __swab16((x)))
+#define __le16_to_cpu(x) __swab16(( __u16) (__le16) (x))
+#define __cpu_to_be64(x) (( __be64) (__u64) (x))
+#define __be64_to_cpu(x) (( __u64) (__be64) (x))
+#define __cpu_to_be32(x) (( __be32) (__u32) (x))
+#define __be32_to_cpu(x) (( __u32) (__be32) (x))
+#define __cpu_to_be16(x) (( __be16) (__u16) (x))
+#define __be16_to_cpu(x) (( __u16) (__be16) (x))
 #define __cpu_to_le64s(x) __swab64s((x))
 #define __le64_to_cpus(x) __swab64s((x))
 #define __cpu_to_le32s(x) __swab32s((x))
diff --git a/libc/kernel/uapi/linux/byteorder/little_endian.h b/libc/kernel/uapi/linux/byteorder/little_endian.h
index a272d4d..28155b5 100644
--- a/libc/kernel/uapi/linux/byteorder/little_endian.h
+++ b/libc/kernel/uapi/linux/byteorder/little_endian.h
@@ -27,34 +27,34 @@
 #include <linux/stddef.h>
 #include <linux/types.h>
 #include <linux/swab.h>
-#define __constant_htonl(x) ((__force __be32) ___constant_swab32((x)))
-#define __constant_ntohl(x) ___constant_swab32((__force __be32) (x))
-#define __constant_htons(x) ((__force __be16) ___constant_swab16((x)))
-#define __constant_ntohs(x) ___constant_swab16((__force __be16) (x))
-#define __constant_cpu_to_le64(x) ((__force __le64) (__u64) (x))
-#define __constant_le64_to_cpu(x) ((__force __u64) (__le64) (x))
-#define __constant_cpu_to_le32(x) ((__force __le32) (__u32) (x))
-#define __constant_le32_to_cpu(x) ((__force __u32) (__le32) (x))
-#define __constant_cpu_to_le16(x) ((__force __le16) (__u16) (x))
-#define __constant_le16_to_cpu(x) ((__force __u16) (__le16) (x))
-#define __constant_cpu_to_be64(x) ((__force __be64) ___constant_swab64((x)))
-#define __constant_be64_to_cpu(x) ___constant_swab64((__force __u64) (__be64) (x))
-#define __constant_cpu_to_be32(x) ((__force __be32) ___constant_swab32((x)))
-#define __constant_be32_to_cpu(x) ___constant_swab32((__force __u32) (__be32) (x))
-#define __constant_cpu_to_be16(x) ((__force __be16) ___constant_swab16((x)))
-#define __constant_be16_to_cpu(x) ___constant_swab16((__force __u16) (__be16) (x))
-#define __cpu_to_le64(x) ((__force __le64) (__u64) (x))
-#define __le64_to_cpu(x) ((__force __u64) (__le64) (x))
-#define __cpu_to_le32(x) ((__force __le32) (__u32) (x))
-#define __le32_to_cpu(x) ((__force __u32) (__le32) (x))
-#define __cpu_to_le16(x) ((__force __le16) (__u16) (x))
-#define __le16_to_cpu(x) ((__force __u16) (__le16) (x))
-#define __cpu_to_be64(x) ((__force __be64) __swab64((x)))
-#define __be64_to_cpu(x) __swab64((__force __u64) (__be64) (x))
-#define __cpu_to_be32(x) ((__force __be32) __swab32((x)))
-#define __be32_to_cpu(x) __swab32((__force __u32) (__be32) (x))
-#define __cpu_to_be16(x) ((__force __be16) __swab16((x)))
-#define __be16_to_cpu(x) __swab16((__force __u16) (__be16) (x))
+#define __constant_htonl(x) (( __be32) ___constant_swab32((x)))
+#define __constant_ntohl(x) ___constant_swab32(( __be32) (x))
+#define __constant_htons(x) (( __be16) ___constant_swab16((x)))
+#define __constant_ntohs(x) ___constant_swab16(( __be16) (x))
+#define __constant_cpu_to_le64(x) (( __le64) (__u64) (x))
+#define __constant_le64_to_cpu(x) (( __u64) (__le64) (x))
+#define __constant_cpu_to_le32(x) (( __le32) (__u32) (x))
+#define __constant_le32_to_cpu(x) (( __u32) (__le32) (x))
+#define __constant_cpu_to_le16(x) (( __le16) (__u16) (x))
+#define __constant_le16_to_cpu(x) (( __u16) (__le16) (x))
+#define __constant_cpu_to_be64(x) (( __be64) ___constant_swab64((x)))
+#define __constant_be64_to_cpu(x) ___constant_swab64(( __u64) (__be64) (x))
+#define __constant_cpu_to_be32(x) (( __be32) ___constant_swab32((x)))
+#define __constant_be32_to_cpu(x) ___constant_swab32(( __u32) (__be32) (x))
+#define __constant_cpu_to_be16(x) (( __be16) ___constant_swab16((x)))
+#define __constant_be16_to_cpu(x) ___constant_swab16(( __u16) (__be16) (x))
+#define __cpu_to_le64(x) (( __le64) (__u64) (x))
+#define __le64_to_cpu(x) (( __u64) (__le64) (x))
+#define __cpu_to_le32(x) (( __le32) (__u32) (x))
+#define __le32_to_cpu(x) (( __u32) (__le32) (x))
+#define __cpu_to_le16(x) (( __le16) (__u16) (x))
+#define __le16_to_cpu(x) (( __u16) (__le16) (x))
+#define __cpu_to_be64(x) (( __be64) __swab64((x)))
+#define __be64_to_cpu(x) __swab64(( __u64) (__be64) (x))
+#define __cpu_to_be32(x) (( __be32) __swab32((x)))
+#define __be32_to_cpu(x) __swab32(( __u32) (__be32) (x))
+#define __cpu_to_be16(x) (( __be16) __swab16((x)))
+#define __be16_to_cpu(x) __swab16(( __u16) (__be16) (x))
 #define __cpu_to_le64s(x) do { (void) (x); } while(0)
 #define __le64_to_cpus(x) do { (void) (x); } while(0)
 #define __cpu_to_le32s(x) do { (void) (x); } while(0)
diff --git a/libc/kernel/uapi/linux/capability.h b/libc/kernel/uapi/linux/capability.h
index c1b5dbf..8f3281e 100644
--- a/libc/kernel/uapi/linux/capability.h
+++ b/libc/kernel/uapi/linux/capability.h
@@ -28,12 +28,12 @@
 typedef struct __user_cap_header_struct {
   __u32 version;
   int pid;
-} __user * cap_user_header_t;
+}  * cap_user_header_t;
 typedef struct __user_cap_data_struct {
   __u32 effective;
   __u32 permitted;
   __u32 inheritable;
-} __user * cap_user_data_t;
+}  * cap_user_data_t;
 #define VFS_CAP_REVISION_MASK 0xFF000000
 #define VFS_CAP_REVISION_SHIFT 24
 #define VFS_CAP_FLAGS_MASK ~VFS_CAP_REVISION_MASK
diff --git a/libc/kernel/uapi/linux/capi.h b/libc/kernel/uapi/linux/capi.h
index de2a839..a09f9bc 100644
--- a/libc/kernel/uapi/linux/capi.h
+++ b/libc/kernel/uapi/linux/capi.h
@@ -51,7 +51,7 @@
 #define CAPI_GET_PROFILE _IOWR('C', 0x09, struct capi_profile)
 typedef struct capi_manufacturer_cmd {
   unsigned long cmd;
-  void __user * data;
+  void  * data;
 } capi_manufacturer_cmd;
 #define CAPI_MANUFACTURER_CMD _IOWR('C', 0x20, struct capi_manufacturer_cmd)
 #define CAPI_GET_ERRCODE _IOR('C', 0x21, __u16)
diff --git a/libc/kernel/uapi/linux/cciss_ioctl.h b/libc/kernel/uapi/linux/cciss_ioctl.h
index 3e9bb3b..827e6a0 100644
--- a/libc/kernel/uapi/linux/cciss_ioctl.h
+++ b/libc/kernel/uapi/linux/cciss_ioctl.h
@@ -47,7 +47,7 @@
   RequestBlock_struct Request;
   ErrorInfo_struct error_info;
   WORD buf_size;
-  BYTE __user * buf;
+  BYTE  * buf;
 } IOCTL_Command_struct;
 typedef struct _BIG_IOCTL_Command_struct {
   LUNAddr_struct LUN_info;
@@ -55,7 +55,7 @@
   ErrorInfo_struct error_info;
   DWORD malloc_size;
   DWORD buf_size;
-  BYTE __user * buf;
+  BYTE  * buf;
 } BIG_IOCTL_Command_struct;
 typedef struct _LogvolInfo_struct {
   __u32 LunID;
diff --git a/libc/kernel/uapi/linux/cdrom.h b/libc/kernel/uapi/linux/cdrom.h
index 0fe0727..bd1d7df 100644
--- a/libc/kernel/uapi/linux/cdrom.h
+++ b/libc/kernel/uapi/linux/cdrom.h
@@ -128,7 +128,7 @@
   union cdrom_addr addr;
   __u8 addr_format;
   int nframes;
-  __u8 __user * buf;
+  __u8  * buf;
 };
 struct cdrom_multisession {
   union cdrom_addr addr;
@@ -149,16 +149,16 @@
 #define CGC_DATA_NONE 3
 struct cdrom_generic_command {
   unsigned char cmd[CDROM_PACKET_SIZE];
-  unsigned char __user * buffer;
+  unsigned char  * buffer;
   unsigned int buflen;
   int stat;
-  struct request_sense __user * sense;
+  struct request_sense  * sense;
   unsigned char data_direction;
   int quiet;
   int timeout;
   union {
-    void __user * reserved[1];
-    void __user * unused;
+    void  * reserved[1];
+    void  * unused;
   };
 };
 struct cdrom_timed_media_change_info {
diff --git a/libc/kernel/uapi/linux/chio.h b/libc/kernel/uapi/linux/chio.h
index 725e760..74f286f 100644
--- a/libc/kernel/uapi/linux/chio.h
+++ b/libc/kernel/uapi/linux/chio.h
@@ -71,7 +71,7 @@
 #define CP_INVERT 1
 struct changer_element_status {
   int ces_type;
-  unsigned char __user * ces_data;
+  unsigned char  * ces_data;
 };
 #define CESTATUS_FULL 0x01
 #define CESTATUS_IMPEXP 0x02
diff --git a/libc/kernel/uapi/linux/coda.h b/libc/kernel/uapi/linux/coda.h
index aad1b97..5795cdf 100644
--- a/libc/kernel/uapi/linux/coda.h
+++ b/libc/kernel/uapi/linux/coda.h
@@ -505,13 +505,13 @@
 };
 #define PIOCPARM_MASK 0x0000ffff
 struct ViceIoctl {
-  void __user * in;
-  void __user * out;
+  void  * in;
+  void  * out;
   u_short in_size;
   u_short out_size;
 };
 struct PioctlData {
-  const char __user * path;
+  const char  * path;
   int follow;
   struct ViceIoctl vi;
 };
diff --git a/libc/kernel/uapi/linux/comedi.h b/libc/kernel/uapi/linux/comedi.h
index e0d015a..465d1bf 100644
--- a/libc/kernel/uapi/linux/comedi.h
+++ b/libc/kernel/uapi/linux/comedi.h
@@ -244,14 +244,14 @@
 struct comedi_insn {
   unsigned int insn;
   unsigned int n;
-  unsigned int __user * data;
+  unsigned int  * data;
   unsigned int subdev;
   unsigned int chanspec;
   unsigned int unused[3];
 };
 struct comedi_insnlist {
   unsigned int n_insns;
-  struct comedi_insn __user * insns;
+  struct comedi_insn  * insns;
 };
 struct comedi_cmd {
   unsigned int subdev;
@@ -268,19 +268,19 @@
   unsigned int stop_arg;
   unsigned int * chanlist;
   unsigned int chanlist_len;
-  short __user * data;
+  short  * data;
   unsigned int data_len;
 };
 struct comedi_chaninfo {
   unsigned int subdev;
-  unsigned int __user * maxdata_list;
-  unsigned int __user * flaglist;
-  unsigned int __user * rangelist;
+  unsigned int  * maxdata_list;
+  unsigned int  * flaglist;
+  unsigned int  * rangelist;
   unsigned int unused[4];
 };
 struct comedi_rangeinfo {
   unsigned int range_type;
-  void __user * range_ptr;
+  void  * range_ptr;
 };
 struct comedi_krange {
   int min;
diff --git a/libc/kernel/uapi/linux/cxl_mem.h b/libc/kernel/uapi/linux/cxl_mem.h
index 578cefd..5a0a34e 100644
--- a/libc/kernel/uapi/linux/cxl_mem.h
+++ b/libc/kernel/uapi/linux/cxl_mem.h
@@ -37,14 +37,16 @@
 struct cxl_command_info {
   __u32 id;
   __u32 flags;
-#define CXL_MEM_COMMAND_FLAG_MASK GENMASK(0, 0)
+#define CXL_MEM_COMMAND_FLAG_MASK GENMASK(1, 0)
+#define CXL_MEM_COMMAND_FLAG_ENABLED BIT(0)
+#define CXL_MEM_COMMAND_FLAG_EXCLUSIVE BIT(1)
   __u32 size_in;
   __u32 size_out;
 };
 struct cxl_mem_query_commands {
   __u32 n_commands;
   __u32 rsvd;
-  struct cxl_command_info __user commands[];
+  struct cxl_command_info  commands[];
 };
 struct cxl_send_command {
   __u32 id;
diff --git a/libc/kernel/uapi/linux/dcbnl.h b/libc/kernel/uapi/linux/dcbnl.h
index bc88387..b2fec7b 100644
--- a/libc/kernel/uapi/linux/dcbnl.h
+++ b/libc/kernel/uapi/linux/dcbnl.h
@@ -181,6 +181,7 @@
   DCB_ATTR_IEEE_QCN_STATS,
   DCB_ATTR_DCB_BUFFER,
   DCB_ATTR_DCB_APP_TRUST_TABLE,
+  DCB_ATTR_DCB_REWR_TABLE,
   __DCB_ATTR_IEEE_MAX
 };
 #define DCB_ATTR_IEEE_MAX (__DCB_ATTR_IEEE_MAX - 1)
diff --git a/libc/kernel/uapi/linux/dlm_device.h b/libc/kernel/uapi/linux/dlm_device.h
index 5e54d2e..e1b0c6d 100644
--- a/libc/kernel/uapi/linux/dlm_device.h
+++ b/libc/kernel/uapi/linux/dlm_device.h
@@ -33,11 +33,11 @@
   __u32 parent;
   __u64 xid;
   __u64 timeout;
-  void __user * castparam;
-  void __user * castaddr;
-  void __user * bastparam;
-  void __user * bastaddr;
-  struct dlm_lksb __user * lksb;
+  void  * castparam;
+  void  * castaddr;
+  void  * bastparam;
+  void  * bastaddr;
+  struct dlm_lksb  * lksb;
   char lvb[DLM_USER_LVB_LEN];
   char name[];
 };
@@ -67,9 +67,9 @@
 struct dlm_lock_result {
   __u32 version[3];
   __u32 length;
-  void __user * user_astaddr;
-  void __user * user_astparam;
-  struct dlm_lksb __user * user_lksb;
+  void  * user_astaddr;
+  void  * user_astparam;
+  struct dlm_lksb  * user_lksb;
   struct dlm_lksb lksb;
   __u8 bast_mode;
   __u8 unused[3];
diff --git a/libc/kernel/uapi/linux/dvb/osd.h b/libc/kernel/uapi/linux/dvb/osd.h
index 84b268b..379294e 100644
--- a/libc/kernel/uapi/linux/dvb/osd.h
+++ b/libc/kernel/uapi/linux/dvb/osd.h
@@ -50,7 +50,7 @@
   int x1;
   int y1;
   int color;
-  void __user * data;
+  void  * data;
 } osd_cmd_t;
 typedef enum {
   OSD_BITMAP1,
diff --git a/libc/kernel/uapi/linux/dvb/video.h b/libc/kernel/uapi/linux/dvb/video.h
index 6577e1f..2458766 100644
--- a/libc/kernel/uapi/linux/dvb/video.h
+++ b/libc/kernel/uapi/linux/dvb/video.h
@@ -94,7 +94,7 @@
   video_displayformat_t display_format;
 };
 struct video_still_picture {
-  char __user * iFrame;
+  char  * iFrame;
   __s32 size;
 };
 typedef __u16 video_attributes_t;
diff --git a/libc/kernel/uapi/linux/elf.h b/libc/kernel/uapi/linux/elf.h
index 28c8426..e4901d1 100644
--- a/libc/kernel/uapi/linux/elf.h
+++ b/libc/kernel/uapi/linux/elf.h
@@ -366,6 +366,7 @@
 #define NT_ARM_PAC_ENABLED_KEYS 0x40a
 #define NT_ARM_SSVE 0x40b
 #define NT_ARM_ZA 0x40c
+#define NT_ARM_ZT 0x40d
 #define NT_ARC_V2 0x600
 #define NT_VMCOREDD 0x700
 #define NT_MIPS_DSP 0x800
@@ -376,6 +377,8 @@
 #define NT_LOONGARCH_LSX 0xa02
 #define NT_LOONGARCH_LASX 0xa03
 #define NT_LOONGARCH_LBT 0xa04
+#define NT_LOONGARCH_HW_BREAK 0xa05
+#define NT_LOONGARCH_HW_WATCH 0xa06
 #define NT_GNU_PROPERTY_TYPE_0 5
 typedef struct elf32_note {
   Elf32_Word n_namesz;
diff --git a/libc/kernel/uapi/linux/ethtool.h b/libc/kernel/uapi/linux/ethtool.h
index a58be6f..eec750d 100644
--- a/libc/kernel/uapi/linux/ethtool.h
+++ b/libc/kernel/uapi/linux/ethtool.h
@@ -269,6 +269,11 @@
   ETH_SS_STATS_RMON,
   ETH_SS_COUNT
 };
+enum ethtool_mac_stats_src {
+  ETHTOOL_MAC_STATS_SRC_AGGREGATE,
+  ETHTOOL_MAC_STATS_SRC_EMAC,
+  ETHTOOL_MAC_STATS_SRC_PMAC,
+};
 enum ethtool_module_power_mode_policy {
   ETHTOOL_MODULE_POWER_MODE_POLICY_HIGH = 1,
   ETHTOOL_MODULE_POWER_MODE_POLICY_AUTO,
@@ -291,6 +296,14 @@
   ETHTOOL_PODL_PSE_PW_D_STATUS_IDLE,
   ETHTOOL_PODL_PSE_PW_D_STATUS_ERROR,
 };
+enum ethtool_mm_verify_status {
+  ETHTOOL_MM_VERIFY_STATUS_UNKNOWN,
+  ETHTOOL_MM_VERIFY_STATUS_INITIAL,
+  ETHTOOL_MM_VERIFY_STATUS_VERIFYING,
+  ETHTOOL_MM_VERIFY_STATUS_SUCCEEDED,
+  ETHTOOL_MM_VERIFY_STATUS_FAILED,
+  ETHTOOL_MM_VERIFY_STATUS_DISABLED,
+};
 struct ethtool_gstrings {
   __u32 cmd;
   __u32 string_set;
@@ -419,7 +432,7 @@
     __u32 rule_cnt;
     __u32 rss_context;
   };
-  __u32 rule_locs[0];
+  __u32 rule_locs[];
 };
 struct ethtool_rxfh_indir {
   __u32 cmd;
@@ -725,6 +738,9 @@
   ETHTOOL_LINK_MODE_800000baseDR8_2_Full_BIT = 96,
   ETHTOOL_LINK_MODE_800000baseSR8_Full_BIT = 97,
   ETHTOOL_LINK_MODE_800000baseVR8_Full_BIT = 98,
+  ETHTOOL_LINK_MODE_10baseT1S_Full_BIT = 99,
+  ETHTOOL_LINK_MODE_10baseT1S_Half_BIT = 100,
+  ETHTOOL_LINK_MODE_10baseT1S_P2MP_Half_BIT = 101,
   __ETHTOOL_LINK_MODE_MASK_NBITS
 };
 #define __ETHTOOL_LINK_MODE_LEGACY_MASK(base_name) (1UL << (ETHTOOL_LINK_MODE_ ##base_name ##_BIT))
diff --git a/libc/kernel/uapi/linux/ethtool_netlink.h b/libc/kernel/uapi/linux/ethtool_netlink.h
index cc9c53c..f1ef896 100644
--- a/libc/kernel/uapi/linux/ethtool_netlink.h
+++ b/libc/kernel/uapi/linux/ethtool_netlink.h
@@ -59,6 +59,11 @@
   ETHTOOL_MSG_PSE_GET,
   ETHTOOL_MSG_PSE_SET,
   ETHTOOL_MSG_RSS_GET,
+  ETHTOOL_MSG_PLCA_GET_CFG,
+  ETHTOOL_MSG_PLCA_SET_CFG,
+  ETHTOOL_MSG_PLCA_GET_STATUS,
+  ETHTOOL_MSG_MM_GET,
+  ETHTOOL_MSG_MM_SET,
   __ETHTOOL_MSG_USER_CNT,
   ETHTOOL_MSG_USER_MAX = __ETHTOOL_MSG_USER_CNT - 1
 };
@@ -102,6 +107,11 @@
   ETHTOOL_MSG_MODULE_NTF,
   ETHTOOL_MSG_PSE_GET_REPLY,
   ETHTOOL_MSG_RSS_GET_REPLY,
+  ETHTOOL_MSG_PLCA_GET_CFG_REPLY,
+  ETHTOOL_MSG_PLCA_GET_STATUS_REPLY,
+  ETHTOOL_MSG_PLCA_NTF,
+  ETHTOOL_MSG_MM_GET_REPLY,
+  ETHTOOL_MSG_MM_NTF,
   __ETHTOOL_MSG_KERNEL_CNT,
   ETHTOOL_MSG_KERNEL_MAX = __ETHTOOL_MSG_KERNEL_CNT - 1
 };
@@ -266,6 +276,7 @@
   ETHTOOL_A_RINGS_TCP_DATA_SPLIT,
   ETHTOOL_A_RINGS_CQE_SIZE,
   ETHTOOL_A_RINGS_TX_PUSH,
+  ETHTOOL_A_RINGS_RX_PUSH,
   __ETHTOOL_A_RINGS_CNT,
   ETHTOOL_A_RINGS_MAX = (__ETHTOOL_A_RINGS_CNT - 1)
 };
@@ -310,6 +321,9 @@
   ETHTOOL_A_COALESCE_RATE_SAMPLE_INTERVAL,
   ETHTOOL_A_COALESCE_USE_CQE_MODE_TX,
   ETHTOOL_A_COALESCE_USE_CQE_MODE_RX,
+  ETHTOOL_A_COALESCE_TX_AGGR_MAX_BYTES,
+  ETHTOOL_A_COALESCE_TX_AGGR_MAX_FRAMES,
+  ETHTOOL_A_COALESCE_TX_AGGR_TIME_USECS,
   __ETHTOOL_A_COALESCE_CNT,
   ETHTOOL_A_COALESCE_MAX = (__ETHTOOL_A_COALESCE_CNT - 1)
 };
@@ -320,6 +334,7 @@
   ETHTOOL_A_PAUSE_RX,
   ETHTOOL_A_PAUSE_TX,
   ETHTOOL_A_PAUSE_STATS,
+  ETHTOOL_A_PAUSE_STATS_SRC,
   __ETHTOOL_A_PAUSE_CNT,
   ETHTOOL_A_PAUSE_MAX = (__ETHTOOL_A_PAUSE_CNT - 1)
 };
@@ -538,6 +553,7 @@
   ETHTOOL_A_STATS_HEADER,
   ETHTOOL_A_STATS_GROUPS,
   ETHTOOL_A_STATS_GRP,
+  ETHTOOL_A_STATS_SRC,
   __ETHTOOL_A_STATS_CNT,
   ETHTOOL_A_STATS_MAX = (__ETHTOOL_A_STATS_CNT - 1)
 };
@@ -635,6 +651,48 @@
   __ETHTOOL_A_RSS_CNT,
   ETHTOOL_A_RSS_MAX = (__ETHTOOL_A_RSS_CNT - 1),
 };
+enum {
+  ETHTOOL_A_PLCA_UNSPEC,
+  ETHTOOL_A_PLCA_HEADER,
+  ETHTOOL_A_PLCA_VERSION,
+  ETHTOOL_A_PLCA_ENABLED,
+  ETHTOOL_A_PLCA_STATUS,
+  ETHTOOL_A_PLCA_NODE_CNT,
+  ETHTOOL_A_PLCA_NODE_ID,
+  ETHTOOL_A_PLCA_TO_TMR,
+  ETHTOOL_A_PLCA_BURST_CNT,
+  ETHTOOL_A_PLCA_BURST_TMR,
+  __ETHTOOL_A_PLCA_CNT,
+  ETHTOOL_A_PLCA_MAX = (__ETHTOOL_A_PLCA_CNT - 1)
+};
+enum {
+  ETHTOOL_A_MM_STAT_UNSPEC,
+  ETHTOOL_A_MM_STAT_PAD,
+  ETHTOOL_A_MM_STAT_REASSEMBLY_ERRORS,
+  ETHTOOL_A_MM_STAT_SMD_ERRORS,
+  ETHTOOL_A_MM_STAT_REASSEMBLY_OK,
+  ETHTOOL_A_MM_STAT_RX_FRAG_COUNT,
+  ETHTOOL_A_MM_STAT_TX_FRAG_COUNT,
+  ETHTOOL_A_MM_STAT_HOLD_COUNT,
+  __ETHTOOL_A_MM_STAT_CNT,
+  ETHTOOL_A_MM_STAT_MAX = (__ETHTOOL_A_MM_STAT_CNT - 1)
+};
+enum {
+  ETHTOOL_A_MM_UNSPEC,
+  ETHTOOL_A_MM_HEADER,
+  ETHTOOL_A_MM_PMAC_ENABLED,
+  ETHTOOL_A_MM_TX_ENABLED,
+  ETHTOOL_A_MM_TX_ACTIVE,
+  ETHTOOL_A_MM_TX_MIN_FRAG_SIZE,
+  ETHTOOL_A_MM_RX_MIN_FRAG_SIZE,
+  ETHTOOL_A_MM_VERIFY_ENABLED,
+  ETHTOOL_A_MM_VERIFY_STATUS,
+  ETHTOOL_A_MM_VERIFY_TIME,
+  ETHTOOL_A_MM_MAX_VERIFY_TIME,
+  ETHTOOL_A_MM_STATS,
+  __ETHTOOL_A_MM_CNT,
+  ETHTOOL_A_MM_MAX = (__ETHTOOL_A_MM_CNT - 1)
+};
 #define ETHTOOL_GENL_NAME "ethtool"
 #define ETHTOOL_GENL_VERSION 1
 #define ETHTOOL_MCGRP_MONITOR_NAME "monitor"
diff --git a/libc/kernel/uapi/linux/eventpoll.h b/libc/kernel/uapi/linux/eventpoll.h
index 2a1a26a..de4c1f1 100644
--- a/libc/kernel/uapi/linux/eventpoll.h
+++ b/libc/kernel/uapi/linux/eventpoll.h
@@ -25,23 +25,23 @@
 #define EPOLL_CTL_ADD 1
 #define EPOLL_CTL_DEL 2
 #define EPOLL_CTL_MOD 3
-#define EPOLLIN (__force __poll_t) 0x00000001
-#define EPOLLPRI (__force __poll_t) 0x00000002
-#define EPOLLOUT (__force __poll_t) 0x00000004
-#define EPOLLERR (__force __poll_t) 0x00000008
-#define EPOLLHUP (__force __poll_t) 0x00000010
-#define EPOLLNVAL (__force __poll_t) 0x00000020
-#define EPOLLRDNORM (__force __poll_t) 0x00000040
-#define EPOLLRDBAND (__force __poll_t) 0x00000080
-#define EPOLLWRNORM (__force __poll_t) 0x00000100
-#define EPOLLWRBAND (__force __poll_t) 0x00000200
-#define EPOLLMSG (__force __poll_t) 0x00000400
-#define EPOLLRDHUP (__force __poll_t) 0x00002000
-#define EPOLL_URING_WAKE ((__force __poll_t) (1U << 27))
-#define EPOLLEXCLUSIVE ((__force __poll_t) (1U << 28))
-#define EPOLLWAKEUP ((__force __poll_t) (1U << 29))
-#define EPOLLONESHOT ((__force __poll_t) (1U << 30))
-#define EPOLLET ((__force __poll_t) (1U << 31))
+#define EPOLLIN ( __poll_t) 0x00000001
+#define EPOLLPRI ( __poll_t) 0x00000002
+#define EPOLLOUT ( __poll_t) 0x00000004
+#define EPOLLERR ( __poll_t) 0x00000008
+#define EPOLLHUP ( __poll_t) 0x00000010
+#define EPOLLNVAL ( __poll_t) 0x00000020
+#define EPOLLRDNORM ( __poll_t) 0x00000040
+#define EPOLLRDBAND ( __poll_t) 0x00000080
+#define EPOLLWRNORM ( __poll_t) 0x00000100
+#define EPOLLWRBAND ( __poll_t) 0x00000200
+#define EPOLLMSG ( __poll_t) 0x00000400
+#define EPOLLRDHUP ( __poll_t) 0x00002000
+#define EPOLL_URING_WAKE (( __poll_t) (1U << 27))
+#define EPOLLEXCLUSIVE (( __poll_t) (1U << 28))
+#define EPOLLWAKEUP (( __poll_t) (1U << 29))
+#define EPOLLONESHOT (( __poll_t) (1U << 30))
+#define EPOLLET (( __poll_t) (1U << 31))
 #ifdef __x86_64__
 #define EPOLL_PACKED __attribute__((packed))
 #else
diff --git a/libc/kernel/uapi/linux/fanotify.h b/libc/kernel/uapi/linux/fanotify.h
index 9815a64..f9551a8 100644
--- a/libc/kernel/uapi/linux/fanotify.h
+++ b/libc/kernel/uapi/linux/fanotify.h
@@ -113,13 +113,27 @@
   __s32 error;
   __u32 error_count;
 };
+#define FAN_RESPONSE_INFO_NONE 0
+#define FAN_RESPONSE_INFO_AUDIT_RULE 1
 struct fanotify_response {
   __s32 fd;
   __u32 response;
 };
+struct fanotify_response_info_header {
+  __u8 type;
+  __u8 pad;
+  __u16 len;
+};
+struct fanotify_response_info_audit_rule {
+  struct fanotify_response_info_header hdr;
+  __u32 rule_number;
+  __u32 subj_trust;
+  __u32 obj_trust;
+};
 #define FAN_ALLOW 0x01
 #define FAN_DENY 0x02
 #define FAN_AUDIT 0x10
+#define FAN_INFO 0x20
 #define FAN_NOFD - 1
 #define FAN_NOPIDFD FAN_NOFD
 #define FAN_EPIDFD - 2
diff --git a/libc/kernel/uapi/linux/fcntl.h b/libc/kernel/uapi/linux/fcntl.h
index a46726b..05393d5 100644
--- a/libc/kernel/uapi/linux/fcntl.h
+++ b/libc/kernel/uapi/linux/fcntl.h
@@ -34,6 +34,7 @@
 #define F_SEAL_GROW 0x0004
 #define F_SEAL_WRITE 0x0008
 #define F_SEAL_FUTURE_WRITE 0x0010
+#define F_SEAL_EXEC 0x0020
 #define F_GET_RW_HINT (F_LINUX_SPECIFIC_BASE + 11)
 #define F_SET_RW_HINT (F_LINUX_SPECIFIC_BASE + 12)
 #define F_GET_FILE_RW_HINT (F_LINUX_SPECIFIC_BASE + 13)
diff --git a/libc/kernel/uapi/linux/fd.h b/libc/kernel/uapi/linux/fd.h
index 4d72d69..dc1d444 100644
--- a/libc/kernel/uapi/linux/fd.h
+++ b/libc/kernel/uapi/linux/fd.h
@@ -175,7 +175,7 @@
 #define FD_RAW_SOFTFAILURE 0x800
 #define FD_RAW_FAILURE 0x10000
 #define FD_RAW_HARDFAILURE 0x20000
-  void __user * data;
+  void  * data;
   char * kernel_data;
   struct floppy_raw_cmd * next;
   long length;
diff --git a/libc/kernel/uapi/linux/filter.h b/libc/kernel/uapi/linux/filter.h
index d13c59d..57fe2fb 100644
--- a/libc/kernel/uapi/linux/filter.h
+++ b/libc/kernel/uapi/linux/filter.h
@@ -31,7 +31,7 @@
 };
 struct sock_fprog {
   unsigned short len;
-  struct sock_filter __user * filter;
+  struct sock_filter  * filter;
 };
 #define BPF_RVAL(code) ((code) & 0x18)
 #define BPF_A 0x10
diff --git a/libc/kernel/uapi/linux/fou.h b/libc/kernel/uapi/linux/fou.h
index a16b8c6..7b06cff 100644
--- a/libc/kernel/uapi/linux/fou.h
+++ b/libc/kernel/uapi/linux/fou.h
@@ -19,7 +19,12 @@
 #ifndef _UAPI_LINUX_FOU_H
 #define _UAPI_LINUX_FOU_H
 #define FOU_GENL_NAME "fou"
-#define FOU_GENL_VERSION 0x1
+#define FOU_GENL_VERSION 1
+enum {
+  FOU_ENCAP_UNSPEC,
+  FOU_ENCAP_DIRECT,
+  FOU_ENCAP_GUE,
+};
 enum {
   FOU_ATTR_UNSPEC,
   FOU_ATTR_PORT,
@@ -33,7 +38,7 @@
   FOU_ATTR_PEER_V6,
   FOU_ATTR_PEER_PORT,
   FOU_ATTR_IFINDEX,
-  __FOU_ATTR_MAX,
+  __FOU_ATTR_MAX
 };
 #define FOU_ATTR_MAX (__FOU_ATTR_MAX - 1)
 enum {
@@ -41,12 +46,7 @@
   FOU_CMD_ADD,
   FOU_CMD_DEL,
   FOU_CMD_GET,
-  __FOU_CMD_MAX,
-};
-enum {
-  FOU_ENCAP_UNSPEC,
-  FOU_ENCAP_DIRECT,
-  FOU_ENCAP_GUE,
+  __FOU_CMD_MAX
 };
 #define FOU_CMD_MAX (__FOU_CMD_MAX - 1)
 #endif
diff --git a/libc/kernel/uapi/linux/fs.h b/libc/kernel/uapi/linux/fs.h
index 96f9181..b8bfaac 100644
--- a/libc/kernel/uapi/linux/fs.h
+++ b/libc/kernel/uapi/linux/fs.h
@@ -190,10 +190,10 @@
 #define SYNC_FILE_RANGE_WAIT_AFTER 4
 #define SYNC_FILE_RANGE_WRITE_AND_WAIT (SYNC_FILE_RANGE_WRITE | SYNC_FILE_RANGE_WAIT_BEFORE | SYNC_FILE_RANGE_WAIT_AFTER)
 typedef int __bitwise __kernel_rwf_t;
-#define RWF_HIPRI ((__force __kernel_rwf_t) 0x00000001)
-#define RWF_DSYNC ((__force __kernel_rwf_t) 0x00000002)
-#define RWF_SYNC ((__force __kernel_rwf_t) 0x00000004)
-#define RWF_NOWAIT ((__force __kernel_rwf_t) 0x00000008)
-#define RWF_APPEND ((__force __kernel_rwf_t) 0x00000010)
+#define RWF_HIPRI (( __kernel_rwf_t) 0x00000001)
+#define RWF_DSYNC (( __kernel_rwf_t) 0x00000002)
+#define RWF_SYNC (( __kernel_rwf_t) 0x00000004)
+#define RWF_NOWAIT (( __kernel_rwf_t) 0x00000008)
+#define RWF_APPEND (( __kernel_rwf_t) 0x00000010)
 #define RWF_SUPPORTED (RWF_HIPRI | RWF_DSYNC | RWF_SYNC | RWF_NOWAIT | RWF_APPEND)
 #endif
diff --git a/libc/kernel/uapi/linux/fuse.h b/libc/kernel/uapi/linux/fuse.h
index f1eec4d..c3668e7 100644
--- a/libc/kernel/uapi/linux/fuse.h
+++ b/libc/kernel/uapi/linux/fuse.h
@@ -111,6 +111,7 @@
 #define FUSE_INIT_RESERVED (1 << 31)
 #define FUSE_SECURITY_CTX (1ULL << 32)
 #define FUSE_HAS_INODE_DAX (1ULL << 33)
+#define FUSE_CREATE_SUPP_GROUP (1ULL << 34)
 #if FUSE_KERNEL_VERSION > 7 || FUSE_KERNEL_VERSION == 7 && FUSE_KERNEL_MINOR_VERSION >= 36
 #define FUSE_PASSTHROUGH (1ULL << 63)
 #else
@@ -140,6 +141,10 @@
 #define FUSE_OPEN_KILL_SUIDGID (1 << 0)
 #define FUSE_SETXATTR_ACL_KILL_SGID (1 << 0)
 #define FUSE_EXPIRE_ONLY (1 << 0)
+enum fuse_ext_type {
+  FUSE_MAX_NR_SECCTX = 31,
+  FUSE_EXT_GROUPS = 32,
+};
 enum fuse_opcode {
   FUSE_LOOKUP = 1,
   FUSE_FORGET = 2,
@@ -465,7 +470,8 @@
   uint32_t uid;
   uint32_t gid;
   uint32_t pid;
-  uint32_t padding;
+  uint16_t total_extlen;
+  uint16_t padding;
 };
 struct fuse_out_header {
   uint32_t len;
@@ -575,4 +581,12 @@
   uint32_t size;
   uint32_t nr_secctx;
 };
+struct fuse_ext_header {
+  uint32_t size;
+  uint32_t type;
+};
+struct fuse_supp_groups {
+  uint32_t nr_groups;
+  uint32_t groups[];
+};
 #endif
diff --git a/libc/kernel/uapi/linux/futex.h b/libc/kernel/uapi/linux/futex.h
index c80b90c..8d1a2a4 100644
--- a/libc/kernel/uapi/linux/futex.h
+++ b/libc/kernel/uapi/linux/futex.h
@@ -59,12 +59,12 @@
   __u32 __reserved;
 };
 struct robust_list {
-  struct robust_list __user * next;
+  struct robust_list  * next;
 };
 struct robust_list_head {
   struct robust_list list;
   long futex_offset;
-  struct robust_list __user * list_op_pending;
+  struct robust_list  * list_op_pending;
 };
 #define FUTEX_WAITERS 0x80000000
 #define FUTEX_OWNER_DIED 0x40000000
diff --git a/libc/kernel/uapi/linux/gsmmux.h b/libc/kernel/uapi/linux/gsmmux.h
index 4e6920a..6ddf1b9 100644
--- a/libc/kernel/uapi/linux/gsmmux.h
+++ b/libc/kernel/uapi/linux/gsmmux.h
@@ -47,4 +47,10 @@
 #define GSMIOC_ENABLE_NET _IOW('G', 2, struct gsm_netconfig)
 #define GSMIOC_DISABLE_NET _IO('G', 3)
 #define GSMIOC_GETFIRST _IOR('G', 4, __u32)
+struct gsm_config_ext {
+  __u32 keep_alive;
+  __u32 reserved[7];
+};
+#define GSMIOC_GETCONF_EXT _IOR('G', 5, struct gsm_config_ext)
+#define GSMIOC_SETCONF_EXT _IOW('G', 6, struct gsm_config_ext)
 #endif
diff --git a/libc/kernel/uapi/linux/i2c-dev.h b/libc/kernel/uapi/linux/i2c-dev.h
index 07fdda2..7a25e20 100644
--- a/libc/kernel/uapi/linux/i2c-dev.h
+++ b/libc/kernel/uapi/linux/i2c-dev.h
@@ -33,10 +33,10 @@
   __u8 read_write;
   __u8 command;
   __u32 size;
-  union i2c_smbus_data __user * data;
+  union i2c_smbus_data  * data;
 };
 struct i2c_rdwr_ioctl_data {
-  struct i2c_msg __user * msgs;
+  struct i2c_msg  * msgs;
   __u32 nmsgs;
 };
 #define I2C_RDWR_IOCTL_MAX_MSGS 42
diff --git a/libc/kernel/uapi/linux/i2o-dev.h b/libc/kernel/uapi/linux/i2o-dev.h
index fc8b26d..afaae74 100644
--- a/libc/kernel/uapi/linux/i2o-dev.h
+++ b/libc/kernel/uapi/linux/i2o-dev.h
@@ -42,38 +42,38 @@
 };
 struct i2o_cmd_passthru {
   unsigned int iop;
-  void __user * msg;
+  void  * msg;
 };
 struct i2o_cmd_hrtlct {
   unsigned int iop;
-  void __user * resbuf;
-  unsigned int __user * reslen;
+  void  * resbuf;
+  unsigned int  * reslen;
 };
 struct i2o_cmd_psetget {
   unsigned int iop;
   unsigned int tid;
-  void __user * opbuf;
+  void  * opbuf;
   unsigned int oplen;
-  void __user * resbuf;
-  unsigned int __user * reslen;
+  void  * resbuf;
+  unsigned int  * reslen;
 };
 struct i2o_sw_xfer {
   unsigned int iop;
   unsigned char flags;
   unsigned char sw_type;
   unsigned int sw_id;
-  void __user * buf;
-  unsigned int __user * swlen;
-  unsigned int __user * maxfrag;
-  unsigned int __user * curfrag;
+  void  * buf;
+  unsigned int  * swlen;
+  unsigned int  * maxfrag;
+  unsigned int  * curfrag;
 };
 struct i2o_html {
   unsigned int iop;
   unsigned int tid;
   unsigned int page;
-  void __user * resbuf;
-  unsigned int __user * reslen;
-  void __user * qbuf;
+  void  * resbuf;
+  unsigned int  * reslen;
+  void  * qbuf;
   unsigned int qlen;
 };
 #define I2O_EVT_Q_LEN 32
diff --git a/libc/kernel/uapi/linux/if.h b/libc/kernel/uapi/linux/if.h
index 63c77eb..fc6d20d 100644
--- a/libc/kernel/uapi/linux/if.h
+++ b/libc/kernel/uapi/linux/if.h
@@ -130,14 +130,14 @@
   unsigned int type;
   unsigned int size;
   union {
-    raw_hdlc_proto __user * raw_hdlc;
-    cisco_proto __user * cisco;
-    fr_proto __user * fr;
-    fr_proto_pvc __user * fr_pvc;
-    fr_proto_pvc_info __user * fr_pvc_info;
-    x25_hdlc_proto __user * x25;
-    sync_serial_settings __user * sync;
-    te1_settings __user * te1;
+    raw_hdlc_proto  * raw_hdlc;
+    cisco_proto  * cisco;
+    fr_proto  * fr;
+    fr_proto_pvc  * fr_pvc;
+    fr_proto_pvc_info  * fr_pvc_info;
+    x25_hdlc_proto  * x25;
+    sync_serial_settings  * sync;
+    te1_settings  * te1;
   } ifs_ifsu;
 };
 #if __UAPI_DEF_IF_IFREQ
@@ -158,7 +158,7 @@
     struct ifmap ifru_map;
     char ifru_slave[IFNAMSIZ];
     char ifru_newname[IFNAMSIZ];
-    void __user * ifru_data;
+    void  * ifru_data;
     struct if_settings ifru_settings;
   } ifr_ifru;
 };
@@ -184,8 +184,8 @@
 struct ifconf {
   int ifc_len;
   union {
-    char __user * ifcu_buf;
-    struct ifreq __user * ifcu_req;
+    char  * ifcu_buf;
+    struct ifreq  * ifcu_req;
   } ifc_ifcu;
 };
 #endif
diff --git a/libc/kernel/uapi/linux/if_bridge.h b/libc/kernel/uapi/linux/if_bridge.h
index 702363e..48f6345 100644
--- a/libc/kernel/uapi/linux/if_bridge.h
+++ b/libc/kernel/uapi/linux/if_bridge.h
@@ -435,6 +435,8 @@
   BRIDGE_VLANDB_ENTRY_TUNNEL_INFO,
   BRIDGE_VLANDB_ENTRY_STATS,
   BRIDGE_VLANDB_ENTRY_MCAST_ROUTER,
+  BRIDGE_VLANDB_ENTRY_MCAST_N_GROUPS,
+  BRIDGE_VLANDB_ENTRY_MCAST_MAX_GROUPS,
   __BRIDGE_VLANDB_ENTRY_MAX,
 };
 #define BRIDGE_VLANDB_ENTRY_MAX (__BRIDGE_VLANDB_ENTRY_MAX - 1)
diff --git a/libc/kernel/uapi/linux/if_link.h b/libc/kernel/uapi/linux/if_link.h
index 19c6346..fbb933b 100644
--- a/libc/kernel/uapi/linux/if_link.h
+++ b/libc/kernel/uapi/linux/if_link.h
@@ -167,6 +167,8 @@
   IFLA_TSO_MAX_SEGS,
   IFLA_ALLMULTI,
   IFLA_DEVLINK_PORT,
+  IFLA_GSO_IPV4_MAX_SIZE,
+  IFLA_GRO_IPV4_MAX_SIZE,
   __IFLA_MAX
 };
 #define IFLA_MAX (__IFLA_MAX - 1)
@@ -307,6 +309,8 @@
   IFLA_BRPORT_MCAST_EHT_HOSTS_CNT,
   IFLA_BRPORT_LOCKED,
   IFLA_BRPORT_MAB,
+  IFLA_BRPORT_MCAST_N_GROUPS,
+  IFLA_BRPORT_MCAST_MAX_GROUPS,
   __IFLA_BRPORT_MAX
 };
 #define IFLA_BRPORT_MAX (__IFLA_BRPORT_MAX - 1)
diff --git a/libc/kernel/uapi/linux/if_packet.h b/libc/kernel/uapi/linux/if_packet.h
index 340b2ee..719f596 100644
--- a/libc/kernel/uapi/linux/if_packet.h
+++ b/libc/kernel/uapi/linux/if_packet.h
@@ -113,6 +113,7 @@
 #define TP_STATUS_BLK_TMO (1 << 5)
 #define TP_STATUS_VLAN_TPID_VALID (1 << 6)
 #define TP_STATUS_CSUM_VALID (1 << 7)
+#define TP_STATUS_GSO_TCP (1 << 8)
 #define TP_STATUS_AVAILABLE 0
 #define TP_STATUS_SEND_REQUEST (1 << 0)
 #define TP_STATUS_SENDING (1 << 1)
diff --git a/libc/kernel/uapi/linux/if_tunnel.h b/libc/kernel/uapi/linux/if_tunnel.h
index 01c2dc9..9b85568 100644
--- a/libc/kernel/uapi/linux/if_tunnel.h
+++ b/libc/kernel/uapi/linux/if_tunnel.h
@@ -142,7 +142,7 @@
   __IFLA_GRE_MAX,
 };
 #define IFLA_GRE_MAX (__IFLA_GRE_MAX - 1)
-#define VTI_ISVTI ((__force __be16) 0x0001)
+#define VTI_ISVTI (( __be16) 0x0001)
 enum {
   IFLA_VTI_UNSPEC,
   IFLA_VTI_LINK,
diff --git a/libc/kernel/uapi/linux/in.h b/libc/kernel/uapi/linux/in.h
index 53d3074..3947d5a 100644
--- a/libc/kernel/uapi/linux/in.h
+++ b/libc/kernel/uapi/linux/in.h
@@ -141,6 +141,7 @@
 #define MCAST_MSFILTER 48
 #define IP_MULTICAST_ALL 49
 #define IP_UNICAST_IF 50
+#define IP_LOCAL_PORT_RANGE 51
 #define MCAST_EXCLUDE 0
 #define MCAST_INCLUDE 1
 #define IP_DEFAULT_MULTICAST_TTL 1
diff --git a/libc/kernel/uapi/linux/input.h b/libc/kernel/uapi/linux/input.h
index 4858c81..1df1398 100644
--- a/libc/kernel/uapi/linux/input.h
+++ b/libc/kernel/uapi/linux/input.h
@@ -173,7 +173,7 @@
   __u16 phase;
   struct ff_envelope envelope;
   __u32 custom_len;
-  __s16 __user * custom_data;
+  __s16  * custom_data;
 };
 struct ff_rumble_effect {
   __u16 strong_magnitude;
diff --git a/libc/kernel/uapi/linux/io_uring.h b/libc/kernel/uapi/linux/io_uring.h
index 5561448..a2d4f5f 100644
--- a/libc/kernel/uapi/linux/io_uring.h
+++ b/libc/kernel/uapi/linux/io_uring.h
@@ -200,6 +200,7 @@
   IORING_MSG_SEND_FD,
 };
 #define IORING_MSG_RING_CQE_SKIP (1U << 0)
+#define IORING_MSG_RING_FLAGS_PASS (1U << 1)
 struct io_uring_cqe {
   __u64 user_data;
   __s32 res;
@@ -272,6 +273,7 @@
 #define IORING_FEAT_RSRC_TAGS (1U << 10)
 #define IORING_FEAT_CQE_SKIP (1U << 11)
 #define IORING_FEAT_LINKED_FILE (1U << 12)
+#define IORING_FEAT_REG_REG_RING (1U << 13)
 enum {
   IORING_REGISTER_BUFFERS = 0,
   IORING_UNREGISTER_BUFFERS = 1,
@@ -299,7 +301,8 @@
   IORING_UNREGISTER_PBUF_RING = 23,
   IORING_REGISTER_SYNC_CANCEL = 24,
   IORING_REGISTER_FILE_ALLOC_RANGE = 25,
-  IORING_REGISTER_LAST
+  IORING_REGISTER_LAST,
+  IORING_REGISTER_USE_REGISTERED_RING = 1U << 31
 };
 enum {
   IO_WQ_BOUND,
@@ -381,7 +384,7 @@
       __u16 resv3;
       __u16 tail;
     };
-    struct io_uring_buf bufs[0];
+    __DECLARE_FLEX_ARRAY(struct io_uring_buf, bufs);
   };
 };
 struct io_uring_buf_reg {
diff --git a/libc/kernel/uapi/linux/ioam6.h b/libc/kernel/uapi/linux/ioam6.h
index e32c8e9..8d2a25b 100644
--- a/libc/kernel/uapi/linux/ioam6.h
+++ b/libc/kernel/uapi/linux/ioam6.h
@@ -58,6 +58,6 @@
 #error "Please fix <asm/byteorder.h>"
 #endif
 #define IOAM6_TRACE_DATA_SIZE_MAX 244
-  __u8 data[0];
+  __u8 data[];
 } __attribute__((packed));
 #endif
diff --git a/libc/kernel/uapi/linux/ipc.h b/libc/kernel/uapi/linux/ipc.h
index a0699cf..4ca9ee1 100644
--- a/libc/kernel/uapi/linux/ipc.h
+++ b/libc/kernel/uapi/linux/ipc.h
@@ -42,7 +42,7 @@
 #define IPC_OLD 0
 #define IPC_64 0x0100
 struct ipc_kludge {
-  struct msgbuf __user * msgp;
+  struct msgbuf  * msgp;
   long msgtyp;
 };
 #define SEMOP 1
diff --git a/libc/kernel/uapi/linux/ipmi.h b/libc/kernel/uapi/linux/ipmi.h
index dd88f2f..bd73b3c 100644
--- a/libc/kernel/uapi/linux/ipmi.h
+++ b/libc/kernel/uapi/linux/ipmi.h
@@ -65,7 +65,7 @@
   unsigned char netfn;
   unsigned char cmd;
   unsigned short data_len;
-  unsigned char __user * data;
+  unsigned char  * data;
 };
 struct kernel_ipmi_msg {
   unsigned char netfn;
@@ -86,7 +86,7 @@
 #define IPMI_MAINTENANCE_MODE_ON 2
 #define IPMI_IOC_MAGIC 'i'
 struct ipmi_req {
-  unsigned char __user * addr;
+  unsigned char  * addr;
   unsigned int addr_len;
   long msgid;
   struct ipmi_msg msg;
@@ -100,7 +100,7 @@
 #define IPMICTL_SEND_COMMAND_SETTIME _IOR(IPMI_IOC_MAGIC, 21, struct ipmi_req_settime)
 struct ipmi_recv {
   int recv_type;
-  unsigned char __user * addr;
+  unsigned char  * addr;
   unsigned int addr_len;
   long msgid;
   struct ipmi_msg msg;
diff --git a/libc/kernel/uapi/linux/ivtv.h b/libc/kernel/uapi/linux/ivtv.h
index 549d6a8..bdd526e 100644
--- a/libc/kernel/uapi/linux/ivtv.h
+++ b/libc/kernel/uapi/linux/ivtv.h
@@ -24,8 +24,8 @@
 struct ivtv_dma_frame {
   enum v4l2_buf_type type;
   __u32 pixelformat;
-  void __user * y_source;
-  void __user * uv_source;
+  void  * y_source;
+  void  * uv_source;
   struct v4l2_rect src;
   struct v4l2_rect dst;
   __u32 src_width;
diff --git a/libc/kernel/uapi/linux/ivtvfb.h b/libc/kernel/uapi/linux/ivtvfb.h
index 9addcbf..171be74 100644
--- a/libc/kernel/uapi/linux/ivtvfb.h
+++ b/libc/kernel/uapi/linux/ivtvfb.h
@@ -21,7 +21,7 @@
 #include <linux/compiler.h>
 #include <linux/types.h>
 struct ivtvfb_dma_frame {
-  void __user * source;
+  void  * source;
   unsigned long dest_offset;
   int count;
 };
diff --git a/libc/kernel/uapi/linux/kd.h b/libc/kernel/uapi/linux/kd.h
index 2385037..a14cab6 100644
--- a/libc/kernel/uapi/linux/kd.h
+++ b/libc/kernel/uapi/linux/kd.h
@@ -27,7 +27,7 @@
 struct consolefontdesc {
   unsigned short charcount;
   unsigned short charheight;
-  char __user * chardata;
+  char  * chardata;
 };
 #define PIO_FONTRESET 0x4B6D
 #define GIO_CMAP 0x4B70
@@ -68,7 +68,7 @@
 };
 struct unimapdesc {
   unsigned short entry_ct;
-  struct unipair __user * entries;
+  struct unipair  * entries;
 };
 #define PIO_UNIMAP 0x4B67
 #define PIO_UNIMAPCLR 0x4B68
@@ -147,7 +147,7 @@
   unsigned int flags;
   unsigned int width, height;
   unsigned int charcount;
-  unsigned char __user * data;
+  unsigned char  * data;
 };
 struct console_font {
   unsigned int width, height;
@@ -158,5 +158,7 @@
 #define KD_FONT_OP_GET 1
 #define KD_FONT_OP_SET_DEFAULT 2
 #define KD_FONT_OP_COPY 3
+#define KD_FONT_OP_SET_TALL 4
+#define KD_FONT_OP_GET_TALL 5
 #define KD_FONT_FLAG_DONT_RECALC 1
 #endif
diff --git a/libc/kernel/uapi/linux/keyctl.h b/libc/kernel/uapi/linux/keyctl.h
index 01ea576..b534f5e 100644
--- a/libc/kernel/uapi/linux/keyctl.h
+++ b/libc/kernel/uapi/linux/keyctl.h
@@ -80,8 +80,8 @@
   __s32 base;
 };
 struct keyctl_kdf_params {
-  char __user * hashname;
-  char __user * otherinfo;
+  char  * hashname;
+  char  * otherinfo;
   __u32 otherinfolen;
   __u32 __spare[8];
 };
diff --git a/libc/kernel/uapi/linux/kvm.h b/libc/kernel/uapi/linux/kvm.h
index 9566f01..342c5c9 100644
--- a/libc/kernel/uapi/linux/kvm.h
+++ b/libc/kernel/uapi/linux/kvm.h
@@ -436,6 +436,8 @@
     struct {
       __u8 ar;
       __u8 key;
+      __u8 pad1[6];
+      __u64 old_addr;
     };
     __u32 sida_offset;
     __u8 reserved[32];
@@ -447,9 +449,12 @@
 #define KVM_S390_MEMOP_SIDA_WRITE 3
 #define KVM_S390_MEMOP_ABSOLUTE_READ 4
 #define KVM_S390_MEMOP_ABSOLUTE_WRITE 5
+#define KVM_S390_MEMOP_ABSOLUTE_CMPXCHG 6
 #define KVM_S390_MEMOP_F_CHECK_ONLY (1ULL << 0)
 #define KVM_S390_MEMOP_F_INJECT_EXCEPTION (1ULL << 1)
 #define KVM_S390_MEMOP_F_SKEY_PROTECTION (1ULL << 2)
+#define KVM_S390_MEMOP_EXTENSION_CAP_BASE (1 << 0)
+#define KVM_S390_MEMOP_EXTENSION_CAP_CMPXCHG (1 << 1)
 struct kvm_interrupt {
   __u32 irq;
 };
@@ -457,7 +462,7 @@
   __u32 slot;
   __u32 padding1;
   union {
-    void __user * dirty_bitmap;
+    void  * dirty_bitmap;
     __u64 padding2;
   };
 };
@@ -466,7 +471,7 @@
   __u32 num_pages;
   __u64 first_page;
   union {
-    void __user * dirty_bitmap;
+    void  * dirty_bitmap;
     __u64 padding2;
   };
 };
@@ -926,6 +931,7 @@
 #define KVM_CAP_DIRTY_LOG_RING_ACQ_REL 223
 #define KVM_CAP_S390_PROTECTED_ASYNC_DISABLE 224
 #define KVM_CAP_DIRTY_LOG_RING_WITH_BITMAP 225
+#define KVM_CAP_PMU_EVENT_MASKED_EVENTS 226
 #ifdef KVM_CAP_IRQ_ROUTING
 struct kvm_irq_routing_irqchip {
   __u32 irqchip;
diff --git a/libc/kernel/uapi/linux/mdio.h b/libc/kernel/uapi/linux/mdio.h
index 7a2c9af..725eb1a 100644
--- a/libc/kernel/uapi/linux/mdio.h
+++ b/libc/kernel/uapi/linux/mdio.h
@@ -78,6 +78,8 @@
 #define MDIO_AN_T1_LP_L 517
 #define MDIO_AN_T1_LP_M 518
 #define MDIO_AN_T1_LP_H 519
+#define MDIO_AN_10BT1_AN_CTRL 526
+#define MDIO_AN_10BT1_AN_STAT 527
 #define MDIO_PMA_PMD_BT1_CTRL 2100
 #define MDIO_PMA_LASI_RXCTRL 0x9000
 #define MDIO_PMA_LASI_TXCTRL 0x9001
@@ -270,6 +272,8 @@
 #define MDIO_AN_T1_LP_M_B10L 0x4000
 #define MDIO_AN_T1_LP_H_10L_TX_HI_REQ 0x1000
 #define MDIO_AN_T1_LP_H_10L_TX_HI 0x2000
+#define MDIO_AN_10BT1_AN_CTRL_ADV_EEE_T1L 0x4000
+#define MDIO_AN_10BT1_AN_STAT_LPA_EEE_T1L 0x4000
 #define MDIO_PMA_PMD_BT1_CTRL_CFG_MST 0x4000
 #define MDIO_AN_EEE_ADV_100TX 0x0002
 #define MDIO_AN_EEE_ADV_1000T 0x0004
diff --git a/libc/kernel/uapi/linux/media-bus-format.h b/libc/kernel/uapi/linux/media-bus-format.h
index 87614cf..79d4cd5 100644
--- a/libc/kernel/uapi/linux/media-bus-format.h
+++ b/libc/kernel/uapi/linux/media-bus-format.h
@@ -30,8 +30,11 @@
 #define MEDIA_BUS_FMT_RGB565_2X8_BE 0x1007
 #define MEDIA_BUS_FMT_RGB565_2X8_LE 0x1008
 #define MEDIA_BUS_FMT_RGB666_1X18 0x1009
+#define MEDIA_BUS_FMT_BGR666_1X18 0x1023
 #define MEDIA_BUS_FMT_RBG888_1X24 0x100e
 #define MEDIA_BUS_FMT_RGB666_1X24_CPADHI 0x1015
+#define MEDIA_BUS_FMT_BGR666_1X24_CPADHI 0x1024
+#define MEDIA_BUS_FMT_RGB565_1X24_CPADHI 0x1022
 #define MEDIA_BUS_FMT_RGB666_1X7X3_SPWG 0x1010
 #define MEDIA_BUS_FMT_BGR888_1X24 0x1013
 #define MEDIA_BUS_FMT_BGR888_3X8 0x101b
diff --git a/libc/kernel/uapi/linux/media.h b/libc/kernel/uapi/linux/media.h
index 869d47b..fe97e90 100644
--- a/libc/kernel/uapi/linux/media.h
+++ b/libc/kernel/uapi/linux/media.h
@@ -125,8 +125,8 @@
 };
 struct media_links_enum {
   __u32 entity;
-  struct media_pad_desc __user * pads;
-  struct media_link_desc __user * links;
+  struct media_pad_desc  * pads;
+  struct media_link_desc  * links;
   __u32 reserved[4];
 };
 #define MEDIA_INTF_T_DVB_BASE 0x00000100
diff --git a/libc/kernel/uapi/linux/membarrier.h b/libc/kernel/uapi/linux/membarrier.h
index 43c103b..94dd797 100644
--- a/libc/kernel/uapi/linux/membarrier.h
+++ b/libc/kernel/uapi/linux/membarrier.h
@@ -29,6 +29,7 @@
   MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_SYNC_CORE = (1 << 6),
   MEMBARRIER_CMD_PRIVATE_EXPEDITED_RSEQ = (1 << 7),
   MEMBARRIER_CMD_REGISTER_PRIVATE_EXPEDITED_RSEQ = (1 << 8),
+  MEMBARRIER_CMD_GET_REGISTRATIONS = (1 << 9),
   MEMBARRIER_CMD_SHARED = MEMBARRIER_CMD_GLOBAL,
 };
 enum membarrier_cmd_flag {
diff --git a/libc/kernel/uapi/linux/memfd.h b/libc/kernel/uapi/linux/memfd.h
index 914c076..28228df 100644
--- a/libc/kernel/uapi/linux/memfd.h
+++ b/libc/kernel/uapi/linux/memfd.h
@@ -22,6 +22,8 @@
 #define MFD_CLOEXEC 0x0001U
 #define MFD_ALLOW_SEALING 0x0002U
 #define MFD_HUGETLB 0x0004U
+#define MFD_NOEXEC_SEAL 0x0008U
+#define MFD_EXEC 0x0010U
 #define MFD_HUGE_SHIFT HUGETLB_FLAG_ENCODE_SHIFT
 #define MFD_HUGE_MASK HUGETLB_FLAG_ENCODE_MASK
 #define MFD_HUGE_64KB HUGETLB_FLAG_ENCODE_64KB
diff --git a/libc/kernel/uapi/linux/meye.h b/libc/kernel/uapi/linux/meye.h
deleted file mode 100644
index a1112c4..0000000
--- a/libc/kernel/uapi/linux/meye.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/****************************************************************************
- ****************************************************************************
- ***
- ***   This header was automatically generated from a Linux kernel header
- ***   of the same name, to make information necessary for userspace to
- ***   call into the kernel available to libc.  It contains only constants,
- ***   structures, and macros generated from the original header, and thus,
- ***   contains no copyrightable information.
- ***
- ***   To edit the content of this header, modify the corresponding
- ***   source file (e.g. under external/kernel-headers/original/) then
- ***   run bionic/libc/kernel/tools/update_all.py
- ***
- ***   Any manual change here will be lost the next time this script will
- ***   be run. You've been warned!
- ***
- ****************************************************************************
- ****************************************************************************/
-#ifndef _MEYE_H_
-#define _MEYE_H_
-struct meye_params {
-  unsigned char subsample;
-  unsigned char quality;
-  unsigned char sharpness;
-  unsigned char agc;
-  unsigned char picture;
-  unsigned char framerate;
-};
-#define MEYEIOC_G_PARAMS _IOR('v', BASE_VIDIOC_PRIVATE + 0, struct meye_params)
-#define MEYEIOC_S_PARAMS _IOW('v', BASE_VIDIOC_PRIVATE + 1, struct meye_params)
-#define MEYEIOC_QBUF_CAPT _IOW('v', BASE_VIDIOC_PRIVATE + 2, int)
-#define MEYEIOC_SYNC _IOWR('v', BASE_VIDIOC_PRIVATE + 3, int)
-#define MEYEIOC_STILLCAPT _IO('v', BASE_VIDIOC_PRIVATE + 4)
-#define MEYEIOC_STILLJCAPT _IOR('v', BASE_VIDIOC_PRIVATE + 5, int)
-#define V4L2_CID_MEYE_AGC (V4L2_CID_USER_MEYE_BASE + 0)
-#define V4L2_CID_MEYE_PICTURE (V4L2_CID_USER_MEYE_BASE + 1)
-#define V4L2_CID_MEYE_FRAMERATE (V4L2_CID_USER_MEYE_BASE + 2)
-#endif
diff --git a/libc/kernel/uapi/linux/netdev.h b/libc/kernel/uapi/linux/netdev.h
new file mode 100644
index 0000000..53a237b
--- /dev/null
+++ b/libc/kernel/uapi/linux/netdev.h
@@ -0,0 +1,49 @@
+/****************************************************************************
+ ****************************************************************************
+ ***
+ ***   This header was automatically generated from a Linux kernel header
+ ***   of the same name, to make information necessary for userspace to
+ ***   call into the kernel available to libc.  It contains only constants,
+ ***   structures, and macros generated from the original header, and thus,
+ ***   contains no copyrightable information.
+ ***
+ ***   To edit the content of this header, modify the corresponding
+ ***   source file (e.g. under external/kernel-headers/original/) then
+ ***   run bionic/libc/kernel/tools/update_all.py
+ ***
+ ***   Any manual change here will be lost the next time this script will
+ ***   be run. You've been warned!
+ ***
+ ****************************************************************************
+ ****************************************************************************/
+#ifndef _UAPI_LINUX_NETDEV_H
+#define _UAPI_LINUX_NETDEV_H
+#define NETDEV_FAMILY_NAME "netdev"
+#define NETDEV_FAMILY_VERSION 1
+enum netdev_xdp_act {
+  NETDEV_XDP_ACT_BASIC = 1,
+  NETDEV_XDP_ACT_REDIRECT = 2,
+  NETDEV_XDP_ACT_NDO_XMIT = 4,
+  NETDEV_XDP_ACT_XSK_ZEROCOPY = 8,
+  NETDEV_XDP_ACT_HW_OFFLOAD = 16,
+  NETDEV_XDP_ACT_RX_SG = 32,
+  NETDEV_XDP_ACT_NDO_XMIT_SG = 64,
+  NETDEV_XDP_ACT_MASK = 127,
+};
+enum {
+  NETDEV_A_DEV_IFINDEX = 1,
+  NETDEV_A_DEV_PAD,
+  NETDEV_A_DEV_XDP_FEATURES,
+  __NETDEV_A_DEV_MAX,
+  NETDEV_A_DEV_MAX = (__NETDEV_A_DEV_MAX - 1)
+};
+enum {
+  NETDEV_CMD_DEV_GET = 1,
+  NETDEV_CMD_DEV_ADD_NTF,
+  NETDEV_CMD_DEV_DEL_NTF,
+  NETDEV_CMD_DEV_CHANGE_NTF,
+  __NETDEV_CMD_MAX,
+  NETDEV_CMD_MAX = (__NETDEV_CMD_MAX - 1)
+};
+#define NETDEV_MCGRP_MGMT "mgmt"
+#endif
diff --git a/libc/kernel/uapi/linux/netfilter/nf_tables.h b/libc/kernel/uapi/linux/netfilter/nf_tables.h
index f07d7c7..33bfb7f 100644
--- a/libc/kernel/uapi/linux/netfilter/nf_tables.h
+++ b/libc/kernel/uapi/linux/netfilter/nf_tables.h
@@ -87,6 +87,13 @@
   NFT_MSG_GETFLOWTABLE,
   NFT_MSG_DELFLOWTABLE,
   NFT_MSG_GETRULE_RESET,
+  NFT_MSG_DESTROYTABLE,
+  NFT_MSG_DESTROYCHAIN,
+  NFT_MSG_DESTROYRULE,
+  NFT_MSG_DESTROYSET,
+  NFT_MSG_DESTROYSETELEM,
+  NFT_MSG_DESTROYOBJ,
+  NFT_MSG_DESTROYFLOWTABLE,
   NFT_MSG_MAX,
 };
 enum nft_list_attributes {
diff --git a/libc/kernel/uapi/linux/netfilter_arp/arp_tables.h b/libc/kernel/uapi/linux/netfilter_arp/arp_tables.h
index 862f514..b1fb537 100644
--- a/libc/kernel/uapi/linux/netfilter_arp/arp_tables.h
+++ b/libc/kernel/uapi/linux/netfilter_arp/arp_tables.h
@@ -98,7 +98,7 @@
   unsigned int hook_entry[NF_ARP_NUMHOOKS];
   unsigned int underflow[NF_ARP_NUMHOOKS];
   unsigned int num_counters;
-  struct xt_counters __user * counters;
+  struct xt_counters  * counters;
   struct arpt_entry entries[];
 };
 struct arpt_get_entries {
diff --git a/libc/kernel/uapi/linux/netfilter_bridge/ebtables.h b/libc/kernel/uapi/linux/netfilter_bridge/ebtables.h
index 7c8f435..d87d65e 100644
--- a/libc/kernel/uapi/linux/netfilter_bridge/ebtables.h
+++ b/libc/kernel/uapi/linux/netfilter_bridge/ebtables.h
@@ -42,10 +42,10 @@
   unsigned int valid_hooks;
   unsigned int nentries;
   unsigned int entries_size;
-  struct ebt_entries __user * hook_entry[NF_BR_NUMHOOKS];
+  struct ebt_entries  * hook_entry[NF_BR_NUMHOOKS];
   unsigned int num_counters;
-  struct ebt_counter __user * counters;
-  char __user * entries;
+  struct ebt_counter  * counters;
+  char  * entries;
 };
 struct ebt_replace_kernel {
   char name[EBT_TABLE_MAXNAMELEN];
diff --git a/libc/kernel/uapi/linux/netfilter_ipv4/ip_tables.h b/libc/kernel/uapi/linux/netfilter_ipv4/ip_tables.h
index 14a65ad..5179be4 100644
--- a/libc/kernel/uapi/linux/netfilter_ipv4/ip_tables.h
+++ b/libc/kernel/uapi/linux/netfilter_ipv4/ip_tables.h
@@ -112,7 +112,7 @@
   unsigned int hook_entry[NF_INET_NUMHOOKS];
   unsigned int underflow[NF_INET_NUMHOOKS];
   unsigned int num_counters;
-  struct xt_counters __user * counters;
+  struct xt_counters  * counters;
   struct ipt_entry entries[];
 };
 struct ipt_get_entries {
diff --git a/libc/kernel/uapi/linux/netfilter_ipv6/ip6_tables.h b/libc/kernel/uapi/linux/netfilter_ipv6/ip6_tables.h
index 22071db..8c4ec88 100644
--- a/libc/kernel/uapi/linux/netfilter_ipv6/ip6_tables.h
+++ b/libc/kernel/uapi/linux/netfilter_ipv6/ip6_tables.h
@@ -132,7 +132,7 @@
   unsigned int hook_entry[NF_INET_NUMHOOKS];
   unsigned int underflow[NF_INET_NUMHOOKS];
   unsigned int num_counters;
-  struct xt_counters __user * counters;
+  struct xt_counters  * counters;
   struct ip6t_entry entries[];
 };
 struct ip6t_get_entries {
diff --git a/libc/kernel/uapi/linux/nfs4_mount.h b/libc/kernel/uapi/linux/nfs4_mount.h
index 0f794dd..9b9c9f8 100644
--- a/libc/kernel/uapi/linux/nfs4_mount.h
+++ b/libc/kernel/uapi/linux/nfs4_mount.h
@@ -21,7 +21,7 @@
 #define NFS4_MOUNT_VERSION 1
 struct nfs_string {
   unsigned int len;
-  const char __user * data;
+  const char  * data;
 };
 struct nfs4_mount_data {
   int version;
@@ -38,10 +38,10 @@
   struct nfs_string mnt_path;
   struct nfs_string hostname;
   unsigned int host_addrlen;
-  struct sockaddr __user * host_addr;
+  struct sockaddr  * host_addr;
   int proto;
   int auth_flavourlen;
-  int __user * auth_flavours;
+  int  * auth_flavours;
 };
 #define NFS4_MOUNT_SOFT 0x0001
 #define NFS4_MOUNT_INTR 0x0002
diff --git a/libc/kernel/uapi/linux/nl80211.h b/libc/kernel/uapi/linux/nl80211.h
index 83fe597..d73922a 100644
--- a/libc/kernel/uapi/linux/nl80211.h
+++ b/libc/kernel/uapi/linux/nl80211.h
@@ -528,6 +528,7 @@
   NL80211_ATTR_TX_HW_TIMESTAMP,
   NL80211_ATTR_RX_HW_TIMESTAMP,
   NL80211_ATTR_TD_BITMAP,
+  NL80211_ATTR_PUNCT_BITMAP,
   __NL80211_ATTR_AFTER_LAST,
   NUM_NL80211_ATTR = __NL80211_ATTR_AFTER_LAST,
   NL80211_ATTR_MAX = __NL80211_ATTR_AFTER_LAST - 1
@@ -1396,6 +1397,7 @@
 #define NL80211_KEK_LEN 16
 #define NL80211_KCK_EXT_LEN 24
 #define NL80211_KEK_EXT_LEN 32
+#define NL80211_KCK_EXT_LEN_32 32
 #define NL80211_REPLAY_CTR_LEN 8
 enum nl80211_rekey_data {
   __NL80211_REKEY_DATA_INVALID,
@@ -1533,6 +1535,8 @@
   NL80211_EXT_FEATURE_FILS_CRYPTO_OFFLOAD,
   NL80211_EXT_FEATURE_RADAR_BACKGROUND,
   NL80211_EXT_FEATURE_POWERED_ADDR_CHANGE,
+  NL80211_EXT_FEATURE_PUNCT,
+  NL80211_EXT_FEATURE_SECURE_NAN,
   NUM_NL80211_EXT_FEATURES,
   MAX_NL80211_EXT_FEATURES = NUM_NL80211_EXT_FEATURES - 1
 };
diff --git a/libc/kernel/uapi/linux/omap3isp.h b/libc/kernel/uapi/linux/omap3isp.h
index 53345e3..1834658 100644
--- a/libc/kernel/uapi/linux/omap3isp.h
+++ b/libc/kernel/uapi/linux/omap3isp.h
@@ -88,7 +88,7 @@
 };
 struct omap3isp_stat_data {
   struct timeval ts;
-  void __user * buf;
+  void  * buf;
   __struct_group(, frame,, __u32 buf_size;
   __u16 frame_number;
   __u16 cur_frame;
@@ -224,12 +224,12 @@
   __u16 update;
   __u16 flag;
   enum omap3isp_alaw_ipwidth alawip;
-  struct omap3isp_ccdc_bclamp __user * bclamp;
-  struct omap3isp_ccdc_blcomp __user * blcomp;
-  struct omap3isp_ccdc_fpc __user * fpc;
-  struct omap3isp_ccdc_lsc_config __user * lsc_cfg;
-  struct omap3isp_ccdc_culling __user * cull;
-  __u8 __user * lsc;
+  struct omap3isp_ccdc_bclamp  * bclamp;
+  struct omap3isp_ccdc_blcomp  * blcomp;
+  struct omap3isp_ccdc_fpc  * fpc;
+  struct omap3isp_ccdc_lsc_config  * lsc_cfg;
+  struct omap3isp_ccdc_culling  * cull;
+  __u8  * lsc;
 };
 #define OMAP3ISP_PREV_LUMAENH (1 << 0)
 #define OMAP3ISP_PREV_INVALAW (1 << 1)
@@ -323,17 +323,17 @@
   __u32 update;
   __u32 flag;
   __u32 shading_shift;
-  struct omap3isp_prev_luma __user * luma;
-  struct omap3isp_prev_hmed __user * hmed;
-  struct omap3isp_prev_cfa __user * cfa;
-  struct omap3isp_prev_csup __user * csup;
-  struct omap3isp_prev_wbal __user * wbal;
-  struct omap3isp_prev_blkadj __user * blkadj;
-  struct omap3isp_prev_rgbtorgb __user * rgb2rgb;
-  struct omap3isp_prev_csc __user * csc;
-  struct omap3isp_prev_yclimit __user * yclimit;
-  struct omap3isp_prev_dcor __user * dcor;
-  struct omap3isp_prev_nf __user * nf;
-  struct omap3isp_prev_gtables __user * gamma;
+  struct omap3isp_prev_luma  * luma;
+  struct omap3isp_prev_hmed  * hmed;
+  struct omap3isp_prev_cfa  * cfa;
+  struct omap3isp_prev_csup  * csup;
+  struct omap3isp_prev_wbal  * wbal;
+  struct omap3isp_prev_blkadj  * blkadj;
+  struct omap3isp_prev_rgbtorgb  * rgb2rgb;
+  struct omap3isp_prev_csc  * csc;
+  struct omap3isp_prev_yclimit  * yclimit;
+  struct omap3isp_prev_dcor  * dcor;
+  struct omap3isp_prev_nf  * nf;
+  struct omap3isp_prev_gtables  * gamma;
 };
 #endif
diff --git a/libc/kernel/uapi/linux/omapfb.h b/libc/kernel/uapi/linux/omapfb.h
index 6ebec08..632e468 100644
--- a/libc/kernel/uapi/linux/omapfb.h
+++ b/libc/kernel/uapi/linux/omapfb.h
@@ -153,7 +153,7 @@
   __u16 w;
   __u16 h;
   size_t buffer_size;
-  void __user * buffer;
+  void  * buffer;
 };
 struct omapfb_ovl_colormode {
   __u8 overlay_idx;
diff --git a/libc/kernel/uapi/linux/pci_regs.h b/libc/kernel/uapi/linux/pci_regs.h
index f932c18..44b0613 100644
--- a/libc/kernel/uapi/linux/pci_regs.h
+++ b/libc/kernel/uapi/linux/pci_regs.h
@@ -594,6 +594,7 @@
 #define PCI_EXP_LNKCTL2_TX_MARGIN 0x0380
 #define PCI_EXP_LNKCTL2_HASD 0x0020
 #define PCI_EXP_LNKSTA2 0x32
+#define PCI_EXP_LNKSTA2_FLIT 0x0400
 #define PCI_CAP_EXP_ENDPOINT_SIZEOF_V2 0x32
 #define PCI_EXP_SLTCAP2 0x34
 #define PCI_EXP_SLTCAP2_IBPD 0x00000001
diff --git a/libc/kernel/uapi/linux/perf_event.h b/libc/kernel/uapi/linux/perf_event.h
index 8f081ed..9223bd7 100644
--- a/libc/kernel/uapi/linux/perf_event.h
+++ b/libc/kernel/uapi/linux/perf_event.h
@@ -237,6 +237,7 @@
 #define PERF_ATTR_SIZE_VER5 112
 #define PERF_ATTR_SIZE_VER6 120
 #define PERF_ATTR_SIZE_VER7 128
+#define PERF_ATTR_SIZE_VER8 136
 struct perf_event_attr {
   __u32 type;
   __u32 size;
@@ -276,6 +277,7 @@
   __u32 aux_sample_size;
   __u32 __reserved_3;
   __u64 sig_data;
+  __u64 config3;
 };
 struct perf_event_query_bpf {
   __u32 ids_len;
diff --git a/libc/kernel/uapi/linux/ppp-ioctl.h b/libc/kernel/uapi/linux/ppp-ioctl.h
index 69c6e6d..165d447 100644
--- a/libc/kernel/uapi/linux/ppp-ioctl.h
+++ b/libc/kernel/uapi/linux/ppp-ioctl.h
@@ -56,7 +56,7 @@
   enum NPmode mode;
 };
 struct ppp_option_data {
-  __u8 __user * ptr;
+  __u8  * ptr;
   __u32 length;
   int transmit;
 };
diff --git a/libc/kernel/uapi/linux/prctl.h b/libc/kernel/uapi/linux/prctl.h
index 1dac726..6ad1c04 100644
--- a/libc/kernel/uapi/linux/prctl.h
+++ b/libc/kernel/uapi/linux/prctl.h
@@ -184,6 +184,9 @@
 #define PR_SME_GET_VL 64
 #define PR_SME_VL_LEN_MASK 0xffff
 #define PR_SME_VL_INHERIT (1 << 17)
+#define PR_SET_MDWE 65
+#define PR_MDWE_REFUSE_EXEC_GAIN 1
+#define PR_GET_MDWE 66
 #define PR_SET_VMA 0x53564d41
 #define PR_SET_VMA_ANON_NAME 0
 #endif
diff --git a/libc/kernel/uapi/linux/route.h b/libc/kernel/uapi/linux/route.h
index 4ba6023..f33327c 100644
--- a/libc/kernel/uapi/linux/route.h
+++ b/libc/kernel/uapi/linux/route.h
@@ -30,7 +30,7 @@
   unsigned long rt_pad3;
   void * rt_pad4;
   short rt_metric;
-  char __user * rt_dev;
+  char  * rt_dev;
   unsigned long rt_mtu;
 #define rt_mss rt_mtu
   unsigned long rt_window;
diff --git a/libc/kernel/uapi/linux/rpl.h b/libc/kernel/uapi/linux/rpl.h
index 3648bfc..4226297 100644
--- a/libc/kernel/uapi/linux/rpl.h
+++ b/libc/kernel/uapi/linux/rpl.h
@@ -34,8 +34,8 @@
 #error "Please fix <asm/byteorder.h>"
 #endif
   union {
-    struct in6_addr addr[0];
-    __u8 data[0];
+    __DECLARE_FLEX_ARRAY(struct in6_addr, addr);
+    __DECLARE_FLEX_ARRAY(__u8, data);
   } segments;
 } __attribute__((packed));
 #define rpl_segaddr segments.addr
diff --git a/libc/kernel/uapi/linux/rseq.h b/libc/kernel/uapi/linux/rseq.h
index 29a9457..f837720 100644
--- a/libc/kernel/uapi/linux/rseq.h
+++ b/libc/kernel/uapi/linux/rseq.h
@@ -49,5 +49,8 @@
   __u32 cpu_id;
   __u64 rseq_cs;
   __u32 flags;
+  __u32 node_id;
+  __u32 mm_cid;
+  char end[];
 } __attribute__((aligned(4 * sizeof(__u64))));
 #endif
diff --git a/libc/kernel/uapi/linux/rtnetlink.h b/libc/kernel/uapi/linux/rtnetlink.h
index 7201827..335a19a 100644
--- a/libc/kernel/uapi/linux/rtnetlink.h
+++ b/libc/kernel/uapi/linux/rtnetlink.h
@@ -463,6 +463,7 @@
   TCA_INGRESS_BLOCK,
   TCA_EGRESS_BLOCK,
   TCA_DUMP_FLAGS,
+  TCA_EXT_WARN_MSG,
   __TCA_MAX
 };
 #define TCA_MAX (__TCA_MAX - 1)
@@ -589,6 +590,7 @@
   TCA_ROOT_FLAGS,
   TCA_ROOT_COUNT,
   TCA_ROOT_TIME_DELTA,
+  TCA_ROOT_EXT_WARN_MSG,
   __TCA_ROOT_MAX,
 #define TCA_ROOT_MAX (__TCA_ROOT_MAX - 1)
 };
diff --git a/libc/kernel/uapi/linux/sed-opal.h b/libc/kernel/uapi/linux/sed-opal.h
index 4c66231..4685bb3 100644
--- a/libc/kernel/uapi/linux/sed-opal.h
+++ b/libc/kernel/uapi/linux/sed-opal.h
@@ -122,6 +122,7 @@
 #define OPAL_FL_LOCKED 0x00000008
 #define OPAL_FL_MBR_ENABLED 0x00000010
 #define OPAL_FL_MBR_DONE 0x00000020
+#define OPAL_FL_SUM_SUPPORTED 0x00000040
 struct opal_status {
   __u32 flags;
   __u32 reserved;
diff --git a/libc/kernel/uapi/linux/sem.h b/libc/kernel/uapi/linux/sem.h
index 98ed1bf..c2f25e7 100644
--- a/libc/kernel/uapi/linux/sem.h
+++ b/libc/kernel/uapi/linux/sem.h
@@ -48,10 +48,10 @@
 };
 union __kernel_legacy_semun {
   int val;
-  struct __kernel_legacy_semid_ds __user * buf;
-  unsigned short __user * array;
-  struct seminfo __user * __buf;
-  void __user * __pad;
+  struct __kernel_legacy_semid_ds  * buf;
+  unsigned short  * array;
+  struct seminfo  * __buf;
+  void  * __pad;
 };
 struct seminfo {
   int semmap;
diff --git a/libc/kernel/uapi/linux/serial_core.h b/libc/kernel/uapi/linux/serial_core.h
index 1e04429..ecd395c 100644
--- a/libc/kernel/uapi/linux/serial_core.h
+++ b/libc/kernel/uapi/linux/serial_core.h
@@ -99,6 +99,7 @@
 #define PORT_VT8500 97
 #define PORT_XUARTPS 98
 #define PORT_AR933X 99
+#define PORT_MCHP16550A 100
 #define PORT_ARC 101
 #define PORT_RP2 102
 #define PORT_LPUART 103
diff --git a/libc/kernel/uapi/linux/serial_reg.h b/libc/kernel/uapi/linux/serial_reg.h
index e41e649..36d778d 100644
--- a/libc/kernel/uapi/linux/serial_reg.h
+++ b/libc/kernel/uapi/linux/serial_reg.h
@@ -37,6 +37,11 @@
 #define UART_IIR_RX_TIMEOUT 0x0c
 #define UART_IIR_XOFF 0x10
 #define UART_IIR_CTS_RTS_DSR 0x20
+#define UART_IIR_64BYTE_FIFO 0x20
+#define UART_IIR_FIFO_ENABLED 0xc0
+#define UART_IIR_FIFO_ENABLED_8250 0x00
+#define UART_IIR_FIFO_ENABLED_16550 0x80
+#define UART_IIR_FIFO_ENABLED_16550A 0xc0
 #define UART_FCR 2
 #define UART_FCR_ENABLE_FIFO 0x01
 #define UART_FCR_CLEAR_RCVR 0x02
diff --git a/libc/kernel/uapi/linux/snmp.h b/libc/kernel/uapi/linux/snmp.h
index e3d6ee3..ea3f058 100644
--- a/libc/kernel/uapi/linux/snmp.h
+++ b/libc/kernel/uapi/linux/snmp.h
@@ -87,6 +87,8 @@
   ICMP_MIB_OUTADDRMASKS,
   ICMP_MIB_OUTADDRMASKREPS,
   ICMP_MIB_CSUMERRORS,
+  ICMP_MIB_RATELIMITGLOBAL,
+  ICMP_MIB_RATELIMITHOST,
   __ICMP_MIB_MAX
 };
 #define __ICMPMSG_MIB_MAX 512
@@ -97,6 +99,7 @@
   ICMP6_MIB_OUTMSGS,
   ICMP6_MIB_OUTERRORS,
   ICMP6_MIB_CSUMERRORS,
+  ICMP6_MIB_RATELIMITHOST,
   __ICMP6_MIB_MAX
 };
 #define __ICMP6MSG_MIB_MAX 512
diff --git a/libc/kernel/uapi/linux/sysctl.h b/libc/kernel/uapi/linux/sysctl.h
index ff17f7c..5714323 100644
--- a/libc/kernel/uapi/linux/sysctl.h
+++ b/libc/kernel/uapi/linux/sysctl.h
@@ -23,11 +23,11 @@
 #include <linux/compiler.h>
 #define CTL_MAXNAME 10
 struct __sysctl_args {
-  int __user * name;
+  int  * name;
   int nlen;
-  void __user * oldval;
-  size_t __user * oldlenp;
-  void __user * newval;
+  void  * oldval;
+  size_t  * oldlenp;
+  void  * newval;
   size_t newlen;
   unsigned long __linux_unused[4];
 };
diff --git a/libc/kernel/uapi/linux/time.h b/libc/kernel/uapi/linux/time.h
index df52295..55d0e6e 100644
--- a/libc/kernel/uapi/linux/time.h
+++ b/libc/kernel/uapi/linux/time.h
@@ -18,14 +18,11 @@
  ****************************************************************************/
 #ifndef _UAPI_LINUX_TIME_H
 #define _UAPI_LINUX_TIME_H
+#include <bits/timespec.h>
 #include <linux/types.h>
 #include <linux/time_types.h>
 #ifndef _STRUCT_TIMESPEC
 #define _STRUCT_TIMESPEC
-struct timespec {
-  __kernel_old_time_t tv_sec;
-  long tv_nsec;
-};
 #endif
 struct timeval {
   __kernel_old_time_t tv_sec;
diff --git a/libc/kernel/uapi/linux/ublk_cmd.h b/libc/kernel/uapi/linux/ublk_cmd.h
index 8c9cbeb..6e0a9f8 100644
--- a/libc/kernel/uapi/linux/ublk_cmd.h
+++ b/libc/kernel/uapi/linux/ublk_cmd.h
@@ -29,6 +29,7 @@
 #define UBLK_CMD_GET_PARAMS 0x09
 #define UBLK_CMD_START_USER_RECOVERY 0x10
 #define UBLK_CMD_END_USER_RECOVERY 0x11
+#define UBLK_CMD_GET_DEV_INFO2 0x12
 #define UBLK_IO_FETCH_REQ 0x20
 #define UBLK_IO_COMMIT_AND_FETCH_REQ 0x21
 #define UBLK_IO_NEED_GET_DATA 0x22
@@ -43,6 +44,7 @@
 #define UBLK_F_NEED_GET_DATA (1UL << 2)
 #define UBLK_F_USER_RECOVERY (1UL << 3)
 #define UBLK_F_USER_RECOVERY_REISSUE (1UL << 4)
+#define UBLK_F_UNPRIVILEGED_DEV (1UL << 5)
 #define UBLK_S_DEV_DEAD 0
 #define UBLK_S_DEV_LIVE 1
 #define UBLK_S_DEV_QUIESCED 2
@@ -51,7 +53,10 @@
   __u16 queue_id;
   __u16 len;
   __u64 addr;
-  __u64 data[2];
+  __u64 data[1];
+  __u16 dev_path_len;
+  __u16 pad;
+  __u32 reserved;
 };
 struct ublksrv_ctrl_dev_info {
   __u16 nr_hw_queues;
@@ -64,7 +69,8 @@
   __u32 pad1;
   __u64 flags;
   __u64 ublksrv_flags;
-  __u64 reserved0;
+  __u32 owner_uid;
+  __u32 owner_gid;
   __u64 reserved1;
   __u64 reserved2;
 };
@@ -116,12 +122,20 @@
   __u16 max_discard_segments;
   __u16 reserved0;
 };
+struct ublk_param_devt {
+  __u32 char_major;
+  __u32 char_minor;
+  __u32 disk_major;
+  __u32 disk_minor;
+};
 struct ublk_params {
   __u32 len;
 #define UBLK_PARAM_TYPE_BASIC (1 << 0)
 #define UBLK_PARAM_TYPE_DISCARD (1 << 1)
+#define UBLK_PARAM_TYPE_DEVT (1 << 2)
   __u32 types;
   struct ublk_param_basic basic;
   struct ublk_param_discard discard;
+  struct ublk_param_devt devt;
 };
 #endif
diff --git a/libc/kernel/uapi/linux/uhid.h b/libc/kernel/uapi/linux/uhid.h
index 228ee50..1d471f8 100644
--- a/libc/kernel/uapi/linux/uhid.h
+++ b/libc/kernel/uapi/linux/uhid.h
@@ -106,7 +106,7 @@
   __u8 name[128];
   __u8 phys[64];
   __u8 uniq[64];
-  __u8 __user * rd_data;
+  __u8  * rd_data;
   __u16 rd_size;
   __u16 bus;
   __u32 vendor;
diff --git a/libc/kernel/uapi/linux/uio.h b/libc/kernel/uapi/linux/uio.h
index fa955cd..04814c7 100644
--- a/libc/kernel/uapi/linux/uio.h
+++ b/libc/kernel/uapi/linux/uio.h
@@ -21,7 +21,7 @@
 #include <linux/compiler.h>
 #include <linux/types.h>
 struct iovec {
-  void __user * iov_base;
+  void  * iov_base;
   __kernel_size_t iov_len;
 };
 #define UIO_FASTIOV 8
diff --git a/libc/kernel/uapi/linux/usb/ch9.h b/libc/kernel/uapi/linux/usb/ch9.h
index 49eb5fa..9ddc640 100644
--- a/libc/kernel/uapi/linux/usb/ch9.h
+++ b/libc/kernel/uapi/linux/usb/ch9.h
@@ -417,6 +417,16 @@
   __u8 ContainerID[16];
 } __attribute__((packed));
 #define USB_DT_USB_SS_CONTN_ID_SIZE 20
+#define USB_PLAT_DEV_CAP_TYPE 5
+struct usb_plat_dev_cap_descriptor {
+  __u8 bLength;
+  __u8 bDescriptorType;
+  __u8 bDevCapabilityType;
+  __u8 bReserved;
+  __u8 UUID[16];
+  __u8 CapabilityData[];
+} __attribute__((packed));
+#define USB_DT_USB_PLAT_DEV_CAP_SIZE(capability_data_size) (20 + capability_data_size)
 #define USB_SSP_CAP_TYPE 0xa
 struct usb_ssp_cap_descriptor {
   __u8 bLength;
diff --git a/libc/kernel/uapi/linux/usb/tmc.h b/libc/kernel/uapi/linux/usb/tmc.h
index 6d0add1..b267290 100644
--- a/libc/kernel/uapi/linux/usb/tmc.h
+++ b/libc/kernel/uapi/linux/usb/tmc.h
@@ -46,7 +46,7 @@
 } __attribute__((packed));
 struct usbtmc_ctrlrequest {
   struct usbtmc_request req;
-  void __user * data;
+  void  * data;
 } __attribute__((packed));
 struct usbtmc_termchar {
   __u8 term_char;
@@ -59,7 +59,7 @@
   __u32 transfer_size;
   __u32 transferred;
   __u32 flags;
-  void __user * message;
+  void  * message;
 } __attribute__((packed));
 #define USBTMC_IOC_NR 91
 #define USBTMC_IOCTL_INDICATOR_PULSE _IO(USBTMC_IOC_NR, 1)
diff --git a/libc/kernel/uapi/linux/usb/video.h b/libc/kernel/uapi/linux/usb/video.h
index c3d360a..0ceabe7 100644
--- a/libc/kernel/uapi/linux/usb/video.h
+++ b/libc/kernel/uapi/linux/usb/video.h
@@ -139,6 +139,32 @@
 #define UVC_CONTROL_CAP_DISABLED (1 << 2)
 #define UVC_CONTROL_CAP_AUTOUPDATE (1 << 3)
 #define UVC_CONTROL_CAP_ASYNCHRONOUS (1 << 4)
+enum uvc_color_primaries_values {
+  UVC_COLOR_PRIMARIES_UNSPECIFIED,
+  UVC_COLOR_PRIMARIES_BT_709_SRGB,
+  UVC_COLOR_PRIMARIES_BT_470_2_M,
+  UVC_COLOR_PRIMARIES_BT_470_2_B_G,
+  UVC_COLOR_PRIMARIES_SMPTE_170M,
+  UVC_COLOR_PRIMARIES_SMPTE_240M,
+};
+enum uvc_transfer_characteristics_values {
+  UVC_TRANSFER_CHARACTERISTICS_UNSPECIFIED,
+  UVC_TRANSFER_CHARACTERISTICS_BT_709,
+  UVC_TRANSFER_CHARACTERISTICS_BT_470_2_M,
+  UVC_TRANSFER_CHARACTERISTICS_BT_470_2_B_G,
+  UVC_TRANSFER_CHARACTERISTICS_SMPTE_170M,
+  UVC_TRANSFER_CHARACTERISTICS_SMPTE_240M,
+  UVC_TRANSFER_CHARACTERISTICS_LINEAR,
+  UVC_TRANSFER_CHARACTERISTICS_SRGB,
+};
+enum uvc_matrix_coefficients {
+  UVC_MATRIX_COEFFICIENTS_UNSPECIFIED,
+  UVC_MATRIX_COEFFICIENTS_BT_709,
+  UVC_MATRIX_COEFFICIENTS_FCC,
+  UVC_MATRIX_COEFFICIENTS_BT_470_2_B_G,
+  UVC_MATRIX_COEFFICIENTS_SMPTE_170M,
+  UVC_MATRIX_COEFFICIENTS_SMPTE_240M,
+};
 struct uvc_descriptor_header {
   __u8 bLength;
   __u8 bDescriptorType;
diff --git a/libc/kernel/uapi/linux/usbdevice_fs.h b/libc/kernel/uapi/linux/usbdevice_fs.h
index 5fef522..af8681b 100644
--- a/libc/kernel/uapi/linux/usbdevice_fs.h
+++ b/libc/kernel/uapi/linux/usbdevice_fs.h
@@ -27,13 +27,13 @@
   __u16 wIndex;
   __u16 wLength;
   __u32 timeout;
-  void __user * data;
+  void  * data;
 };
 struct usbdevfs_bulktransfer {
   unsigned int ep;
   unsigned int len;
   unsigned int timeout;
-  void __user * data;
+  void  * data;
 };
 struct usbdevfs_setinterface {
   unsigned int interface;
@@ -41,7 +41,7 @@
 };
 struct usbdevfs_disconnectsignal {
   unsigned int signr;
-  void __user * context;
+  void  * context;
 };
 #define USBDEVFS_MAXDRIVERNAME 255
 struct usbdevfs_getdriver {
@@ -80,7 +80,7 @@
   unsigned char endpoint;
   int status;
   unsigned int flags;
-  void __user * buffer;
+  void  * buffer;
   int buffer_length;
   int actual_length;
   int start_frame;
@@ -90,13 +90,13 @@
   };
   int error_count;
   unsigned int signr;
-  void __user * usercontext;
+  void  * usercontext;
   struct usbdevfs_iso_packet_desc iso_frame_desc[];
 };
 struct usbdevfs_ioctl {
   int ifno;
   int ioctl_code;
-  void __user * data;
+  void  * data;
 };
 struct usbdevfs_hub_portinfo {
   char nports;
diff --git a/libc/kernel/uapi/linux/uuid.h b/libc/kernel/uapi/linux/uuid.h
index d0f82c1..1505137 100644
--- a/libc/kernel/uapi/linux/uuid.h
+++ b/libc/kernel/uapi/linux/uuid.h
@@ -21,11 +21,9 @@
 #include <linux/types.h>
 typedef struct {
   __u8 b[16];
-} guid_t;
-#define GUID_INIT(a,b,c,d0,d1,d2,d3,d4,d5,d6,d7) \
-((guid_t) \
+} uuid_le;
+#define UUID_LE(a,b,c,d0,d1,d2,d3,d4,d5,d6,d7) \
+((uuid_le) \
 { { (a) & 0xff, ((a) >> 8) & 0xff, ((a) >> 16) & 0xff, ((a) >> 24) & 0xff, (b) & 0xff, ((b) >> 8) & 0xff, (c) & 0xff, ((c) >> 8) & 0xff, (d0), (d1), (d2), (d3), (d4), (d5), (d6), (d7) } })
-typedef guid_t uuid_le;
-#define UUID_LE(a,b,c,d0,d1,d2,d3,d4,d5,d6,d7) GUID_INIT(a, b, c, d0, d1, d2, d3, d4, d5, d6, d7)
 #define NULL_UUID_LE UUID_LE(0x00000000, 0x0000, 0x0000, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00)
 #endif
diff --git a/libc/kernel/uapi/linux/uvcvideo.h b/libc/kernel/uapi/linux/uvcvideo.h
index 46528a9..b63858f 100644
--- a/libc/kernel/uapi/linux/uvcvideo.h
+++ b/libc/kernel/uapi/linux/uvcvideo.h
@@ -36,9 +36,10 @@
 #define UVC_CTRL_FLAG_AUTO_UPDATE (1 << 7)
 #define UVC_CTRL_FLAG_ASYNCHRONOUS (1 << 8)
 #define UVC_CTRL_FLAG_GET_RANGE (UVC_CTRL_FLAG_GET_CUR | UVC_CTRL_FLAG_GET_MIN | UVC_CTRL_FLAG_GET_MAX | UVC_CTRL_FLAG_GET_RES | UVC_CTRL_FLAG_GET_DEF)
+#define UVC_MENU_NAME_LEN 32
 struct uvc_menu_info {
   __u32 value;
-  __u8 name[32];
+  __u8 name[UVC_MENU_NAME_LEN];
 };
 struct uvc_xu_control_mapping {
   __u32 id;
@@ -49,7 +50,7 @@
   __u8 offset;
   __u32 v4l2_type;
   __u32 data_type;
-  struct uvc_menu_info __user * menu_info;
+  struct uvc_menu_info  * menu_info;
   __u32 menu_count;
   __u32 reserved[4];
 };
@@ -58,7 +59,7 @@
   __u8 selector;
   __u8 query;
   __u16 size;
-  __u8 __user * data;
+  __u8  * data;
 };
 #define UVCIOC_CTRL_MAP _IOWR('u', 0x20, struct uvc_xu_control_mapping)
 #define UVCIOC_CTRL_QUERY _IOWR('u', 0x21, struct uvc_xu_control_query)
diff --git a/libc/kernel/uapi/linux/v4l2-subdev.h b/libc/kernel/uapi/linux/v4l2-subdev.h
index 2954dc3..8b2c1bd 100644
--- a/libc/kernel/uapi/linux/v4l2-subdev.h
+++ b/libc/kernel/uapi/linux/v4l2-subdev.h
@@ -18,6 +18,7 @@
  ****************************************************************************/
 #ifndef __LINUX_V4L2_SUBDEV_H
 #define __LINUX_V4L2_SUBDEV_H
+#include <linux/const.h>
 #include <linux/ioctl.h>
 #include <linux/types.h>
 #include <linux/v4l2-common.h>
@@ -30,13 +31,15 @@
   __u32 which;
   __u32 pad;
   struct v4l2_mbus_framefmt format;
-  __u32 reserved[8];
+  __u32 stream;
+  __u32 reserved[7];
 };
 struct v4l2_subdev_crop {
   __u32 which;
   __u32 pad;
   struct v4l2_rect rect;
-  __u32 reserved[8];
+  __u32 stream;
+  __u32 reserved[7];
 };
 #define V4L2_SUBDEV_MBUS_CODE_CSC_COLORSPACE 0x00000001
 #define V4L2_SUBDEV_MBUS_CODE_CSC_XFER_FUNC 0x00000002
@@ -49,7 +52,8 @@
   __u32 code;
   __u32 which;
   __u32 flags;
-  __u32 reserved[7];
+  __u32 stream;
+  __u32 reserved[6];
 };
 struct v4l2_subdev_frame_size_enum {
   __u32 index;
@@ -60,12 +64,14 @@
   __u32 min_height;
   __u32 max_height;
   __u32 which;
-  __u32 reserved[8];
+  __u32 stream;
+  __u32 reserved[7];
 };
 struct v4l2_subdev_frame_interval {
   __u32 pad;
   struct v4l2_fract interval;
-  __u32 reserved[9];
+  __u32 stream;
+  __u32 reserved[8];
 };
 struct v4l2_subdev_frame_interval_enum {
   __u32 index;
@@ -75,7 +81,8 @@
   __u32 height;
   struct v4l2_fract interval;
   __u32 which;
-  __u32 reserved[8];
+  __u32 stream;
+  __u32 reserved[7];
 };
 struct v4l2_subdev_selection {
   __u32 which;
@@ -83,7 +90,8 @@
   __u32 target;
   __u32 flags;
   struct v4l2_rect r;
-  __u32 reserved[8];
+  __u32 stream;
+  __u32 reserved[7];
 };
 struct v4l2_subdev_capability {
   __u32 version;
@@ -91,6 +99,22 @@
   __u32 reserved[14];
 };
 #define V4L2_SUBDEV_CAP_RO_SUBDEV 0x00000001
+#define V4L2_SUBDEV_CAP_STREAMS 0x00000002
+#define V4L2_SUBDEV_ROUTE_FL_ACTIVE (1U << 0)
+struct v4l2_subdev_route {
+  __u32 sink_pad;
+  __u32 sink_stream;
+  __u32 source_pad;
+  __u32 source_stream;
+  __u32 flags;
+  __u32 reserved[5];
+};
+struct v4l2_subdev_routing {
+  __u32 which;
+  __u32 num_routes;
+  __u64 routes;
+  __u32 reserved[6];
+};
 #define v4l2_subdev_edid v4l2_edid
 #define VIDIOC_SUBDEV_QUERYCAP _IOR('V', 0, struct v4l2_subdev_capability)
 #define VIDIOC_SUBDEV_G_FMT _IOWR('V', 4, struct v4l2_subdev_format)
@@ -104,6 +128,8 @@
 #define VIDIOC_SUBDEV_S_CROP _IOWR('V', 60, struct v4l2_subdev_crop)
 #define VIDIOC_SUBDEV_G_SELECTION _IOWR('V', 61, struct v4l2_subdev_selection)
 #define VIDIOC_SUBDEV_S_SELECTION _IOWR('V', 62, struct v4l2_subdev_selection)
+#define VIDIOC_SUBDEV_G_ROUTING _IOWR('V', 38, struct v4l2_subdev_routing)
+#define VIDIOC_SUBDEV_S_ROUTING _IOWR('V', 39, struct v4l2_subdev_routing)
 #define VIDIOC_SUBDEV_G_STD _IOR('V', 23, v4l2_std_id)
 #define VIDIOC_SUBDEV_S_STD _IOW('V', 24, v4l2_std_id)
 #define VIDIOC_SUBDEV_ENUMSTD _IOWR('V', 25, struct v4l2_standard)
diff --git a/libc/kernel/uapi/linux/version.h b/libc/kernel/uapi/linux/version.h
index 0d50613..9d48e3d 100644
--- a/libc/kernel/uapi/linux/version.h
+++ b/libc/kernel/uapi/linux/version.h
@@ -16,8 +16,8 @@
  ***
  ****************************************************************************
  ****************************************************************************/
-#define LINUX_VERSION_CODE 393728
+#define LINUX_VERSION_CODE 393984
 #define KERNEL_VERSION(a,b,c) (((a) << 16) + ((b) << 8) + ((c) > 255 ? 255 : (c)))
 #define LINUX_VERSION_MAJOR 6
-#define LINUX_VERSION_PATCHLEVEL 2
+#define LINUX_VERSION_PATCHLEVEL 3
 #define LINUX_VERSION_SUBLEVEL 0
diff --git a/libc/kernel/uapi/linux/vfio.h b/libc/kernel/uapi/linux/vfio.h
index 7dc3440..3c1821c 100644
--- a/libc/kernel/uapi/linux/vfio.h
+++ b/libc/kernel/uapi/linux/vfio.h
@@ -390,7 +390,7 @@
 struct vfio_bitmap {
   __u64 pgsize;
   __u64 size;
-  __u64 __user * data;
+  __u64  * data;
 };
 struct vfio_iommu_type1_dma_unmap {
   __u32 argsz;
diff --git a/libc/kernel/uapi/linux/vhost.h b/libc/kernel/uapi/linux/vhost.h
index e5b1327..5138f0c 100644
--- a/libc/kernel/uapi/linux/vhost.h
+++ b/libc/kernel/uapi/linux/vhost.h
@@ -69,4 +69,5 @@
 #define VHOST_VDPA_GET_VRING_GROUP _IOWR(VHOST_VIRTIO, 0x7B, struct vhost_vring_state)
 #define VHOST_VDPA_SET_GROUP_ASID _IOW(VHOST_VIRTIO, 0x7C, struct vhost_vring_state)
 #define VHOST_VDPA_SUSPEND _IO(VHOST_VIRTIO, 0x7D)
+#define VHOST_VDPA_RESUME _IO(VHOST_VIRTIO, 0x7E)
 #endif
diff --git a/libc/kernel/uapi/linux/vhost_types.h b/libc/kernel/uapi/linux/vhost_types.h
index 32efa85..1669c28 100644
--- a/libc/kernel/uapi/linux/vhost_types.h
+++ b/libc/kernel/uapi/linux/vhost_types.h
@@ -106,4 +106,5 @@
 #define VHOST_BACKEND_F_IOTLB_BATCH 0x2
 #define VHOST_BACKEND_F_IOTLB_ASID 0x3
 #define VHOST_BACKEND_F_SUSPEND 0x4
+#define VHOST_BACKEND_F_RESUME 0x5
 #endif
diff --git a/libc/kernel/uapi/linux/videodev2.h b/libc/kernel/uapi/linux/videodev2.h
index d418fd2..95c2d94 100644
--- a/libc/kernel/uapi/linux/videodev2.h
+++ b/libc/kernel/uapi/linux/videodev2.h
@@ -244,6 +244,9 @@
 #define V4L2_PIX_FMT_RGBX32 v4l2_fourcc('X', 'B', '2', '4')
 #define V4L2_PIX_FMT_ARGB32 v4l2_fourcc('B', 'A', '2', '4')
 #define V4L2_PIX_FMT_XRGB32 v4l2_fourcc('B', 'X', '2', '4')
+#define V4L2_PIX_FMT_RGBX1010102 v4l2_fourcc('R', 'X', '3', '0')
+#define V4L2_PIX_FMT_RGBA1010102 v4l2_fourcc('R', 'A', '3', '0')
+#define V4L2_PIX_FMT_ARGB2101010 v4l2_fourcc('A', 'R', '3', '0')
 #define V4L2_PIX_FMT_GREY v4l2_fourcc('G', 'R', 'E', 'Y')
 #define V4L2_PIX_FMT_Y4 v4l2_fourcc('Y', '0', '4', ' ')
 #define V4L2_PIX_FMT_Y6 v4l2_fourcc('Y', '0', '6', ' ')
@@ -275,6 +278,9 @@
 #define V4L2_PIX_FMT_YUVA32 v4l2_fourcc('Y', 'U', 'V', 'A')
 #define V4L2_PIX_FMT_YUVX32 v4l2_fourcc('Y', 'U', 'V', 'X')
 #define V4L2_PIX_FMT_M420 v4l2_fourcc('M', '4', '2', '0')
+#define V4L2_PIX_FMT_Y210 v4l2_fourcc('Y', '2', '1', '0')
+#define V4L2_PIX_FMT_Y212 v4l2_fourcc('Y', '2', '1', '2')
+#define V4L2_PIX_FMT_Y216 v4l2_fourcc('Y', '2', '1', '6')
 #define V4L2_PIX_FMT_NV12 v4l2_fourcc('N', 'V', '1', '2')
 #define V4L2_PIX_FMT_NV21 v4l2_fourcc('N', 'V', '2', '1')
 #define V4L2_PIX_FMT_NV16 v4l2_fourcc('N', 'V', '1', '6')
@@ -650,7 +656,7 @@
 #define V4L2_FBUF_FLAG_SRC_CHROMAKEY 0x0040
 struct v4l2_clip {
   struct v4l2_rect c;
-  struct v4l2_clip __user * next;
+  struct v4l2_clip  * next;
 };
 struct v4l2_window {
   struct v4l2_rect w;
@@ -658,7 +664,7 @@
   __u32 chromakey;
   struct v4l2_clip * clips;
   __u32 clipcount;
-  void __user * bitmap;
+  void  * bitmap;
   __u8 global_alpha;
 };
 struct v4l2_captureparm {
@@ -895,32 +901,32 @@
   union {
     __s32 value;
     __s64 value64;
-    char __user * string;
-    __u8 __user * p_u8;
-    __u16 __user * p_u16;
-    __u32 __user * p_u32;
-    __u32 __user * p_s32;
-    __u32 __user * p_s64;
-    struct v4l2_area __user * p_area;
-    struct v4l2_ctrl_h264_sps __user * p_h264_sps;
+    char  * string;
+    __u8  * p_u8;
+    __u16  * p_u16;
+    __u32  * p_u32;
+    __u32  * p_s32;
+    __u32  * p_s64;
+    struct v4l2_area  * p_area;
+    struct v4l2_ctrl_h264_sps  * p_h264_sps;
     struct v4l2_ctrl_h264_pps * p_h264_pps;
-    struct v4l2_ctrl_h264_scaling_matrix __user * p_h264_scaling_matrix;
-    struct v4l2_ctrl_h264_pred_weights __user * p_h264_pred_weights;
-    struct v4l2_ctrl_h264_slice_params __user * p_h264_slice_params;
-    struct v4l2_ctrl_h264_decode_params __user * p_h264_decode_params;
-    struct v4l2_ctrl_fwht_params __user * p_fwht_params;
-    struct v4l2_ctrl_vp8_frame __user * p_vp8_frame;
-    struct v4l2_ctrl_mpeg2_sequence __user * p_mpeg2_sequence;
-    struct v4l2_ctrl_mpeg2_picture __user * p_mpeg2_picture;
-    struct v4l2_ctrl_mpeg2_quantisation __user * p_mpeg2_quantisation;
-    struct v4l2_ctrl_vp9_compressed_hdr __user * p_vp9_compressed_hdr_probs;
-    struct v4l2_ctrl_vp9_frame __user * p_vp9_frame;
-    struct v4l2_ctrl_hevc_sps __user * p_hevc_sps;
-    struct v4l2_ctrl_hevc_pps __user * p_hevc_pps;
-    struct v4l2_ctrl_hevc_slice_params __user * p_hevc_slice_params;
-    struct v4l2_ctrl_hevc_scaling_matrix __user * p_hevc_scaling_matrix;
-    struct v4l2_ctrl_hevc_decode_params __user * p_hevc_decode_params;
-    void __user * ptr;
+    struct v4l2_ctrl_h264_scaling_matrix  * p_h264_scaling_matrix;
+    struct v4l2_ctrl_h264_pred_weights  * p_h264_pred_weights;
+    struct v4l2_ctrl_h264_slice_params  * p_h264_slice_params;
+    struct v4l2_ctrl_h264_decode_params  * p_h264_decode_params;
+    struct v4l2_ctrl_fwht_params  * p_fwht_params;
+    struct v4l2_ctrl_vp8_frame  * p_vp8_frame;
+    struct v4l2_ctrl_mpeg2_sequence  * p_mpeg2_sequence;
+    struct v4l2_ctrl_mpeg2_picture  * p_mpeg2_picture;
+    struct v4l2_ctrl_mpeg2_quantisation  * p_mpeg2_quantisation;
+    struct v4l2_ctrl_vp9_compressed_hdr  * p_vp9_compressed_hdr_probs;
+    struct v4l2_ctrl_vp9_frame  * p_vp9_frame;
+    struct v4l2_ctrl_hevc_sps  * p_hevc_sps;
+    struct v4l2_ctrl_hevc_pps  * p_hevc_pps;
+    struct v4l2_ctrl_hevc_slice_params  * p_hevc_slice_params;
+    struct v4l2_ctrl_hevc_scaling_matrix  * p_hevc_scaling_matrix;
+    struct v4l2_ctrl_hevc_decode_params  * p_hevc_decode_params;
+    void  * ptr;
   };
 } __attribute__((packed));
 struct v4l2_ext_controls {
diff --git a/libc/kernel/uapi/linux/virtio_blk.h b/libc/kernel/uapi/linux/virtio_blk.h
index 0dd08c5..1b7c7e9 100644
--- a/libc/kernel/uapi/linux/virtio_blk.h
+++ b/libc/kernel/uapi/linux/virtio_blk.h
@@ -32,6 +32,7 @@
 #define VIRTIO_BLK_F_DISCARD 13
 #define VIRTIO_BLK_F_WRITE_ZEROES 14
 #define VIRTIO_BLK_F_SECURE_ERASE 16
+#define VIRTIO_BLK_F_ZONED 17
 #ifndef VIRTIO_BLK_NO_LEGACY
 #define VIRTIO_BLK_F_BARRIER 0
 #define VIRTIO_BLK_F_SCSI 7
@@ -67,6 +68,15 @@
   __virtio32 max_secure_erase_sectors;
   __virtio32 max_secure_erase_seg;
   __virtio32 secure_erase_sector_alignment;
+  struct virtio_blk_zoned_characteristics {
+    __virtio32 zone_sectors;
+    __virtio32 max_open_zones;
+    __virtio32 max_active_zones;
+    __virtio32 max_append_sectors;
+    __virtio32 write_granularity;
+    __u8 model;
+    __u8 unused2[3];
+  } zoned;
 } __attribute__((packed));
 #define VIRTIO_BLK_T_IN 0
 #define VIRTIO_BLK_T_OUT 1
@@ -78,6 +88,13 @@
 #define VIRTIO_BLK_T_DISCARD 11
 #define VIRTIO_BLK_T_WRITE_ZEROES 13
 #define VIRTIO_BLK_T_SECURE_ERASE 14
+#define VIRTIO_BLK_T_ZONE_APPEND 15
+#define VIRTIO_BLK_T_ZONE_REPORT 16
+#define VIRTIO_BLK_T_ZONE_OPEN 18
+#define VIRTIO_BLK_T_ZONE_CLOSE 20
+#define VIRTIO_BLK_T_ZONE_FINISH 22
+#define VIRTIO_BLK_T_ZONE_RESET 24
+#define VIRTIO_BLK_T_ZONE_RESET_ALL 26
 #ifndef VIRTIO_BLK_NO_LEGACY
 #define VIRTIO_BLK_T_BARRIER 0x80000000
 #endif
@@ -86,6 +103,33 @@
   __virtio32 ioprio;
   __virtio64 sector;
 };
+#define VIRTIO_BLK_Z_NONE 0
+#define VIRTIO_BLK_Z_HM 1
+#define VIRTIO_BLK_Z_HA 2
+struct virtio_blk_zone_descriptor {
+  __virtio64 z_cap;
+  __virtio64 z_start;
+  __virtio64 z_wp;
+  __u8 z_type;
+  __u8 z_state;
+  __u8 reserved[38];
+};
+struct virtio_blk_zone_report {
+  __virtio64 nr_zones;
+  __u8 reserved[56];
+  struct virtio_blk_zone_descriptor zones[];
+};
+#define VIRTIO_BLK_ZT_CONV 1
+#define VIRTIO_BLK_ZT_SWR 2
+#define VIRTIO_BLK_ZT_SWP 3
+#define VIRTIO_BLK_ZS_NOT_WP 0
+#define VIRTIO_BLK_ZS_EMPTY 1
+#define VIRTIO_BLK_ZS_IOPEN 2
+#define VIRTIO_BLK_ZS_EOPEN 3
+#define VIRTIO_BLK_ZS_CLOSED 4
+#define VIRTIO_BLK_ZS_RDONLY 13
+#define VIRTIO_BLK_ZS_FULL 14
+#define VIRTIO_BLK_ZS_OFFLINE 15
 #define VIRTIO_BLK_WRITE_ZEROES_FLAG_UNMAP 0x00000001
 struct virtio_blk_discard_write_zeroes {
   __le64 sector;
@@ -103,4 +147,8 @@
 #define VIRTIO_BLK_S_OK 0
 #define VIRTIO_BLK_S_IOERR 1
 #define VIRTIO_BLK_S_UNSUPP 2
+#define VIRTIO_BLK_S_ZONE_INVALID_CMD 3
+#define VIRTIO_BLK_S_ZONE_UNALIGNED_WP 4
+#define VIRTIO_BLK_S_ZONE_OPEN_RESOURCE 5
+#define VIRTIO_BLK_S_ZONE_ACTIVE_RESOURCE 6
 #endif
diff --git a/libc/kernel/uapi/linux/wireless.h b/libc/kernel/uapi/linux/wireless.h
index ca31dd2..eb57fff 100644
--- a/libc/kernel/uapi/linux/wireless.h
+++ b/libc/kernel/uapi/linux/wireless.h
@@ -264,7 +264,7 @@
   __u16 flags;
 };
 struct iw_point {
-  void __user * pointer;
+  void  * pointer;
   __u16 length;
   __u16 flags;
 };
diff --git a/libc/kernel/uapi/mtd/mtd-abi.h b/libc/kernel/uapi/mtd/mtd-abi.h
index 6e26cae..aed2acc 100644
--- a/libc/kernel/uapi/mtd/mtd-abi.h
+++ b/libc/kernel/uapi/mtd/mtd-abi.h
@@ -30,7 +30,7 @@
 struct mtd_oob_buf {
   __u32 start;
   __u32 length;
-  unsigned char __user * ptr;
+  unsigned char  * ptr;
 };
 struct mtd_oob_buf64 {
   __u64 start;
diff --git a/libc/kernel/uapi/rdma/hns-abi.h b/libc/kernel/uapi/rdma/hns-abi.h
index 0407571..f778ef2 100644
--- a/libc/kernel/uapi/rdma/hns-abi.h
+++ b/libc/kernel/uapi/rdma/hns-abi.h
@@ -62,9 +62,13 @@
 };
 enum {
   HNS_ROCE_EXSGE_FLAGS = 1 << 0,
+  HNS_ROCE_RQ_INLINE_FLAGS = 1 << 1,
+  HNS_ROCE_CQE_INLINE_FLAGS = 1 << 2,
 };
 enum {
   HNS_ROCE_RSP_EXSGE_FLAGS = 1 << 0,
+  HNS_ROCE_RSP_RQ_INLINE_FLAGS = 1 << 1,
+  HNS_ROCE_RSP_CQE_INLINE_FLAGS = 1 << 2,
 };
 struct hns_roce_ib_alloc_ucontext_resp {
   __u32 qp_tab_size;
diff --git a/libc/kernel/uapi/scsi/scsi_bsg_fc.h b/libc/kernel/uapi/scsi/scsi_bsg_fc.h
index 2647249..3836282 100644
--- a/libc/kernel/uapi/scsi/scsi_bsg_fc.h
+++ b/libc/kernel/uapi/scsi/scsi_bsg_fc.h
@@ -69,7 +69,7 @@
   __u32 vendor_cmd[];
 };
 struct fc_bsg_host_vendor_reply {
-  __u32 vendor_rsp[0];
+  __DECLARE_FLEX_ARRAY(__u32, vendor_rsp);
 };
 struct fc_bsg_rport_els {
   __u8 els_code;
diff --git a/libc/kernel/uapi/scsi/scsi_bsg_mpi3mr.h b/libc/kernel/uapi/scsi/scsi_bsg_mpi3mr.h
index fcba8cd..48e88d3 100644
--- a/libc/kernel/uapi/scsi/scsi_bsg_mpi3mr.h
+++ b/libc/kernel/uapi/scsi/scsi_bsg_mpi3mr.h
@@ -220,9 +220,6 @@
     struct mpi3mr_bsg_mptcmd mptcmd;
   } cmd;
 };
-#ifndef MPI3_NVME_ENCAP_CMD_MAX
-#define MPI3_NVME_ENCAP_CMD_MAX (1)
-#endif
 struct mpi3_nvme_encapsulated_request {
   __le16 host_tag;
   __u8 ioc_use_only02;
@@ -236,7 +233,7 @@
   __le16 flags;
   __le32 data_length;
   __le32 reserved14[3];
-  __le32 command[MPI3_NVME_ENCAP_CMD_MAX];
+  __le32 command[];
 };
 struct mpi3_nvme_encapsulated_error_reply {
   __le16 host_tag;
diff --git a/libc/kernel/uapi/scsi/scsi_bsg_ufs.h b/libc/kernel/uapi/scsi/scsi_bsg_ufs.h
index ae5c757..036243e 100644
--- a/libc/kernel/uapi/scsi/scsi_bsg_ufs.h
+++ b/libc/kernel/uapi/scsi/scsi_bsg_ufs.h
@@ -20,8 +20,22 @@
 #define SCSI_BSG_UFS_H
 #include <linux/types.h>
 #define UFS_CDB_SIZE 16
-#define UPIU_TRANSACTION_UIC_CMD 0x1F
 #define UIC_CMD_SIZE (sizeof(__u32) * 4)
+enum ufs_bsg_msg_code {
+  UPIU_TRANSACTION_UIC_CMD = 0x1F,
+  UPIU_TRANSACTION_ARPMB_CMD,
+};
+enum ufs_rpmb_op_type {
+  UFS_RPMB_WRITE_KEY = 0x01,
+  UFS_RPMB_READ_CNT = 0x02,
+  UFS_RPMB_WRITE = 0x03,
+  UFS_RPMB_READ = 0x04,
+  UFS_RPMB_READ_RESP = 0x05,
+  UFS_RPMB_SEC_CONF_WRITE = 0x06,
+  UFS_RPMB_SEC_CONF_READ = 0x07,
+  UFS_RPMB_PURGE_ENABLE = 0x08,
+  UFS_RPMB_PURGE_STATUS_READ = 0x09,
+};
 struct utp_upiu_header {
   __be32 dword_0;
   __be32 dword_1;
@@ -49,13 +63,36 @@
     struct utp_upiu_query uc;
   };
 };
+struct ufs_arpmb_meta {
+  __be16 req_resp_type;
+  __u8 nonce[16];
+  __be32 write_counter;
+  __be16 addr_lun;
+  __be16 block_count;
+  __be16 result;
+} __attribute__((__packed__));
+struct ufs_ehs {
+  __u8 length;
+  __u8 ehs_type;
+  __be16 ehssub_type;
+  struct ufs_arpmb_meta meta;
+  __u8 mac_key[32];
+} __attribute__((__packed__));
 struct ufs_bsg_request {
   __u32 msgcode;
   struct utp_upiu_req upiu_req;
 };
 struct ufs_bsg_reply {
-  __u32 result;
+  int result;
   __u32 reply_payload_rcv_len;
   struct utp_upiu_req upiu_rsp;
 };
+struct ufs_rpmb_request {
+  struct ufs_bsg_request bsg_request;
+  struct ufs_ehs ehs_req;
+};
+struct ufs_rpmb_reply {
+  struct ufs_bsg_reply bsg_reply;
+  struct ufs_ehs ehs_rsp;
+};
 #endif
diff --git a/libc/kernel/uapi/sound/asequencer.h b/libc/kernel/uapi/sound/asequencer.h
index 0076933..01a5058 100644
--- a/libc/kernel/uapi/sound/asequencer.h
+++ b/libc/kernel/uapi/sound/asequencer.h
@@ -209,9 +209,9 @@
 #define SNDRV_SEQ_CLIENT_DUMMY 14
 #define SNDRV_SEQ_CLIENT_OSS 15
 typedef int __bitwise snd_seq_client_type_t;
-#define NO_CLIENT ((__force snd_seq_client_type_t) 0)
-#define USER_CLIENT ((__force snd_seq_client_type_t) 1)
-#define KERNEL_CLIENT ((__force snd_seq_client_type_t) 2)
+#define NO_CLIENT (( snd_seq_client_type_t) 0)
+#define USER_CLIENT (( snd_seq_client_type_t) 1)
+#define KERNEL_CLIENT (( snd_seq_client_type_t) 2)
 #define SNDRV_SEQ_FILTER_BROADCAST (1U << 0)
 #define SNDRV_SEQ_FILTER_MULTICAST (1U << 1)
 #define SNDRV_SEQ_FILTER_BOUNCE (1U << 2)
diff --git a/libc/kernel/uapi/sound/asound.h b/libc/kernel/uapi/sound/asound.h
index 6e325e9..9c1a3ae 100644
--- a/libc/kernel/uapi/sound/asound.h
+++ b/libc/kernel/uapi/sound/asound.h
@@ -96,7 +96,7 @@
 struct snd_hwdep_dsp_image {
   unsigned int index;
   unsigned char name[64];
-  unsigned char __user * image;
+  unsigned char  * image;
   size_t length;
   unsigned long driver_data;
 };
@@ -125,64 +125,64 @@
   SNDRV_PCM_STREAM_LAST = SNDRV_PCM_STREAM_CAPTURE,
 };
 typedef int __bitwise snd_pcm_access_t;
-#define SNDRV_PCM_ACCESS_MMAP_INTERLEAVED ((__force snd_pcm_access_t) 0)
-#define SNDRV_PCM_ACCESS_MMAP_NONINTERLEAVED ((__force snd_pcm_access_t) 1)
-#define SNDRV_PCM_ACCESS_MMAP_COMPLEX ((__force snd_pcm_access_t) 2)
-#define SNDRV_PCM_ACCESS_RW_INTERLEAVED ((__force snd_pcm_access_t) 3)
-#define SNDRV_PCM_ACCESS_RW_NONINTERLEAVED ((__force snd_pcm_access_t) 4)
+#define SNDRV_PCM_ACCESS_MMAP_INTERLEAVED (( snd_pcm_access_t) 0)
+#define SNDRV_PCM_ACCESS_MMAP_NONINTERLEAVED (( snd_pcm_access_t) 1)
+#define SNDRV_PCM_ACCESS_MMAP_COMPLEX (( snd_pcm_access_t) 2)
+#define SNDRV_PCM_ACCESS_RW_INTERLEAVED (( snd_pcm_access_t) 3)
+#define SNDRV_PCM_ACCESS_RW_NONINTERLEAVED (( snd_pcm_access_t) 4)
 #define SNDRV_PCM_ACCESS_LAST SNDRV_PCM_ACCESS_RW_NONINTERLEAVED
 typedef int __bitwise snd_pcm_format_t;
-#define SNDRV_PCM_FORMAT_S8 ((__force snd_pcm_format_t) 0)
-#define SNDRV_PCM_FORMAT_U8 ((__force snd_pcm_format_t) 1)
-#define SNDRV_PCM_FORMAT_S16_LE ((__force snd_pcm_format_t) 2)
-#define SNDRV_PCM_FORMAT_S16_BE ((__force snd_pcm_format_t) 3)
-#define SNDRV_PCM_FORMAT_U16_LE ((__force snd_pcm_format_t) 4)
-#define SNDRV_PCM_FORMAT_U16_BE ((__force snd_pcm_format_t) 5)
-#define SNDRV_PCM_FORMAT_S24_LE ((__force snd_pcm_format_t) 6)
-#define SNDRV_PCM_FORMAT_S24_BE ((__force snd_pcm_format_t) 7)
-#define SNDRV_PCM_FORMAT_U24_LE ((__force snd_pcm_format_t) 8)
-#define SNDRV_PCM_FORMAT_U24_BE ((__force snd_pcm_format_t) 9)
-#define SNDRV_PCM_FORMAT_S32_LE ((__force snd_pcm_format_t) 10)
-#define SNDRV_PCM_FORMAT_S32_BE ((__force snd_pcm_format_t) 11)
-#define SNDRV_PCM_FORMAT_U32_LE ((__force snd_pcm_format_t) 12)
-#define SNDRV_PCM_FORMAT_U32_BE ((__force snd_pcm_format_t) 13)
-#define SNDRV_PCM_FORMAT_FLOAT_LE ((__force snd_pcm_format_t) 14)
-#define SNDRV_PCM_FORMAT_FLOAT_BE ((__force snd_pcm_format_t) 15)
-#define SNDRV_PCM_FORMAT_FLOAT64_LE ((__force snd_pcm_format_t) 16)
-#define SNDRV_PCM_FORMAT_FLOAT64_BE ((__force snd_pcm_format_t) 17)
-#define SNDRV_PCM_FORMAT_IEC958_SUBFRAME_LE ((__force snd_pcm_format_t) 18)
-#define SNDRV_PCM_FORMAT_IEC958_SUBFRAME_BE ((__force snd_pcm_format_t) 19)
-#define SNDRV_PCM_FORMAT_MU_LAW ((__force snd_pcm_format_t) 20)
-#define SNDRV_PCM_FORMAT_A_LAW ((__force snd_pcm_format_t) 21)
-#define SNDRV_PCM_FORMAT_IMA_ADPCM ((__force snd_pcm_format_t) 22)
-#define SNDRV_PCM_FORMAT_MPEG ((__force snd_pcm_format_t) 23)
-#define SNDRV_PCM_FORMAT_GSM ((__force snd_pcm_format_t) 24)
-#define SNDRV_PCM_FORMAT_S20_LE ((__force snd_pcm_format_t) 25)
-#define SNDRV_PCM_FORMAT_S20_BE ((__force snd_pcm_format_t) 26)
-#define SNDRV_PCM_FORMAT_U20_LE ((__force snd_pcm_format_t) 27)
-#define SNDRV_PCM_FORMAT_U20_BE ((__force snd_pcm_format_t) 28)
-#define SNDRV_PCM_FORMAT_SPECIAL ((__force snd_pcm_format_t) 31)
-#define SNDRV_PCM_FORMAT_S24_3LE ((__force snd_pcm_format_t) 32)
-#define SNDRV_PCM_FORMAT_S24_3BE ((__force snd_pcm_format_t) 33)
-#define SNDRV_PCM_FORMAT_U24_3LE ((__force snd_pcm_format_t) 34)
-#define SNDRV_PCM_FORMAT_U24_3BE ((__force snd_pcm_format_t) 35)
-#define SNDRV_PCM_FORMAT_S20_3LE ((__force snd_pcm_format_t) 36)
-#define SNDRV_PCM_FORMAT_S20_3BE ((__force snd_pcm_format_t) 37)
-#define SNDRV_PCM_FORMAT_U20_3LE ((__force snd_pcm_format_t) 38)
-#define SNDRV_PCM_FORMAT_U20_3BE ((__force snd_pcm_format_t) 39)
-#define SNDRV_PCM_FORMAT_S18_3LE ((__force snd_pcm_format_t) 40)
-#define SNDRV_PCM_FORMAT_S18_3BE ((__force snd_pcm_format_t) 41)
-#define SNDRV_PCM_FORMAT_U18_3LE ((__force snd_pcm_format_t) 42)
-#define SNDRV_PCM_FORMAT_U18_3BE ((__force snd_pcm_format_t) 43)
-#define SNDRV_PCM_FORMAT_G723_24 ((__force snd_pcm_format_t) 44)
-#define SNDRV_PCM_FORMAT_G723_24_1B ((__force snd_pcm_format_t) 45)
-#define SNDRV_PCM_FORMAT_G723_40 ((__force snd_pcm_format_t) 46)
-#define SNDRV_PCM_FORMAT_G723_40_1B ((__force snd_pcm_format_t) 47)
-#define SNDRV_PCM_FORMAT_DSD_U8 ((__force snd_pcm_format_t) 48)
-#define SNDRV_PCM_FORMAT_DSD_U16_LE ((__force snd_pcm_format_t) 49)
-#define SNDRV_PCM_FORMAT_DSD_U32_LE ((__force snd_pcm_format_t) 50)
-#define SNDRV_PCM_FORMAT_DSD_U16_BE ((__force snd_pcm_format_t) 51)
-#define SNDRV_PCM_FORMAT_DSD_U32_BE ((__force snd_pcm_format_t) 52)
+#define SNDRV_PCM_FORMAT_S8 (( snd_pcm_format_t) 0)
+#define SNDRV_PCM_FORMAT_U8 (( snd_pcm_format_t) 1)
+#define SNDRV_PCM_FORMAT_S16_LE (( snd_pcm_format_t) 2)
+#define SNDRV_PCM_FORMAT_S16_BE (( snd_pcm_format_t) 3)
+#define SNDRV_PCM_FORMAT_U16_LE (( snd_pcm_format_t) 4)
+#define SNDRV_PCM_FORMAT_U16_BE (( snd_pcm_format_t) 5)
+#define SNDRV_PCM_FORMAT_S24_LE (( snd_pcm_format_t) 6)
+#define SNDRV_PCM_FORMAT_S24_BE (( snd_pcm_format_t) 7)
+#define SNDRV_PCM_FORMAT_U24_LE (( snd_pcm_format_t) 8)
+#define SNDRV_PCM_FORMAT_U24_BE (( snd_pcm_format_t) 9)
+#define SNDRV_PCM_FORMAT_S32_LE (( snd_pcm_format_t) 10)
+#define SNDRV_PCM_FORMAT_S32_BE (( snd_pcm_format_t) 11)
+#define SNDRV_PCM_FORMAT_U32_LE (( snd_pcm_format_t) 12)
+#define SNDRV_PCM_FORMAT_U32_BE (( snd_pcm_format_t) 13)
+#define SNDRV_PCM_FORMAT_FLOAT_LE (( snd_pcm_format_t) 14)
+#define SNDRV_PCM_FORMAT_FLOAT_BE (( snd_pcm_format_t) 15)
+#define SNDRV_PCM_FORMAT_FLOAT64_LE (( snd_pcm_format_t) 16)
+#define SNDRV_PCM_FORMAT_FLOAT64_BE (( snd_pcm_format_t) 17)
+#define SNDRV_PCM_FORMAT_IEC958_SUBFRAME_LE (( snd_pcm_format_t) 18)
+#define SNDRV_PCM_FORMAT_IEC958_SUBFRAME_BE (( snd_pcm_format_t) 19)
+#define SNDRV_PCM_FORMAT_MU_LAW (( snd_pcm_format_t) 20)
+#define SNDRV_PCM_FORMAT_A_LAW (( snd_pcm_format_t) 21)
+#define SNDRV_PCM_FORMAT_IMA_ADPCM (( snd_pcm_format_t) 22)
+#define SNDRV_PCM_FORMAT_MPEG (( snd_pcm_format_t) 23)
+#define SNDRV_PCM_FORMAT_GSM (( snd_pcm_format_t) 24)
+#define SNDRV_PCM_FORMAT_S20_LE (( snd_pcm_format_t) 25)
+#define SNDRV_PCM_FORMAT_S20_BE (( snd_pcm_format_t) 26)
+#define SNDRV_PCM_FORMAT_U20_LE (( snd_pcm_format_t) 27)
+#define SNDRV_PCM_FORMAT_U20_BE (( snd_pcm_format_t) 28)
+#define SNDRV_PCM_FORMAT_SPECIAL (( snd_pcm_format_t) 31)
+#define SNDRV_PCM_FORMAT_S24_3LE (( snd_pcm_format_t) 32)
+#define SNDRV_PCM_FORMAT_S24_3BE (( snd_pcm_format_t) 33)
+#define SNDRV_PCM_FORMAT_U24_3LE (( snd_pcm_format_t) 34)
+#define SNDRV_PCM_FORMAT_U24_3BE (( snd_pcm_format_t) 35)
+#define SNDRV_PCM_FORMAT_S20_3LE (( snd_pcm_format_t) 36)
+#define SNDRV_PCM_FORMAT_S20_3BE (( snd_pcm_format_t) 37)
+#define SNDRV_PCM_FORMAT_U20_3LE (( snd_pcm_format_t) 38)
+#define SNDRV_PCM_FORMAT_U20_3BE (( snd_pcm_format_t) 39)
+#define SNDRV_PCM_FORMAT_S18_3LE (( snd_pcm_format_t) 40)
+#define SNDRV_PCM_FORMAT_S18_3BE (( snd_pcm_format_t) 41)
+#define SNDRV_PCM_FORMAT_U18_3LE (( snd_pcm_format_t) 42)
+#define SNDRV_PCM_FORMAT_U18_3BE (( snd_pcm_format_t) 43)
+#define SNDRV_PCM_FORMAT_G723_24 (( snd_pcm_format_t) 44)
+#define SNDRV_PCM_FORMAT_G723_24_1B (( snd_pcm_format_t) 45)
+#define SNDRV_PCM_FORMAT_G723_40 (( snd_pcm_format_t) 46)
+#define SNDRV_PCM_FORMAT_G723_40_1B (( snd_pcm_format_t) 47)
+#define SNDRV_PCM_FORMAT_DSD_U8 (( snd_pcm_format_t) 48)
+#define SNDRV_PCM_FORMAT_DSD_U16_LE (( snd_pcm_format_t) 49)
+#define SNDRV_PCM_FORMAT_DSD_U32_LE (( snd_pcm_format_t) 50)
+#define SNDRV_PCM_FORMAT_DSD_U16_BE (( snd_pcm_format_t) 51)
+#define SNDRV_PCM_FORMAT_DSD_U32_BE (( snd_pcm_format_t) 52)
 #define SNDRV_PCM_FORMAT_LAST SNDRV_PCM_FORMAT_DSD_U32_BE
 #define SNDRV_PCM_FORMAT_FIRST SNDRV_PCM_FORMAT_S8
 #ifdef SNDRV_LITTLE_ENDIAN
@@ -212,7 +212,7 @@
 #define SNDRV_PCM_FORMAT_U20 SNDRV_PCM_FORMAT_U20_BE
 #endif
 typedef int __bitwise snd_pcm_subformat_t;
-#define SNDRV_PCM_SUBFORMAT_STD ((__force snd_pcm_subformat_t) 0)
+#define SNDRV_PCM_SUBFORMAT_STD (( snd_pcm_subformat_t) 0)
 #define SNDRV_PCM_SUBFORMAT_LAST SNDRV_PCM_SUBFORMAT_STD
 #define SNDRV_PCM_INFO_MMAP 0x00000001
 #define SNDRV_PCM_INFO_MMAP_VALID 0x00000002
@@ -243,15 +243,15 @@
 #define __SND_STRUCT_TIME64
 #endif
 typedef int __bitwise snd_pcm_state_t;
-#define SNDRV_PCM_STATE_OPEN ((__force snd_pcm_state_t) 0)
-#define SNDRV_PCM_STATE_SETUP ((__force snd_pcm_state_t) 1)
-#define SNDRV_PCM_STATE_PREPARED ((__force snd_pcm_state_t) 2)
-#define SNDRV_PCM_STATE_RUNNING ((__force snd_pcm_state_t) 3)
-#define SNDRV_PCM_STATE_XRUN ((__force snd_pcm_state_t) 4)
-#define SNDRV_PCM_STATE_DRAINING ((__force snd_pcm_state_t) 5)
-#define SNDRV_PCM_STATE_PAUSED ((__force snd_pcm_state_t) 6)
-#define SNDRV_PCM_STATE_SUSPENDED ((__force snd_pcm_state_t) 7)
-#define SNDRV_PCM_STATE_DISCONNECTED ((__force snd_pcm_state_t) 8)
+#define SNDRV_PCM_STATE_OPEN (( snd_pcm_state_t) 0)
+#define SNDRV_PCM_STATE_SETUP (( snd_pcm_state_t) 1)
+#define SNDRV_PCM_STATE_PREPARED (( snd_pcm_state_t) 2)
+#define SNDRV_PCM_STATE_RUNNING (( snd_pcm_state_t) 3)
+#define SNDRV_PCM_STATE_XRUN (( snd_pcm_state_t) 4)
+#define SNDRV_PCM_STATE_DRAINING (( snd_pcm_state_t) 5)
+#define SNDRV_PCM_STATE_PAUSED (( snd_pcm_state_t) 6)
+#define SNDRV_PCM_STATE_SUSPENDED (( snd_pcm_state_t) 7)
+#define SNDRV_PCM_STATE_DISCONNECTED (( snd_pcm_state_t) 8)
 #define SNDRV_PCM_STATE_LAST SNDRV_PCM_STATE_DISCONNECTED
 enum {
   SNDRV_PCM_MMAP_OFFSET_DATA = 0x00000000,
@@ -475,12 +475,12 @@
 };
 struct snd_xferi {
   snd_pcm_sframes_t result;
-  void __user * buf;
+  void  * buf;
   snd_pcm_uframes_t frames;
 };
 struct snd_xfern {
   snd_pcm_sframes_t result;
-  void __user * __user * bufs;
+  void  *  * bufs;
   snd_pcm_uframes_t frames;
 };
 enum {
@@ -776,22 +776,22 @@
   unsigned char components[128];
 };
 typedef int __bitwise snd_ctl_elem_type_t;
-#define SNDRV_CTL_ELEM_TYPE_NONE ((__force snd_ctl_elem_type_t) 0)
-#define SNDRV_CTL_ELEM_TYPE_BOOLEAN ((__force snd_ctl_elem_type_t) 1)
-#define SNDRV_CTL_ELEM_TYPE_INTEGER ((__force snd_ctl_elem_type_t) 2)
-#define SNDRV_CTL_ELEM_TYPE_ENUMERATED ((__force snd_ctl_elem_type_t) 3)
-#define SNDRV_CTL_ELEM_TYPE_BYTES ((__force snd_ctl_elem_type_t) 4)
-#define SNDRV_CTL_ELEM_TYPE_IEC958 ((__force snd_ctl_elem_type_t) 5)
-#define SNDRV_CTL_ELEM_TYPE_INTEGER64 ((__force snd_ctl_elem_type_t) 6)
+#define SNDRV_CTL_ELEM_TYPE_NONE (( snd_ctl_elem_type_t) 0)
+#define SNDRV_CTL_ELEM_TYPE_BOOLEAN (( snd_ctl_elem_type_t) 1)
+#define SNDRV_CTL_ELEM_TYPE_INTEGER (( snd_ctl_elem_type_t) 2)
+#define SNDRV_CTL_ELEM_TYPE_ENUMERATED (( snd_ctl_elem_type_t) 3)
+#define SNDRV_CTL_ELEM_TYPE_BYTES (( snd_ctl_elem_type_t) 4)
+#define SNDRV_CTL_ELEM_TYPE_IEC958 (( snd_ctl_elem_type_t) 5)
+#define SNDRV_CTL_ELEM_TYPE_INTEGER64 (( snd_ctl_elem_type_t) 6)
 #define SNDRV_CTL_ELEM_TYPE_LAST SNDRV_CTL_ELEM_TYPE_INTEGER64
 typedef int __bitwise snd_ctl_elem_iface_t;
-#define SNDRV_CTL_ELEM_IFACE_CARD ((__force snd_ctl_elem_iface_t) 0)
-#define SNDRV_CTL_ELEM_IFACE_HWDEP ((__force snd_ctl_elem_iface_t) 1)
-#define SNDRV_CTL_ELEM_IFACE_MIXER ((__force snd_ctl_elem_iface_t) 2)
-#define SNDRV_CTL_ELEM_IFACE_PCM ((__force snd_ctl_elem_iface_t) 3)
-#define SNDRV_CTL_ELEM_IFACE_RAWMIDI ((__force snd_ctl_elem_iface_t) 4)
-#define SNDRV_CTL_ELEM_IFACE_TIMER ((__force snd_ctl_elem_iface_t) 5)
-#define SNDRV_CTL_ELEM_IFACE_SEQUENCER ((__force snd_ctl_elem_iface_t) 6)
+#define SNDRV_CTL_ELEM_IFACE_CARD (( snd_ctl_elem_iface_t) 0)
+#define SNDRV_CTL_ELEM_IFACE_HWDEP (( snd_ctl_elem_iface_t) 1)
+#define SNDRV_CTL_ELEM_IFACE_MIXER (( snd_ctl_elem_iface_t) 2)
+#define SNDRV_CTL_ELEM_IFACE_PCM (( snd_ctl_elem_iface_t) 3)
+#define SNDRV_CTL_ELEM_IFACE_RAWMIDI (( snd_ctl_elem_iface_t) 4)
+#define SNDRV_CTL_ELEM_IFACE_TIMER (( snd_ctl_elem_iface_t) 5)
+#define SNDRV_CTL_ELEM_IFACE_SEQUENCER (( snd_ctl_elem_iface_t) 6)
 #define SNDRV_CTL_ELEM_IFACE_LAST SNDRV_CTL_ELEM_IFACE_SEQUENCER
 #define SNDRV_CTL_ELEM_ACCESS_READ (1 << 0)
 #define SNDRV_CTL_ELEM_ACCESS_WRITE (1 << 1)
@@ -826,7 +826,7 @@
   unsigned int space;
   unsigned int used;
   unsigned int count;
-  struct snd_ctl_elem_id __user * pids;
+  struct snd_ctl_elem_id  * pids;
   unsigned char reserved[50];
 };
 struct snd_ctl_elem_info {
diff --git a/libc/kernel/uapi/sound/firewire.h b/libc/kernel/uapi/sound/firewire.h
index d26d722..cc13cb9 100644
--- a/libc/kernel/uapi/sound/firewire.h
+++ b/libc/kernel/uapi/sound/firewire.h
@@ -27,6 +27,7 @@
 #define SNDRV_FIREWIRE_EVENT_MOTU_NOTIFICATION 0x64776479
 #define SNDRV_FIREWIRE_EVENT_TASCAM_CONTROL 0x7473636d
 #define SNDRV_FIREWIRE_EVENT_MOTU_REGISTER_DSP_CHANGE 0x4d545244
+#define SNDRV_FIREWIRE_EVENT_FF400_MESSAGE 0x4f6c6761
 struct snd_firewire_event_common {
   unsigned int type;
 };
@@ -74,6 +75,14 @@
   __u32 count;
   __u32 changes[];
 };
+struct snd_firewire_event_ff400_message {
+  unsigned int type;
+  unsigned int message_count;
+  struct {
+    __u32 message;
+    __u32 tstamp;
+  } messages[];
+};
 union snd_firewire_event {
   struct snd_firewire_event_common common;
   struct snd_firewire_event_lock_status lock_status;
@@ -83,6 +92,7 @@
   struct snd_firewire_event_tascam_control tascam_control;
   struct snd_firewire_event_motu_notification motu_notification;
   struct snd_firewire_event_motu_register_dsp_change motu_register_dsp_change;
+  struct snd_firewire_event_ff400_message ff400_message;
 };
 #define SNDRV_FIREWIRE_IOCTL_GET_INFO _IOR('H', 0xf8, struct snd_firewire_get_info)
 #define SNDRV_FIREWIRE_IOCTL_LOCK _IO('H', 0xf9)
diff --git a/libc/kernel/uapi/sound/intel/avs/tokens.h b/libc/kernel/uapi/sound/intel/avs/tokens.h
index b6b3002..d524278 100644
--- a/libc/kernel/uapi/sound/intel/avs/tokens.h
+++ b/libc/kernel/uapi/sound/intel/avs/tokens.h
@@ -100,6 +100,7 @@
   AVS_TKN_MOD_CORE_ID_U8 = 1704,
   AVS_TKN_MOD_PROC_DOMAIN_U8 = 1705,
   AVS_TKN_MOD_MODCFG_EXT_ID_U32 = 1706,
+  AVS_TKN_MOD_KCONTROL_ID_U32 = 1707,
   AVS_TKN_PATH_TMPL_ID_U32 = 1801,
   AVS_TKN_PATH_ID_U32 = 1901,
   AVS_TKN_PATH_FE_FMT_ID_U32 = 1902,
@@ -107,5 +108,6 @@
   AVS_TKN_PIN_FMT_INDEX_U32 = 2201,
   AVS_TKN_PIN_FMT_IOBS_U32 = 2202,
   AVS_TKN_PIN_FMT_AFMT_ID_U32 = 2203,
+  AVS_TKN_KCONTROL_ID_U32 = 2301,
 };
 #endif
diff --git a/libc/kernel/uapi/xen/gntdev.h b/libc/kernel/uapi/xen/gntdev.h
index 1e78ac3..eada73c 100644
--- a/libc/kernel/uapi/xen/gntdev.h
+++ b/libc/kernel/uapi/xen/gntdev.h
@@ -55,7 +55,7 @@
 };
 struct gntdev_grant_copy_segment {
   union {
-    void __user * virt;
+    void  * virt;
     struct {
       grant_ref_t ref;
       __u16 offset;
@@ -69,7 +69,7 @@
 #define IOCTL_GNTDEV_GRANT_COPY _IOC(_IOC_NONE, 'G', 8, sizeof(struct ioctl_gntdev_grant_copy))
 struct ioctl_gntdev_grant_copy {
   unsigned int count;
-  struct gntdev_grant_copy_segment __user * segments;
+  struct gntdev_grant_copy_segment  * segments;
 };
 #define UNMAP_NOTIFY_CLEAR_BYTE 0x1
 #define UNMAP_NOTIFY_SEND_EVENT 0x2
diff --git a/libc/kernel/uapi/xen/privcmd.h b/libc/kernel/uapi/xen/privcmd.h
index 145446b..21d9f84 100644
--- a/libc/kernel/uapi/xen/privcmd.h
+++ b/libc/kernel/uapi/xen/privcmd.h
@@ -33,13 +33,13 @@
 struct privcmd_mmap {
   int num;
   domid_t dom;
-  struct privcmd_mmap_entry __user * entry;
+  struct privcmd_mmap_entry  * entry;
 };
 struct privcmd_mmapbatch {
   int num;
   domid_t dom;
   __u64 addr;
-  xen_pfn_t __user * arr;
+  xen_pfn_t  * arr;
 };
 #define PRIVCMD_MMAPBATCH_MFN_ERROR 0xf0000000U
 #define PRIVCMD_MMAPBATCH_PAGED_ERROR 0x80000000U
@@ -47,17 +47,17 @@
   unsigned int num;
   domid_t dom;
   __u64 addr;
-  const xen_pfn_t __user * arr;
-  int __user * err;
+  const xen_pfn_t  * arr;
+  int  * err;
 };
 struct privcmd_dm_op_buf {
-  void __user * uptr;
+  void  * uptr;
   size_t size;
 };
 struct privcmd_dm_op {
   domid_t dom;
   __u16 num;
-  const struct privcmd_dm_op_buf __user * ubufs;
+  const struct privcmd_dm_op_buf  * ubufs;
 };
 struct privcmd_mmap_resource {
   domid_t dom;
diff --git a/libc/libc.map.txt b/libc/libc.map.txt
index 4a4e607..0102b30 100644
--- a/libc/libc.map.txt
+++ b/libc/libc.map.txt
@@ -1580,8 +1580,15 @@
     close_range;
     copy_file_range;
     memset_explicit;
+    posix_spawn_file_actions_addchdir_np;
+    posix_spawn_file_actions_addfchdir_np;
 } LIBC_T;
 
+LIBC_V { # introduced=VanillaIceCream
+  global:
+    timespec_getres;
+} LIBC_U;
+
 LIBC_PRIVATE {
   global:
     __accept4; # arm x86
diff --git a/libc/malloc_debug/malloc_debug.cpp b/libc/malloc_debug/malloc_debug.cpp
index 7b0f599..b06ec9e 100644
--- a/libc/malloc_debug/malloc_debug.cpp
+++ b/libc/malloc_debug/malloc_debug.cpp
@@ -496,7 +496,7 @@
   g_dispatch->free(info);
   // Purge the memory that was freed since a significant amount of
   // memory could have been allocated and freed.
-  g_dispatch->mallopt(M_PURGE, 0);
+  g_dispatch->mallopt(M_PURGE_ALL, 0);
 }
 
 size_t debug_malloc_usable_size(void* pointer) {
@@ -1123,7 +1123,7 @@
 
   // Purge the memory that was allocated and freed during this operation
   // since it can be large enough to expand the RSS significantly.
-  g_dispatch->mallopt(M_PURGE, 0);
+  g_dispatch->mallopt(M_PURGE_ALL, 0);
 }
 
 bool debug_write_malloc_leak_info(FILE* fp) {
diff --git a/libc/bionic/timespec_get.cpp b/libc/private/bionic_asm_offsets.h
similarity index 86%
copy from libc/bionic/timespec_get.cpp
copy to libc/private/bionic_asm_offsets.h
index 7fc2182..c2f2b56 100644
--- a/libc/bionic/timespec_get.cpp
+++ b/libc/private/bionic_asm_offsets.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018 The Android Open Source Project
+ * Copyright (C) 2023 The Android Open Source Project
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -26,8 +26,8 @@
  * SUCH DAMAGE.
  */
 
-#include <time.h>
+#pragma once
 
-int timespec_get(timespec* ts, int base) {
-  return (base == TIME_UTC && clock_gettime(CLOCK_REALTIME, ts) != -1) ? base : 0;
-}
+#ifdef __aarch64__
+#define OFFSETOF_libc_globals_memtag_stack 80
+#endif
diff --git a/libc/private/bionic_constants.h b/libc/private/bionic_constants.h
index 09294b6..d7f4474 100644
--- a/libc/private/bionic_constants.h
+++ b/libc/private/bionic_constants.h
@@ -14,18 +14,18 @@
  * limitations under the License.
  */
 
-#ifndef _BIONIC_CONSTANTS_H_
-#define _BIONIC_CONSTANTS_H_
+#pragma once
 
 #define NS_PER_S 1000000000
 
-// Size of the shadow call stack. This must be a power of 2.
+// Size of the shadow call stack. This can be small because these stacks only
+// contain return addresses. This must be a power of 2 so the mask trick works.
+// See the SCS commentary in pthread_internal.h for more detail.
 #define SCS_SIZE (8 * 1024)
+#define SCS_MASK (SCS_SIZE - 1)
 
 // The shadow call stack is allocated at an aligned address within a guard region of this size. The
 // guard region must be large enough that we can allocate an SCS_SIZE-aligned SCS while ensuring
 // that there is at least one guard page after the SCS so that a stack overflow results in a SIGSEGV
 // instead of corrupting the allocation that comes after it.
 #define SCS_GUARD_REGION_SIZE (16 * 1024 * 1024)
-
-#endif // _BIONIC_CONSTANTS_H_
diff --git a/libc/private/bionic_globals.h b/libc/private/bionic_globals.h
index c375cc4..510d556 100644
--- a/libc/private/bionic_globals.h
+++ b/libc/private/bionic_globals.h
@@ -38,6 +38,7 @@
 
 #include "private/WriteProtected.h"
 #include "private/bionic_allocator.h"
+#include "private/bionic_asm_offsets.h"
 #include "private/bionic_elf_tls.h"
 #include "private/bionic_fdsan.h"
 #include "private/bionic_malloc_dispatch.h"
@@ -65,6 +66,10 @@
   MallocDispatch malloc_dispatch_table;
 };
 
+#ifdef __aarch64__
+static_assert(OFFSETOF_libc_globals_memtag_stack == offsetof(libc_globals, memtag_stack));
+#endif
+
 __LIBC_HIDDEN__ extern WriteProtected<libc_globals> __libc_globals;
 
 struct abort_msg_t;
diff --git a/libc/stdio/local.h b/libc/stdio/local.h
index 2fc12a0..a5eb636 100644
--- a/libc/stdio/local.h
+++ b/libc/stdio/local.h
@@ -290,17 +290,21 @@
 
 #define WCIO_GET(fp) (_EXT(fp) ? &(_EXT(fp)->_wcio) : (struct wchar_io_data*)0)
 
-#define _SET_ORIENTATION(fp, mode)                                 \
-  do {                                                             \
-    struct wchar_io_data* _wcio = WCIO_GET(fp);                    \
-    if (_wcio && _wcio->wcio_mode == 0) _wcio->wcio_mode = (mode); \
+#define ORIENT_BYTES (-1)
+#define ORIENT_UNKNOWN 0
+#define ORIENT_CHARS 1
+
+#define _SET_ORIENTATION(fp, mode)                                              \
+  do {                                                                          \
+    struct wchar_io_data* _wcio = WCIO_GET(fp);                                 \
+    if (_wcio && _wcio->wcio_mode == ORIENT_UNKNOWN) _wcio->wcio_mode = (mode); \
   } while (0)
 
 #define WCIO_FREE(fp)                           \
   do {                                          \
     struct wchar_io_data* _wcio = WCIO_GET(fp); \
     if (_wcio) {                                \
-      _wcio->wcio_mode = 0;                     \
+      _wcio->wcio_mode = ORIENT_UNKNOWN;        \
       _wcio->wcio_ungetwc_inbuf = 0;            \
     }                                           \
   } while (0)
diff --git a/libc/stdio/printf_common.h b/libc/stdio/printf_common.h
index e761835..365728b 100644
--- a/libc/stdio/printf_common.h
+++ b/libc/stdio/printf_common.h
@@ -528,6 +528,29 @@
       case 'b':
         ADDUARG();
         break;
+      case 'w': {
+        n = 0;
+        bool fast = false;
+        ch = *fmt++;
+        if (ch == 'f') {
+          fast = true;
+          ch = *fmt++;
+        }
+        while (is_digit(ch)) {
+          APPEND_DIGIT(n, ch);
+          ch = *fmt++;
+        }
+        if (n == 64) {
+          flags |= LLONGINT;
+        } else {
+          if (n != 8 && fast) {
+#if defined(__LP64__)
+            flags |= LLONGINT;
+#endif
+          }
+        }
+        goto reswitch;
+      }
       default: /* "%?" prints ?, unless ? is NUL */
         if (ch == '\0') goto done;
         break;
@@ -813,4 +836,15 @@
     return convbuf;
   }
 
+  // Trasnlate a fixed size integer argument for the %w/%wf format to a
+  // flag representation. Supported sizes are 8, 16, 32, and 64 so far.
+  // See details in bionic/libc/include/stdint.h
+  static int w_to_flag(int size, bool fast) {
+    static constexpr int fast_size = sizeof(void*) == 8 ? LLONGINT : 0;
+    if (size == 8) return CHARINT;
+    if (size == 16) return fast ? fast_size : SHORTINT;
+    if (size == 32) return fast ? fast_size : 0;
+    if (size == 64) return LLONGINT;
+    __fortify_fatal("%%w%s%d is unsupported", fast ? "f" : "", size);
+  }
 };
diff --git a/libc/stdio/stdio.cpp b/libc/stdio/stdio.cpp
index 645aefa..f18cd81 100644
--- a/libc/stdio/stdio.cpp
+++ b/libc/stdio/stdio.cpp
@@ -773,7 +773,7 @@
 char* fgets_unlocked(char* buf, int n, FILE* fp) {
   if (n <= 0) __fortify_fatal("fgets: buffer size %d <= 0", n);
 
-  _SET_ORIENTATION(fp, -1);
+  _SET_ORIENTATION(fp, ORIENT_BYTES);
 
   char* s = buf;
   n--; // Leave space for NUL.
@@ -903,7 +903,7 @@
     errno = EBADF;
     return EOF;
   }
-  _SET_ORIENTATION(fp, -1);
+  _SET_ORIENTATION(fp, ORIENT_BYTES);
   if (--fp->_w >= 0 || (fp->_w >= fp->_lbfsize && c != '\n')) {
     return (*fp->_p++ = c);
   }
@@ -1098,7 +1098,7 @@
   size_t total = desired_total;
   if (total == 0) return 0;
 
-  _SET_ORIENTATION(fp, -1);
+  _SET_ORIENTATION(fp, ORIENT_BYTES);
 
   // TODO: how can this ever happen?!
   if (fp->_r < 0) fp->_r = 0;
@@ -1165,7 +1165,7 @@
   __siov iov = { .iov_base = const_cast<void*>(buf), .iov_len = n };
   __suio uio = { .uio_iov = &iov, .uio_iovcnt = 1, .uio_resid = n };
 
-  _SET_ORIENTATION(fp, -1);
+  _SET_ORIENTATION(fp, ORIENT_BYTES);
 
   // The usual case is success (__sfvwrite returns 0); skip the divide if this happens,
   // since divides are generally slow.
diff --git a/libc/stdio/vfprintf.cpp b/libc/stdio/vfprintf.cpp
index d83a5bf..12cceeb 100644
--- a/libc/stdio/vfprintf.cpp
+++ b/libc/stdio/vfprintf.cpp
@@ -39,7 +39,27 @@
 #define CHAR_TYPE_inf "inf"
 #define CHAR_TYPE_NAN "NAN"
 #define CHAR_TYPE_nan "nan"
-#define CHAR_TYPE_ORIENTATION -1
+#define CHAR_TYPE_ORIENTATION ORIENT_BYTES
+
+#define PRINT(ptr, len)                          \
+  do {                                           \
+    iovp->iov_base = (ptr);                      \
+    iovp->iov_len = (len);                       \
+    uio.uio_resid += (len);                      \
+    iovp++;                                      \
+    if (++uio.uio_iovcnt >= NIOV) {              \
+      if (helpers::sprint(fp, &uio)) goto error; \
+      iovp = iov;                                \
+    }                                            \
+  } while (0)
+
+#define FLUSH()                                                 \
+  do {                                                          \
+    if (uio.uio_resid && helpers::sprint(fp, &uio)) goto error; \
+    uio.uio_iovcnt = 0;                                         \
+    iovp = iov;                                                 \
+  } while (0)
+
 #include "printf_common.h"
 
 int FUNCTION_NAME(FILE* fp, const CHAR_TYPE* fmt0, va_list ap) {
@@ -115,24 +135,6 @@
   static const char xdigs_lower[] = "0123456789abcdef";
   static const char xdigs_upper[] = "0123456789ABCDEF";
 
-#define PRINT(ptr, len)                   \
-  do {                                    \
-    iovp->iov_base = (ptr);               \
-    iovp->iov_len = (len);                \
-    uio.uio_resid += (len);               \
-    iovp++;                               \
-    if (++uio.uio_iovcnt >= NIOV) {       \
-      if (helpers::sprint(fp, &uio)) goto error; \
-      iovp = iov;                         \
-    }                                     \
-  } while (0)
-#define FLUSH()                                          \
-  do {                                                   \
-    if (uio.uio_resid && helpers::sprint(fp, &uio)) goto error; \
-    uio.uio_iovcnt = 0;                                  \
-    iovp = iov;                                          \
-  } while (0)
-
   _SET_ORIENTATION(fp, CHAR_TYPE_ORIENTATION);
 
   // Writing "" to a read only file returns EOF, not 0.
@@ -359,14 +361,14 @@
         if (dtoaresult) __freedtoa(dtoaresult);
         if (flags & LONGDBL) {
           fparg.ldbl = GETARG(long double);
-          dtoaresult = cp = __hldtoa(fparg.ldbl, xdigs, prec, &expt, &signflag, &dtoaend);
+          dtoaresult = __hldtoa(fparg.ldbl, xdigs, prec, &expt, &signflag, &dtoaend);
           if (dtoaresult == nullptr) {
             errno = ENOMEM;
             goto error;
           }
         } else {
           fparg.dbl = GETARG(double);
-          dtoaresult = cp = __hdtoa(fparg.dbl, xdigs, prec, &expt, &signflag, &dtoaend);
+          dtoaresult = __hdtoa(fparg.dbl, xdigs, prec, &expt, &signflag, &dtoaend);
           if (dtoaresult == nullptr) {
             errno = ENOMEM;
             goto error;
@@ -396,14 +398,14 @@
         if (dtoaresult) __freedtoa(dtoaresult);
         if (flags & LONGDBL) {
           fparg.ldbl = GETARG(long double);
-          dtoaresult = cp = __ldtoa(&fparg.ldbl, expchar ? 2 : 3, prec, &expt, &signflag, &dtoaend);
+          dtoaresult = __ldtoa(&fparg.ldbl, expchar ? 2 : 3, prec, &expt, &signflag, &dtoaend);
           if (dtoaresult == nullptr) {
             errno = ENOMEM;
             goto error;
           }
         } else {
           fparg.dbl = GETARG(double);
-          dtoaresult = cp = __dtoa(fparg.dbl, expchar ? 2 : 3, prec, &expt, &signflag, &dtoaend);
+          dtoaresult = __dtoa(fparg.dbl, expchar ? 2 : 3, prec, &expt, &signflag, &dtoaend);
           if (dtoaresult == nullptr) {
             errno = ENOMEM;
             goto error;
@@ -411,6 +413,13 @@
           if (expt == 9999) expt = INT_MAX;
         }
       fp_common:
+#if CHAR_TYPE_ORIENTATION == ORIENT_BYTES
+        cp = dtoaresult;
+#else
+        free(convbuf);
+        cp = convbuf = helpers::mbsconv(dtoaresult, -1);
+        if (cp == nullptr) goto error;
+#endif
         if (signflag) sign = '-';
         if (expt == INT_MAX) { /* inf or nan */
           if (*cp == 'N') {
@@ -423,7 +432,7 @@
           break;
         }
         flags |= FPT;
-        ndig = dtoaend - cp;
+        ndig = dtoaend - dtoaresult;
         if (ch == 'g' || ch == 'G') {
           if (expt > -4 && expt <= prec) {
             /* Make %[gG] smell like %[fF] */
@@ -521,6 +530,21 @@
         _umax = UARG();
         base = DEC;
         goto nosign;
+      case 'w': {
+        n = 0;
+        bool fast = false;
+        ch = *fmt++;
+        if (ch == 'f') {
+          fast = true;
+          ch = *fmt++;
+        }
+        while (is_digit(ch)) {
+          APPEND_DIGIT(n, ch);
+          ch = *fmt++;
+        }
+        flags |= helpers::w_to_flag(n, fast);
+        goto reswitch;
+      }
       case 'X':
         xdigs = xdigs_upper;
         goto hex;
@@ -645,6 +669,7 @@
     } else { /* glue together f_p fragments */
       if (decimal_point == nullptr) decimal_point = nl_langinfo(RADIXCHAR);
       if (!expchar) { /* %[fF] or sufficiently short %[gG] */
+        CHAR_TYPE* end = cp + ndig;
         if (expt <= 0) {
           PRINT(zeroes, 1);
           if (prec || flags & ALT) PRINT(decimal_point, 1);
@@ -652,11 +677,11 @@
           /* already handled initial 0's */
           prec += expt;
         } else {
-          PRINTANDPAD(cp, dtoaend, lead, zeroes);
+          PRINTANDPAD(cp, end, lead, zeroes);
           cp += lead;
           if (prec || flags & ALT) PRINT(decimal_point, 1);
         }
-        PRINTANDPAD(cp, dtoaend, prec, zeroes);
+        PRINTANDPAD(cp, end, prec, zeroes);
       } else { /* %[eE] or sufficiently long %[gG] */
         if (prec > 1 || flags & ALT) {
           buf[0] = *cp++;
diff --git a/libc/stdio/vfscanf.cpp b/libc/stdio/vfscanf.cpp
index d05a3a6..dfd001d 100644
--- a/libc/stdio/vfscanf.cpp
+++ b/libc/stdio/vfscanf.cpp
@@ -102,7 +102,7 @@
   void* allocation = nullptr; // Allocated but unassigned result for %mc/%ms/%m[.
   size_t capacity = 0; // Number of char/wchar_t units allocated in `allocation`.
 
-  _SET_ORIENTATION(fp, -1);
+  _SET_ORIENTATION(fp, ORIENT_BYTES);
 
   nassigned = 0;
   nread = 0;
diff --git a/libc/stdio/vfwprintf.cpp b/libc/stdio/vfwprintf.cpp
index 9819a73..d6f6a6b 100644
--- a/libc/stdio/vfwprintf.cpp
+++ b/libc/stdio/vfwprintf.cpp
@@ -39,7 +39,17 @@
 #define CHAR_TYPE_inf L"inf"
 #define CHAR_TYPE_NAN L"NAN"
 #define CHAR_TYPE_nan L"nan"
-#define CHAR_TYPE_ORIENTATION 1
+#define CHAR_TYPE_ORIENTATION ORIENT_CHARS
+
+#define PRINT(ptr, len)                                          \
+  do {                                                           \
+    for (int n3 = 0; n3 < (len); n3++) {                         \
+      if ((helpers::xfputwc((ptr)[n3], fp)) == WEOF) goto error; \
+    }                                                            \
+  } while (0)
+
+#define FLUSH()
+
 #include "printf_common.h"
 
 int FUNCTION_NAME(FILE* fp, const CHAR_TYPE* fmt0, va_list ap) {
@@ -115,13 +125,6 @@
   static const char xdigs_lower[] = "0123456789abcdef";
   static const char xdigs_upper[] = "0123456789ABCDEF";
 
-#define PRINT(ptr, len)                                   \
-  do {                                                    \
-    for (int n3 = 0; n3 < (len); n3++) {                      \
-      if ((helpers::xfputwc((ptr)[n3], fp)) == WEOF) goto error; \
-    }                                                     \
-  } while (0)
-
   _SET_ORIENTATION(fp, CHAR_TYPE_ORIENTATION);
 
   // Writing "" to a read only file returns EOF, not 0.
@@ -352,10 +355,6 @@
         }
         if (prec < 0) prec = dtoaend - dtoaresult;
         if (expt == INT_MAX) ox[1] = '\0';
-        free(convbuf);
-        cp = convbuf = helpers::mbsconv(dtoaresult, -1);
-        if (cp == nullptr) goto error;
-        ndig = dtoaend - dtoaresult;
         goto fp_common;
       case 'e':
       case 'E':
@@ -392,11 +391,14 @@
           }
           if (expt == 9999) expt = INT_MAX;
         }
+      fp_common:
+#if CHAR_TYPE_ORIENTATION == ORIENT_BYTES
+        cp = dtoaresult;
+#else
         free(convbuf);
         cp = convbuf = helpers::mbsconv(dtoaresult, -1);
         if (cp == nullptr) goto error;
-        ndig = dtoaend - dtoaresult;
-      fp_common:
+#endif
         if (signflag) sign = '-';
         if (expt == INT_MAX) { /* inf or nan */
           if (*cp == 'N') {
@@ -409,6 +411,7 @@
           break;
         }
         flags |= FPT;
+        ndig = dtoaend - dtoaresult;
         if (ch == 'g' || ch == 'G') {
           if (expt > -4 && expt <= prec) {
             /* Make %[gG] smell like %[fF] */
@@ -510,6 +513,21 @@
         _umax = UARG();
         base = DEC;
         goto nosign;
+      case 'w': {
+        n = 0;
+        bool fast = false;
+        ch = *fmt++;
+        if (ch == 'f') {
+          fast = true;
+          ch = *fmt++;
+        }
+        while (is_digit(ch)) {
+          APPEND_DIGIT(n, ch);
+          ch = *fmt++;
+        }
+        flags |= helpers::w_to_flag(n, fast);
+        goto reswitch;
+      }
       case 'X':
         xdigs = xdigs_upper;
         goto hex;
@@ -634,6 +652,7 @@
     } else { /* glue together f_p fragments */
       if (decimal_point == nullptr) decimal_point = nl_langinfo(RADIXCHAR);
       if (!expchar) { /* %[fF] or sufficiently short %[gG] */
+        CHAR_TYPE* end = cp + ndig;
         if (expt <= 0) {
           PRINT(zeroes, 1);
           if (prec || flags & ALT) PRINT(decimal_point, 1);
@@ -641,11 +660,11 @@
           /* already handled initial 0's */
           prec += expt;
         } else {
-          PRINTANDPAD(cp, convbuf + ndig, lead, zeroes);
+          PRINTANDPAD(cp, end, lead, zeroes);
           cp += lead;
           if (prec || flags & ALT) PRINT(decimal_point, 1);
         }
-        PRINTANDPAD(cp, convbuf + ndig, prec, zeroes);
+        PRINTANDPAD(cp, end, prec, zeroes);
       } else { /* %[eE] or sufficiently long %[gG] */
         if (prec > 1 || flags & ALT) {
           buf[0] = *cp++;
@@ -666,8 +685,11 @@
     if (width < realsz) width = realsz;
     if (width > INT_MAX - ret) goto overflow;
     ret += width;
+
+    FLUSH(); /* copy out the I/O vectors */
   }
 done:
+  FLUSH();
 error:
   va_end(orgap);
   if (__sferror(fp)) ret = -1;
diff --git a/libc/stdio/vfwscanf.cpp b/libc/stdio/vfwscanf.cpp
index 06f706a..5f21acd 100644
--- a/libc/stdio/vfwscanf.cpp
+++ b/libc/stdio/vfwscanf.cpp
@@ -150,7 +150,7 @@
   char mbbuf[MB_LEN_MAX]; /* temporary mb. character buffer */
   mbstate_t mbs;
 
-  _SET_ORIENTATION(fp, 1);
+  _SET_ORIENTATION(fp, ORIENT_CHARS);
 
   nassigned = 0;
   nconversions = 0;
diff --git a/libc/tools/gensyscalls.py b/libc/tools/gensyscalls.py
index 558b004..4f33777 100755
--- a/libc/tools/gensyscalls.py
+++ b/libc/tools/gensyscalls.py
@@ -88,7 +88,7 @@
     ecall
 
     li      a7, -MAX_ERRNO
-    bgtu    a0, a7, 1f
+    bgeu    a0, a7, 1f
 
     ret
 1:
diff --git a/libc/tzcode/asctime.c b/libc/tzcode/asctime.c
index ce5d4be..4cdfd13 100644
--- a/libc/tzcode/asctime.c
+++ b/libc/tzcode/asctime.c
@@ -17,12 +17,6 @@
 #include <stdio.h>
 
 /*
-** Some systems only handle "%.2d"; others only handle "%02d";
-** "%02.2d" makes (most) everybody happy.
-** At least some versions of gcc warn about the %02.2d;
-** we conditionalize below to avoid the warning.
-*/
-/*
 ** All years associated with 32-bit time_t values are exactly four digits long;
 ** some years associated with 64-bit time_t values are not.
 ** Vintage programs are coded for years that are always four digits long
@@ -34,24 +28,16 @@
 ** The ISO C and POSIX standards prohibit padding the year,
 ** but many implementations pad anyway; most likely the standards are buggy.
 */
-#ifdef __GNUC__
-#define ASCTIME_FMT	"%s %s%3d %2.2d:%2.2d:%2.2d %-4s\n"
-#else /* !defined __GNUC__ */
-#define ASCTIME_FMT	"%s %s%3d %02.2d:%02.2d:%02.2d %-4s\n"
-#endif /* !defined __GNUC__ */
+static char const ASCTIME_FMT[] = "%s %s%3d %.2d:%.2d:%.2d %-4s\n";
 /*
 ** For years that are more than four digits we put extra spaces before the year
 ** so that code trying to overwrite the newline won't end up overwriting
 ** a digit within a year and truncating the year (operating on the assumption
 ** that no output is better than wrong output).
 */
-#ifdef __GNUC__
-#define ASCTIME_FMT_B	"%s %s%3d %2.2d:%2.2d:%2.2d     %s\n"
-#else /* !defined __GNUC__ */
-#define ASCTIME_FMT_B	"%s %s%3d %02.2d:%02.2d:%02.2d     %s\n"
-#endif /* !defined __GNUC__ */
+static char const ASCTIME_FMT_B[] = "%s %s%3d %.2d:%.2d:%.2d     %s\n";
 
-#define STD_ASCTIME_BUF_SIZE	26
+enum { STD_ASCTIME_BUF_SIZE = 26 };
 /*
 ** Big enough for something such as
 ** ??? ???-2147483648 -2147483648:-2147483648:-2147483648     -2147483648\n
@@ -59,15 +45,23 @@
 ** seven explicit spaces, two explicit colons, a newline,
 ** and a trailing NUL byte).
 ** The values above are for systems where an int is 32 bits and are provided
-** as an example; the define below calculates the maximum for the system at
+** as an example; the size expression below is a bound for the system at
 ** hand.
 */
-#define MAX_ASCTIME_BUF_SIZE	(2*3+5*INT_STRLEN_MAXIMUM(int)+7+2+1+1)
+static char buf_asctime[2*3 + 5*INT_STRLEN_MAXIMUM(int) + 7 + 2 + 1 + 1];
 
-static char	buf_asctime[MAX_ASCTIME_BUF_SIZE];
+/* A similar buffer for ctime.
+   C89 requires that they be the same buffer.
+   This requirement was removed in C99, so support it only if requested,
+   as support is more likely to lead to bugs in badly written programs.  */
+#if SUPPORT_C89
+# define buf_ctime buf_asctime
+#else
+static char buf_ctime[sizeof buf_asctime];
+#endif
 
 char *
-asctime_r(register const struct tm *timeptr, char *buf)
+asctime_r(struct tm const *restrict timeptr, char *restrict buf)
 {
 	static const char	wday_name[][4] = {
 		"Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"
@@ -79,7 +73,7 @@
 	register const char *	wn;
 	register const char *	mn;
 	char			year[INT_STRLEN_MAXIMUM(int) + 2];
-	char			result[MAX_ASCTIME_BUF_SIZE];
+	char result[sizeof buf_asctime];
 
 	if (timeptr == NULL) {
 		errno = EINVAL;
@@ -107,7 +101,8 @@
 		timeptr->tm_mday, timeptr->tm_hour,
 		timeptr->tm_min, timeptr->tm_sec,
 		year);
-	if (strlen(result) < STD_ASCTIME_BUF_SIZE || buf == buf_asctime)
+	if (strlen(result) < STD_ASCTIME_BUF_SIZE
+	    || buf == buf_ctime || buf == buf_asctime)
 		return strcpy(buf, result);
 	else {
 		errno = EOVERFLOW;
@@ -120,3 +115,17 @@
 {
 	return asctime_r(timeptr, buf_asctime);
 }
+
+char *
+ctime_r(const time_t *timep, char *buf)
+{
+  struct tm mytm;
+  struct tm *tmp = localtime_r(timep, &mytm);
+  return tmp ? asctime_r(tmp, buf) : NULL;
+}
+
+char *
+ctime(const time_t *timep)
+{
+  return ctime_r(timep, buf_ctime);
+}
diff --git a/libc/tzcode/localtime.c b/libc/tzcode/localtime.c
index 8ff5cee..5e1181f 100644
--- a/libc/tzcode/localtime.c
+++ b/libc/tzcode/localtime.c
@@ -28,29 +28,22 @@
 static void unlock(void) { }
 #endif
 
-#ifndef TZ_ABBR_MAX_LEN
-#define TZ_ABBR_MAX_LEN 16
-#endif /* !defined TZ_ABBR_MAX_LEN */
-
 #ifndef TZ_ABBR_CHAR_SET
-#define TZ_ABBR_CHAR_SET \
+# define TZ_ABBR_CHAR_SET \
     "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789 :+-._"
 #endif /* !defined TZ_ABBR_CHAR_SET */
 
 #ifndef TZ_ABBR_ERR_CHAR
-#define TZ_ABBR_ERR_CHAR    '_'
+# define TZ_ABBR_ERR_CHAR    '_'
 #endif /* !defined TZ_ABBR_ERR_CHAR */
 
 /*
-** SunOS 4.1.1 headers lack O_BINARY.
++** Support non-POSIX platforms that distinguish between text and binary files.
 */
 
-#ifdef O_BINARY
-#define OPEN_MODE   (O_RDONLY | O_BINARY)
-#endif /* defined O_BINARY */
 #ifndef O_BINARY
-#define OPEN_MODE   O_RDONLY
-#endif /* !defined O_BINARY */
+# define O_BINARY 0
+#endif
 
 #ifndef WILDABBR
 /*
@@ -72,12 +65,13 @@
 ** manual page of what this "time zone abbreviation" means (doing this so
 ** that tzname[0] has the "normal" length of three characters).
 */
-#define WILDABBR    "   "
+# define WILDABBR    "   "
 #endif /* !defined WILDABBR */
 
 static const char       wildabbr[] = WILDABBR;
 
-static const char gmt[] = "GMT";
+static char const etc_utc[] = "Etc/UTC";
+static char const *utc = etc_utc + sizeof "Etc/" - 1;
 
 /*
 ** The DST rules to use if TZ has no rules and we can't load TZDEFRULES.
@@ -86,7 +80,7 @@
 ** for historical reasons, US rules are a common default.
 */
 #ifndef TZDEFRULESTRING
-#define TZDEFRULESTRING ",M3.2.0,M11.1.0"
+# define TZDEFRULESTRING ",M3.2.0,M11.1.0"
 #endif
 
 struct ttinfo {              /* time type information */
@@ -102,9 +96,6 @@
     int_fast32_t ls_corr;    /* correction to apply */
 };
 
-#define SMALLEST(a, b)	(((a) < (b)) ? (a) : (b))
-#define BIGGEST(a, b)   (((a) > (b)) ? (a) : (b))
-
 /* This abbreviation means local time is unspecified.  */
 static char const UNSPEC[] = "-00";
 
@@ -112,14 +103,13 @@
    This needs to be at least 1 for null termination in case the input
    data isn't properly terminated, and it also needs to be big enough
    for ttunspecified to work without crashing.  */
-enum { CHARS_EXTRA = BIGGEST(sizeof UNSPEC, 2) - 1 };
+enum { CHARS_EXTRA = max(sizeof UNSPEC, 2) - 1 };
 
-#ifdef TZNAME_MAX
-#define MY_TZNAME_MAX   TZNAME_MAX
-#endif /* defined TZNAME_MAX */
-#ifndef TZNAME_MAX
-#define MY_TZNAME_MAX   255
-#endif /* !defined TZNAME_MAX */
+/* Limit to time zone abbreviation length in POSIX-style TZ strings.
+   This is distinct from TZ_MAX_CHARS, which limits TZif file contents.  */
+#ifndef TZNAME_MAXIMUM
+# define TZNAME_MAXIMUM 255
+#endif
 
 struct state {
     int           leapcnt;
@@ -131,9 +121,8 @@
     time_t        ats[TZ_MAX_TIMES];
     unsigned char types[TZ_MAX_TIMES];
     struct ttinfo ttis[TZ_MAX_TYPES];
-    char          chars[BIGGEST(BIGGEST(TZ_MAX_CHARS + CHARS_EXTRA,
-                            sizeof gmt),
-                  (2 * (MY_TZNAME_MAX + 1)))];
+    char chars[max(max(TZ_MAX_CHARS + CHARS_EXTRA, sizeof "UTC"),
+		         2 * (TZNAME_MAXIMUM + 1))];
     struct lsinfo lsis[TZ_MAX_LEAPS];
     /* The time type to use for early times or if no transitions.
        It is always zero for recent tzdb releases.
@@ -174,12 +163,12 @@
 #ifndef ALL_STATE
 static struct state lclmem;
 static struct state gmtmem;
-#define lclptr      (&lclmem)
-#define gmtptr      (&gmtmem)
+static struct state *const lclptr = &lclmem;
+static struct state *const gmtptr = &gmtmem;
 #endif /* State Farm */
 
 #ifndef TZ_STRLEN_MAX
-#define TZ_STRLEN_MAX 255
+# define TZ_STRLEN_MAX 255
 #endif /* !defined TZ_STRLEN_MAX */
 
 static char lcl_TZname[TZ_STRLEN_MAX + 1];
@@ -191,9 +180,14 @@
 **  ctime, gmtime, localtime] return values in one of two static
 **  objects: a broken-down time structure and an array of char.
 ** Thanks to Paul Eggert for noting this.
+**
+** This requirement was removed in C99, so support it only if requested,
+** as support is more likely to lead to bugs in badly written programs.
 */
 
+#if SUPPORT_C89
 static struct tm	tm;
+#endif
 
 #if 2 <= HAVE_TZNAME + TZ_TIME_T
 char *			tzname[2] = {
@@ -321,7 +315,7 @@
 	int stddst_mask = 0;
 
 #if HAVE_TZNAME
-	tzname[0] = tzname[1] = (char *) (sp ? wildabbr : gmt);
+	tzname[0] = tzname[1] = (char *) (sp ? wildabbr : utc);
 	stddst_mask = 3;
 #endif
 #if USG_COMPAT
@@ -346,27 +340,28 @@
 #endif
 }
 
-static void
+/* Replace bogus characters in time zone abbreviations.
+   Return 0 on success, an errno value if a time zone abbreviation is
+   too long.  */
+static int
 scrub_abbrs(struct state *sp)
 {
 	int i;
-	/*
-	** First, replace bogus characters.
-	*/
+
+	/* Reject overlong abbreviations.  */
+	for (i = 0; i < sp->charcnt - (TZNAME_MAXIMUM + 1); ) {
+	  int len = strlen(&sp->chars[i]);
+	  if (TZNAME_MAXIMUM < len)
+	    return EOVERFLOW;
+	  i += len + 1;
+	}
+
+	/* Replace bogus characters.  */
 	for (i = 0; i < sp->charcnt; ++i)
 		if (strchr(TZ_ABBR_CHAR_SET, sp->chars[i]) == NULL)
 			sp->chars[i] = TZ_ABBR_ERR_CHAR;
-	/*
-	** Second, truncate long abbreviations.
-	*/
-	for (i = 0; i < sp->typecnt; ++i) {
-		register const struct ttinfo * const	ttisp = &sp->ttis[i];
-		char *cp = &sp->chars[ttisp->tt_desigidx];
 
-		if (strlen(cp) > TZ_ABBR_MAX_LEN &&
-			strcmp(cp, GRANDPARENTED) != 0)
-				*(cp + TZ_ABBR_MAX_LEN) = '\0';
-	}
+	return 0;
 }
 
 /* Input buffer for data read from a compiled tz file.  */
@@ -399,8 +394,7 @@
   // Android-removed: There is no directory with file-per-time zone on Android.
   #ifndef __BIONIC__
   /* The file name to be opened.  */
-  char fullname[BIGGEST(sizeof(struct file_analysis),
-      sizeof tzdirslash + 1024)];
+  char fullname[max(sizeof(struct file_analysis), sizeof tzdirslash + 1024)];
   #endif
 };
 
@@ -446,8 +440,7 @@
 #endif
 	if (!doaccess) {
 		char const *dot;
-		size_t namelen = strlen(name);
-		if (sizeof lsp->fullname - sizeof tzdirslash <= namelen)
+		if (sizeof lsp->fullname - sizeof tzdirslash <= strlen(name))
 		  return ENAMETOOLONG;
 
 		/* Create a string "TZDIR/NAME".  Using sprintf here
@@ -470,7 +463,7 @@
 	}
 	if (doaccess && access(name, R_OK) != 0)
 	  return errno;
-	fid = open(name, OPEN_MODE);
+  fid = open(name, O_RDONLY | O_BINARY);
 #endif
 	if (fid < 0)
 	  return errno;
@@ -828,12 +821,14 @@
 		b < 0 || b >= sp->typecnt)
 			result = false;
 	else {
+		/* Compare the relevant members of *AP and *BP.
+		   Ignore tt_ttisstd and tt_ttisut, as they are
+		   irrelevant now and counting them could cause
+		   sp->goahead to mistakenly remain false.  */
 		register const struct ttinfo *	ap = &sp->ttis[a];
 		register const struct ttinfo *	bp = &sp->ttis[b];
 		result = (ap->tt_utoff == bp->tt_utoff
 			  && ap->tt_isdst == bp->tt_isdst
-			  && ap->tt_ttisstd == bp->tt_ttisstd
-			  && ap->tt_ttisut == bp->tt_ttisut
 			  && (strcmp(&sp->chars[ap->tt_desigidx],
 				     &sp->chars[bp->tt_desigidx])
 			      == 0));
@@ -863,7 +858,7 @@
 ** Return a pointer to that character.
 */
 
-static ATTRIBUTE_PURE const char *
+ATTRIBUTE_REPRODUCIBLE static const char *
 getzname(register const char *strp)
 {
 	register char	c;
@@ -884,7 +879,7 @@
 ** We don't do any checking here; checking is done later in common-case code.
 */
 
-static ATTRIBUTE_PURE const char *
+ATTRIBUTE_REPRODUCIBLE static const char *
 getqzname(register const char *strp, const int delim)
 {
 	register int	c;
@@ -1122,7 +1117,7 @@
             value += mon_lengths[leapyear][i] * SECSPERDAY;
         break;
 
-        default: UNREACHABLE();
+        default: unreachable();
     }
 
     /*
@@ -1144,13 +1139,11 @@
 {
 	const char *			stdname;
 	const char *			dstname;
-	size_t				stdlen;
-	size_t				dstlen;
-	size_t				charcnt;
 	int_fast32_t			stdoffset;
 	int_fast32_t			dstoffset;
 	register char *			cp;
 	register bool			load_ok;
+	ptrdiff_t stdlen, dstlen, charcnt;
 	time_t atlo = TIME_T_MIN, leaplo = TIME_T_MIN;
 
 	stdname = name;
@@ -1166,14 +1159,12 @@
 	  name = getzname(name);
 	  stdlen = name - stdname;
 	}
-	if (!stdlen)
+	if (! (0 < stdlen && stdlen <= TZNAME_MAXIMUM))
 	  return false;
 	name = getoffset(name, &stdoffset);
 	if (name == NULL)
 	  return false;
 	charcnt = stdlen + 1;
-	if (sizeof sp->chars < charcnt)
-	  return false;
 	if (basep) {
 	  if (0 < basep->timecnt)
 	    atlo = basep->ats[basep->timecnt - 1];
@@ -1200,11 +1191,9 @@
 			name = getzname(name);
 			dstlen = name - dstname; /* length of DST abbr. */
 		}
-		if (!dstlen)
+		if (! (0 < dstlen && dstlen <= TZNAME_MAXIMUM))
 		  return false;
 		charcnt += dstlen + 1;
-		if (sizeof sp->chars < charcnt)
-		  return false;
 		if (*name != '\0' && *name != ',' && *name != ';') {
 			name = getoffset(name, &dstoffset);
 			if (name == NULL)
@@ -1420,8 +1409,8 @@
 static void
 gmtload(struct state *const sp)
 {
-	if (tzload(gmt, sp, true) != 0)
-	  tzparse("GMT0", sp, NULL);
+	if (tzload(etc_utc, sp, true) != 0)
+	  tzparse("UTC0", sp, NULL);
 }
 
 /* Initialize *SP to a value appropriate for the TZ setting NAME.
@@ -1439,7 +1428,7 @@
     sp->charcnt = 0;
     sp->goback = sp->goahead = false;
     init_ttinfo(&sp->ttis[0], 0, false, 0);
-    strcpy(sp->chars, gmt);
+    strcpy(sp->chars, utc);
     sp->defaulttype = 0;
     return 0;
   } else {
@@ -1447,7 +1436,7 @@
     if (err != 0 && name && name[0] != ':' && tzparse(name, sp, NULL))
       err = 0;
     if (err == 0)
-      scrub_abbrs(sp);
+      err = scrub_abbrs(sp);
     return err;
   }
 }
@@ -1557,7 +1546,7 @@
 ** set the applicable parts of tzname, timezone and altzone;
 ** however, it's OK to omit this step if the timezone is POSIX-compatible,
 ** since in that case tzset should have already done this step correctly.
-** SETNAME's type is intfast32_t for compatibility with gmtsub,
+** SETNAME's type is int_fast32_t for compatibility with gmtsub,
 ** but it is actually a boolean and its value should be 0 or 1.
 */
 
@@ -1601,6 +1590,14 @@
 					return NULL;	/* "cannot happen" */
 			result = localsub(sp, &newt, setname, tmp);
 			if (result) {
+#if defined ckd_add && defined ckd_sub
+				if (t < sp->ats[0]
+				    ? ckd_sub(&result->tm_year,
+					      result->tm_year, years)
+				    : ckd_add(&result->tm_year,
+					      result->tm_year, years))
+				  return NULL;
+#else
 				register int_fast64_t newy;
 
 				newy = result->tm_year;
@@ -1610,6 +1607,7 @@
 				if (! (INT_MIN <= newy && newy <= INT_MAX))
 					return NULL;
 				result->tm_year = newy;
+#endif
 			}
 			return result;
 	}
@@ -1650,7 +1648,8 @@
 #if NETBSD_INSPIRED
 
 struct tm *
-localtime_rz(struct state *sp, time_t const *timep, struct tm *tmp)
+localtime_rz(struct state *restrict sp, time_t const *restrict timep,
+	     struct tm *restrict tmp)
 {
   return localsub(sp, timep, 0, tmp);
 }
@@ -1681,11 +1680,14 @@
 struct tm *
 localtime(const time_t *timep)
 {
+#if !SUPPORT_C89
+  static struct tm tm;
+#endif
   return localtime_tzset(timep, &tm);
 }
 
 struct tm *
-localtime_r(const time_t *timep, struct tm *tmp)
+localtime_r(const time_t *restrict timep, struct tm *restrict tmp)
 {
   return localtime_tzset(timep, tmp);
 }
@@ -1695,8 +1697,8 @@
 */
 
 static struct tm *
-gmtsub(struct state const *sp, time_t const *timep, int_fast32_t offset,
-       struct tm *tmp)
+gmtsub(ATTRIBUTE_MAYBE_UNUSED struct state const *sp, time_t const *timep,
+       int_fast32_t offset, struct tm *tmp)
 {
 	register struct tm *	result;
 
@@ -1708,7 +1710,7 @@
 	** but this is no time for a treasure hunt.
 	*/
 	tmp->TM_ZONE = ((char *)
-			(offset ? wildabbr : gmtptr ? gmtptr->chars : gmt));
+			(offset ? wildabbr : gmtptr ? gmtptr->chars : utc));
 #endif /* defined TM_ZONE */
 	return result;
 }
@@ -1718,7 +1720,7 @@
 */
 
 struct tm *
-gmtime_r(const time_t *timep, struct tm *tmp)
+gmtime_r(time_t const *restrict timep, struct tm *restrict tmp)
 {
   gmtcheck();
   return gmtsub(gmtptr, timep, 0, tmp);
@@ -1727,19 +1729,26 @@
 struct tm *
 gmtime(const time_t *timep)
 {
+#if !SUPPORT_C89
+  static struct tm tm;
+#endif
   return gmtime_r(timep, &tm);
 }
 
-#ifdef STD_INSPIRED
+#if STD_INSPIRED
 
 struct tm *
 offtime(const time_t *timep, long offset)
 {
   gmtcheck();
+
+#if !SUPPORT_C89
+  static struct tm tm;
+#endif
   return gmtsub(gmtptr, timep, offset, &tm);
 }
 
-#endif /* defined STD_INSPIRED */
+#endif
 
 /*
 ** Return the number of leap years through the end of the given year
@@ -1825,6 +1834,12 @@
 		y = newy;
 	}
 
+#ifdef ckd_add
+	if (ckd_add(&tmp->tm_year, y, -TM_YEAR_BASE)) {
+	  errno = EOVERFLOW;
+	  return NULL;
+	}
+#else
 	if (!TYPE_SIGNED(time_t) && y < TM_YEAR_BASE) {
 	  int signed_y = y;
 	  tmp->tm_year = signed_y - TM_YEAR_BASE;
@@ -1835,6 +1850,7 @@
 	  errno = EOVERFLOW;
 	  return NULL;
 	}
+#endif
 	tmp->tm_yday = idays;
 	/*
 	** The "extra" mods below avoid overflow problems.
@@ -1868,27 +1884,6 @@
 	return tmp;
 }
 
-char *
-ctime(const time_t *timep)
-{
-/*
-** Section 4.12.3.2 of X3.159-1989 requires that
-**	The ctime function converts the calendar time pointed to by timer
-**	to local time in the form of a string. It is equivalent to
-**		asctime(localtime(timer))
-*/
-  struct tm *tmp = localtime(timep);
-  return tmp ? asctime(tmp) : NULL;
-}
-
-char *
-ctime_r(const time_t *timep, char *buf)
-{
-  struct tm mytm;
-  struct tm *tmp = localtime_r(timep, &mytm);
-  return tmp ? asctime_r(tmp, buf) : NULL;
-}
-
 /*
 ** Adapted from code provided by Robert Elz, who writes:
 **	The "best" way to do mktime I think is based on an idea of Bob
@@ -1899,7 +1894,7 @@
 */
 
 #ifndef WRONG
-#define WRONG	(-1)
+# define WRONG (-1)
 #endif /* !defined WRONG */
 
 /*
@@ -1909,6 +1904,9 @@
 static bool
 increment_overflow(int *ip, int j)
 {
+#ifdef ckd_add
+	return ckd_add(ip, *ip, j);
+#else
 	register int const	i = *ip;
 
 	/*
@@ -1921,22 +1919,30 @@
 		return true;
 	*ip += j;
 	return false;
+#endif
 }
 
 static bool
 increment_overflow32(int_fast32_t *const lp, int const m)
 {
+#ifdef ckd_add
+	return ckd_add(lp, *lp, m);
+#else
 	register int_fast32_t const	l = *lp;
 
 	if ((l >= 0) ? (m > INT_FAST32_MAX - l) : (m < INT_FAST32_MIN - l))
 		return true;
 	*lp += m;
 	return false;
+#endif
 }
 
 static bool
 increment_overflow_time(time_t *tp, int_fast32_t j)
 {
+#ifdef ckd_add
+	return ckd_add(tp, *tp, j);
+#else
 	/*
 	** This is like
 	** 'if (! (TIME_T_MIN <= *tp + j && *tp + j <= TIME_T_MAX)) ...',
@@ -1948,6 +1954,7 @@
 		return true;
 	*tp += j;
 	return false;
+#endif
 }
 
 static bool
@@ -1990,6 +1997,23 @@
 	return result;
 }
 
+/* Copy to *DEST from *SRC.  Copy only the members needed for mktime,
+   as other members might not be initialized.  */
+static void
+mktmcpy(struct tm *dest, struct tm const *src)
+{
+  dest->tm_sec = src->tm_sec;
+  dest->tm_min = src->tm_min;
+  dest->tm_hour = src->tm_hour;
+  dest->tm_mday = src->tm_mday;
+  dest->tm_mon = src->tm_mon;
+  dest->tm_year = src->tm_year;
+  dest->tm_isdst = src->tm_isdst;
+#if defined TM_GMTOFF && ! UNINIT_TRAP
+  dest->TM_GMTOFF = src->TM_GMTOFF;
+#endif
+}
+
 static time_t
 time2sub(struct tm *const tmp,
 	 struct tm *(*funcp)(struct state const *, time_t const *,
@@ -2011,7 +2035,8 @@
 	struct tm			yourtm, mytm;
 
 	*okayp = false;
-	yourtm = *tmp;
+	mktmcpy(&yourtm, tmp);
+
 	if (do_norm_secs) {
 		if (normalize_overflow(&yourtm.tm_min, &yourtm.tm_sec,
 			SECSPERMIN))
@@ -2053,14 +2078,19 @@
 				return WRONG;
 		}
 	}
+#ifdef ckd_add
+	if (ckd_add(&yourtm.tm_year, y, -TM_YEAR_BASE))
+	  return WRONG;
+#else
 	if (increment_overflow32(&y, -TM_YEAR_BASE))
 		return WRONG;
 	if (! (INT_MIN <= y && y <= INT_MAX))
 		return WRONG;
 	yourtm.tm_year = y;
+#endif
 	if (yourtm.tm_sec >= 0 && yourtm.tm_sec < SECSPERMIN)
 		saved_seconds = 0;
-	else if (y + TM_YEAR_BASE < EPOCH_YEAR) {
+	else if (yourtm.tm_year < EPOCH_YEAR - TM_YEAR_BASE) {
 		/*
 		** We can't set tm_sec to 0, because that might push the
 		** time below the minimum representable time.
@@ -2120,10 +2150,10 @@
 		    && (yourtm.TM_GMTOFF < 0
 			? (-SECSPERDAY <= yourtm.TM_GMTOFF
 			   && (mytm.TM_GMTOFF <=
-			       (SMALLEST(INT_FAST32_MAX, LONG_MAX)
+			       (min(INT_FAST32_MAX, LONG_MAX)
 				+ yourtm.TM_GMTOFF)))
 			: (yourtm.TM_GMTOFF <= SECSPERDAY
-			   && ((BIGGEST(INT_FAST32_MIN, LONG_MIN)
+			   && ((max(INT_FAST32_MIN, LONG_MIN)
 				+ yourtm.TM_GMTOFF)
 			       <= mytm.TM_GMTOFF)))) {
 		  /* MYTM matches YOURTM except with the wrong UT offset.
@@ -2294,7 +2324,7 @@
 #if NETBSD_INSPIRED
 
 time_t
-mktime_z(struct state *sp, struct tm *tmp)
+mktime_z(struct state *restrict sp, struct tm *restrict tmp)
 {
   return mktime_tzname(sp, tmp, false);
 }
@@ -2324,8 +2354,7 @@
   return t;
 }
 
-#ifdef STD_INSPIRED
-
+#if STD_INSPIRED
 time_t
 timelocal(struct tm *tmp)
 {
@@ -2333,13 +2362,9 @@
 		tmp->tm_isdst = -1;	/* in case it wasn't initialized */
 	return mktime(tmp);
 }
-
-time_t
-timegm(struct tm *tmp)
-{
-  return timeoff(tmp, 0);
-}
-
+#else
+static
+#endif
 time_t
 timeoff(struct tm *tmp, long offset)
 {
@@ -2349,7 +2374,18 @@
   return time1(tmp, gmtsub, gmtptr, offset);
 }
 
-#endif /* defined STD_INSPIRED */
+time_t
+timegm(struct tm *tmp)
+{
+  time_t t;
+  struct tm tmcpy;
+  mktmcpy(&tmcpy, tmp);
+  tmcpy.tm_wday = -1;
+  t = timeoff(&tmcpy, 0);
+  if (0 <= tmcpy.tm_wday)
+    *tmp = tmcpy;
+  return t;
+}
 
 static int_fast32_t
 leapcorr(struct state const *sp, time_t t)
@@ -2370,7 +2406,7 @@
 ** XXX--is the below the right way to conditionalize??
 */
 
-#ifdef STD_INSPIRED
+#if STD_INSPIRED
 
 /* NETBSD_INSPIRED_EXTERN functions are exported to callers if
    NETBSD_INSPIRED is defined, and are private otherwise.  */
@@ -2455,7 +2491,7 @@
   return t;
 }
 
-#endif /* defined STD_INSPIRED */
+#endif /* STD_INSPIRED */
 
 #if TZ_TIME_T
 
diff --git a/libc/tzcode/private.h b/libc/tzcode/private.h
index 4c03324..838ab2b 100644
--- a/libc/tzcode/private.h
+++ b/libc/tzcode/private.h
@@ -17,6 +17,36 @@
 ** Thank you!
 */
 
+/* PORT_TO_C89 means the code should work even if the underlying
+   compiler and library support only C89.  SUPPORT_C89 means the
+   tzcode library should support C89 callers in addition to the usual
+   support for C99-and-later callers.  These macros are obsolescent,
+   and the plan is to remove them along with any code needed only when
+   they are nonzero.  */
+#ifndef PORT_TO_C89
+# define PORT_TO_C89 0
+#endif
+#ifndef SUPPORT_C89
+# define SUPPORT_C89 0
+#endif
+
+#ifndef __STDC_VERSION__
+# define __STDC_VERSION__ 0
+#endif
+
+/* Define true, false and bool if they don't work out of the box.  */
+#if PORT_TO_C89 && __STDC_VERSION__ < 199901
+# define true 1
+# define false 0
+# define bool int
+#elif __STDC_VERSION__ < 202311
+# include <stdbool.h>
+#endif
+
+#if __STDC_VERSION__ < 202311
+# define static_assert(cond) extern int static_assert_check[(cond) ? 1 : -1]
+#endif
+
 /*
 ** zdump has been made independent of the rest of the time
 ** conversion package to increase confidence in the verification it provides.
@@ -36,79 +66,86 @@
 */
 
 #ifndef HAVE_DECL_ASCTIME_R
-#define HAVE_DECL_ASCTIME_R 1
+# define HAVE_DECL_ASCTIME_R 1
 #endif
 
-#if !defined HAVE_GENERIC && defined __has_extension
+#if !defined HAVE__GENERIC && defined __has_extension
 # if __has_extension(c_generic_selections)
-#  define HAVE_GENERIC 1
+#  define HAVE__GENERIC 1
 # else
-#  define HAVE_GENERIC 0
+#  define HAVE__GENERIC 0
 # endif
 #endif
 /* _Generic is buggy in pre-4.9 GCC.  */
-#if !defined HAVE_GENERIC && defined __GNUC__
-# define HAVE_GENERIC (4 < __GNUC__ + (9 <= __GNUC_MINOR__))
+#if !defined HAVE__GENERIC && defined __GNUC__ && !defined __STRICT_ANSI__
+# define HAVE__GENERIC (4 < __GNUC__ + (9 <= __GNUC_MINOR__))
 #endif
-#ifndef HAVE_GENERIC
-# define HAVE_GENERIC (201112 <= __STDC_VERSION__)
+#ifndef HAVE__GENERIC
+# define HAVE__GENERIC (201112 <= __STDC_VERSION__)
 #endif
 
+#if !defined HAVE_GETTEXT && defined __has_include
+# if __has_include(<libintl.h>)
+#  define HAVE_GETTEXT true
+# endif
+#endif
 #ifndef HAVE_GETTEXT
-#define HAVE_GETTEXT		0
-#endif /* !defined HAVE_GETTEXT */
+# define HAVE_GETTEXT false
+#endif
 
 #ifndef HAVE_INCOMPATIBLE_CTIME_R
-#define HAVE_INCOMPATIBLE_CTIME_R	0
+# define HAVE_INCOMPATIBLE_CTIME_R 0
 #endif
 
 #ifndef HAVE_LINK
-#define HAVE_LINK		1
+# define HAVE_LINK 1
 #endif /* !defined HAVE_LINK */
 
 #ifndef HAVE_MALLOC_ERRNO
-#define HAVE_MALLOC_ERRNO 1
+# define HAVE_MALLOC_ERRNO 1
 #endif
 
 #ifndef HAVE_POSIX_DECLS
-#define HAVE_POSIX_DECLS 1
+# define HAVE_POSIX_DECLS 1
 #endif
 
-#ifndef HAVE_STDBOOL_H
-#define HAVE_STDBOOL_H (199901 <= __STDC_VERSION__)
+#ifndef HAVE_SETENV
+# define HAVE_SETENV 1
 #endif
 
 #ifndef HAVE_STRDUP
-#define HAVE_STRDUP 1
-#endif
-
-#ifndef HAVE_STRTOLL
-#define HAVE_STRTOLL 1
+# define HAVE_STRDUP 1
 #endif
 
 #ifndef HAVE_SYMLINK
-#define HAVE_SYMLINK		1
+# define HAVE_SYMLINK 1
 #endif /* !defined HAVE_SYMLINK */
 
+#if !defined HAVE_SYS_STAT_H && defined __has_include
+# if !__has_include(<sys/stat.h>)
+#  define HAVE_SYS_STAT_H false
+# endif
+#endif
 #ifndef HAVE_SYS_STAT_H
-#define HAVE_SYS_STAT_H		1
-#endif /* !defined HAVE_SYS_STAT_H */
+# define HAVE_SYS_STAT_H true
+#endif
 
+#if !defined HAVE_UNISTD_H && defined __has_include
+# if !__has_include(<unistd.h>)
+#  define HAVE_UNISTD_H false
+# endif
+#endif
 #ifndef HAVE_UNISTD_H
-#define HAVE_UNISTD_H		1
-#endif /* !defined HAVE_UNISTD_H */
-
-#ifndef HAVE_UTMPX_H
-#define HAVE_UTMPX_H		1
-#endif /* !defined HAVE_UTMPX_H */
+# define HAVE_UNISTD_H true
+#endif
 
 #ifndef NETBSD_INSPIRED
 # define NETBSD_INSPIRED 1
 #endif
 
 #if HAVE_INCOMPATIBLE_CTIME_R
-#define asctime_r _incompatible_asctime_r
-#define ctime_r _incompatible_ctime_r
+# define asctime_r _incompatible_asctime_r
+# define ctime_r _incompatible_ctime_r
 #endif /* HAVE_INCOMPATIBLE_CTIME_R */
 
 /* Enable tm_gmtoff, tm_zone, and environ on GNUish systems.  */
@@ -118,15 +155,17 @@
 /* Enable strtoimax on pre-C99 Solaris 11.  */
 #define __EXTENSIONS__ 1
 
-/* To avoid having 'stat' fail unnecessarily with errno == EOVERFLOW,
-   enable large files on GNUish systems ...  */
+/* On GNUish systems where time_t might be 32 or 64 bits, use 64.
+   On these platforms _FILE_OFFSET_BITS must also be 64; otherwise
+   setting _TIME_BITS to 64 does not work.  The code does not
+   otherwise rely on _FILE_OFFSET_BITS being 64, since it does not
+   use off_t or functions like 'stat' that depend on off_t.  */
 #ifndef _FILE_OFFSET_BITS
 # define _FILE_OFFSET_BITS 64
 #endif
-/* ... and on AIX ...  */
-#define _LARGE_FILES 1
-/* ... and enable large inode numbers on Mac OS X 10.5 and later.  */
-#define _DARWIN_USE_64_BIT_INODE 1
+#if !defined _TIME_BITS && _FILE_OFFSET_BITS == 64
+# define _TIME_BITS 64
+#endif
 
 /*
 ** Nested includes
@@ -157,8 +196,11 @@
 #undef tzalloc
 #undef tzfree
 
-#include <sys/types.h>	/* for time_t */
+#include <stddef.h>
 #include <string.h>
+#if !PORT_TO_C89
+# include <inttypes.h>
+#endif
 #include <limits.h>	/* for CHAR_BIT et al. */
 #include <stdlib.h>
 
@@ -168,6 +210,9 @@
 # define EINVAL ERANGE
 #endif
 
+#ifndef ELOOP
+# define ELOOP EINVAL
+#endif
 #ifndef ENAMETOOLONG
 # define ENAMETOOLONG EINVAL
 #endif
@@ -182,11 +227,11 @@
 #endif
 
 #if HAVE_GETTEXT
-#include <libintl.h>
+# include <libintl.h>
 #endif /* HAVE_GETTEXT */
 
 #if HAVE_UNISTD_H
-#include <unistd.h>	/* for R_OK, and other POSIX goodness */
+# include <unistd.h> /* for R_OK, and other POSIX goodness */
 #endif /* HAVE_UNISTD_H */
 
 #ifndef HAVE_STRFTIME_L
@@ -222,24 +267,29 @@
 #endif
 
 #ifndef R_OK
-#define R_OK	4
+# define R_OK 4
 #endif /* !defined R_OK */
 
+#if PORT_TO_C89
+
 /*
 ** Define HAVE_STDINT_H's default value here, rather than at the
 ** start, since __GLIBC__ and INTMAX_MAX's values depend on
-** previously-included files.  glibc 2.1 and Solaris 10 and later have
+** previously included files.  glibc 2.1 and Solaris 10 and later have
 ** stdint.h, even with pre-C99 compilers.
 */
+#if !defined HAVE_STDINT_H && defined __has_include
+# define HAVE_STDINT_H true /* C23 __has_include implies C99 stdint.h.  */
+#endif
 #ifndef HAVE_STDINT_H
-#define HAVE_STDINT_H \
+# define HAVE_STDINT_H \
    (199901 <= __STDC_VERSION__ \
-    || 2 < __GLIBC__ + (1 <= __GLIBC_MINOR__)	\
+    || 2 < __GLIBC__ + (1 <= __GLIBC_MINOR__) \
     || __CYGWIN__ || INTMAX_MAX)
 #endif /* !defined HAVE_STDINT_H */
 
 #if HAVE_STDINT_H
-#include <stdint.h>
+# include <stdint.h>
 #endif /* !HAVE_STDINT_H */
 
 #ifndef HAVE_INTTYPES_H
@@ -250,36 +300,36 @@
 #endif
 
 /* Pre-C99 GCC compilers define __LONG_LONG_MAX__ instead of LLONG_MAX.  */
-#ifdef __LONG_LONG_MAX__
+#if defined __LONG_LONG_MAX__ && !defined __STRICT_ANSI__
 # ifndef LLONG_MAX
 #  define LLONG_MAX __LONG_LONG_MAX__
 # endif
 # ifndef LLONG_MIN
 #  define LLONG_MIN (-1 - LLONG_MAX)
 # endif
+# ifndef ULLONG_MAX
+#  define ULLONG_MAX (LLONG_MAX * 2ull + 1)
+# endif
 #endif
 
 #ifndef INT_FAST64_MAX
-# ifdef LLONG_MAX
-typedef long long	int_fast64_t;
-#  define INT_FAST64_MIN LLONG_MIN
-#  define INT_FAST64_MAX LLONG_MAX
-# else
-#  if LONG_MAX >> 31 < 0xffffffff
-Please use a compiler that supports a 64-bit integer type (or wider);
-you may need to compile with "-DHAVE_STDINT_H".
-#  endif
-typedef long		int_fast64_t;
+# if 1 <= LONG_MAX >> 31 >> 31
+typedef long int_fast64_t;
 #  define INT_FAST64_MIN LONG_MIN
 #  define INT_FAST64_MAX LONG_MAX
+# else
+/* If this fails, compile with -DHAVE_STDINT_H or with a better compiler.  */
+typedef long long int_fast64_t;
+#  define INT_FAST64_MIN LLONG_MIN
+#  define INT_FAST64_MAX LLONG_MAX
 # endif
 #endif
 
 #ifndef PRIdFAST64
-# if INT_FAST64_MAX == LLONG_MAX
-#  define PRIdFAST64 "lld"
-# else
+# if INT_FAST64_MAX == LONG_MAX
 #  define PRIdFAST64 "ld"
+# else
+#  define PRIdFAST64 "lld"
 # endif
 #endif
 
@@ -302,6 +352,9 @@
 #ifndef INTMAX_MAX
 # ifdef LLONG_MAX
 typedef long long intmax_t;
+#  ifndef HAVE_STRTOLL
+#   define HAVE_STRTOLL true
+#  endif
 #  if HAVE_STRTOLL
 #   define strtoimax strtoll
 #  endif
@@ -325,70 +378,183 @@
 # endif
 #endif
 
+#ifndef PTRDIFF_MAX
+# define PTRDIFF_MAX MAXVAL(ptrdiff_t, TYPE_BIT(ptrdiff_t))
+#endif
+
 #ifndef UINT_FAST32_MAX
 typedef unsigned long uint_fast32_t;
 #endif
 
 #ifndef UINT_FAST64_MAX
-# if defined ULLONG_MAX || defined __LONG_LONG_MAX__
-typedef unsigned long long uint_fast64_t;
+# if 3 <= ULONG_MAX >> 31 >> 31
+typedef unsigned long uint_fast64_t;
+#  define UINT_FAST64_MAX ULONG_MAX
 # else
-#  if ULONG_MAX >> 31 >> 1 < 0xffffffff
-Please use a compiler that supports a 64-bit integer type (or wider);
-you may need to compile with "-DHAVE_STDINT_H".
-#  endif
-typedef unsigned long	uint_fast64_t;
+/* If this fails, compile with -DHAVE_STDINT_H or with a better compiler.  */
+typedef unsigned long long uint_fast64_t;
+#  define UINT_FAST64_MAX ULLONG_MAX
 # endif
 #endif
 
 #ifndef UINTMAX_MAX
-# if defined ULLONG_MAX || defined __LONG_LONG_MAX__
+# ifdef ULLONG_MAX
 typedef unsigned long long uintmax_t;
+#  define UINTMAX_MAX ULLONG_MAX
 # else
 typedef unsigned long uintmax_t;
+#  define UINTMAX_MAX ULONG_MAX
 # endif
 #endif
 
 #ifndef PRIuMAX
-# if defined ULLONG_MAX || defined __LONG_LONG_MAX__
+# ifdef ULLONG_MAX
 #  define PRIuMAX "llu"
 # else
 #  define PRIuMAX "lu"
 # endif
 #endif
 
-#ifndef INT32_MAX
-#define INT32_MAX 0x7fffffff
-#endif /* !defined INT32_MAX */
-#ifndef INT32_MIN
-#define INT32_MIN (-1 - INT32_MAX)
-#endif /* !defined INT32_MIN */
-
 #ifndef SIZE_MAX
-#define SIZE_MAX ((size_t) -1)
+# define SIZE_MAX ((size_t) -1)
+#endif
+
+#endif /* PORT_TO_C89 */
+
+/* The maximum size of any created object, as a signed integer.
+   Although the C standard does not outright prohibit larger objects,
+   behavior is undefined if the result of pointer subtraction does not
+   fit into ptrdiff_t, and the code assumes in several places that
+   pointer subtraction works.  As a practical matter it's OK to not
+   support objects larger than this.  */
+#define INDEX_MAX ((ptrdiff_t) min(PTRDIFF_MAX, SIZE_MAX))
+
+/* Support ckd_add, ckd_sub, ckd_mul on C23 or recent-enough GCC-like
+   hosts, unless compiled with -DHAVE_STDCKDINT_H=0 or with pre-C23 EDG.  */
+#if !defined HAVE_STDCKDINT_H && defined __has_include
+# if __has_include(<stdckdint.h>)
+#  define HAVE_STDCKDINT_H true
+# endif
+#endif
+#ifdef HAVE_STDCKDINT_H
+# if HAVE_STDCKDINT_H
+#  include <stdckdint.h>
+# endif
+#elif defined __EDG__
+/* Do nothing, to work around EDG bug <https://bugs.gnu.org/53256>.  */
+#elif defined __has_builtin
+# if __has_builtin(__builtin_add_overflow)
+#  define ckd_add(r, a, b) __builtin_add_overflow(a, b, r)
+# endif
+# if __has_builtin(__builtin_sub_overflow)
+#  define ckd_sub(r, a, b) __builtin_sub_overflow(a, b, r)
+# endif
+# if __has_builtin(__builtin_mul_overflow)
+#  define ckd_mul(r, a, b) __builtin_mul_overflow(a, b, r)
+# endif
+#elif 7 <= __GNUC__
+# define ckd_add(r, a, b) __builtin_add_overflow(a, b, r)
+# define ckd_sub(r, a, b) __builtin_sub_overflow(a, b, r)
+# define ckd_mul(r, a, b) __builtin_mul_overflow(a, b, r)
 #endif
 
 #if 3 <= __GNUC__
-# define ATTRIBUTE_CONST __attribute__((const))
-# define ATTRIBUTE_MALLOC __attribute__((__malloc__))
-# define ATTRIBUTE_PURE __attribute__((__pure__))
-# define ATTRIBUTE_FORMAT(spec) __attribute__((__format__ spec))
+# define ATTRIBUTE_MALLOC __attribute__((malloc))
+# define ATTRIBUTE_FORMAT(spec) __attribute__((format spec))
 #else
-# define ATTRIBUTE_CONST /* empty */
 # define ATTRIBUTE_MALLOC /* empty */
-# define ATTRIBUTE_PURE /* empty */
 # define ATTRIBUTE_FORMAT(spec) /* empty */
 #endif
 
-#if !defined _Noreturn && __STDC_VERSION__ < 201112
-# if 2 < __GNUC__ + (8 <= __GNUC_MINOR__)
-#  define _Noreturn __attribute__((__noreturn__))
+#if (defined __has_c_attribute \
+     && (202311 <= __STDC_VERSION__ || !defined __STRICT_ANSI__))
+# define HAVE___HAS_C_ATTRIBUTE true
+#else
+# define HAVE___HAS_C_ATTRIBUTE false
+#endif
+
+#if HAVE___HAS_C_ATTRIBUTE
+# if __has_c_attribute(deprecated)
+#  define ATTRIBUTE_DEPRECATED [[deprecated]]
+# endif
+#endif
+#ifndef ATTRIBUTE_DEPRECATED
+# if 3 < __GNUC__ + (2 <= __GNUC_MINOR__)
+#  define ATTRIBUTE_DEPRECATED __attribute__((deprecated))
 # else
-#  define _Noreturn
+#  define ATTRIBUTE_DEPRECATED /* empty */
 # endif
 #endif
 
-#if __STDC_VERSION__ < 199901 && !defined restrict
+#if HAVE___HAS_C_ATTRIBUTE
+# if __has_c_attribute(fallthrough)
+#  define ATTRIBUTE_FALLTHROUGH [[fallthrough]]
+# endif
+#endif
+#ifndef ATTRIBUTE_FALLTHROUGH
+# if 7 <= __GNUC__
+#  define ATTRIBUTE_FALLTHROUGH __attribute__((fallthrough))
+# else
+#  define ATTRIBUTE_FALLTHROUGH ((void) 0)
+# endif
+#endif
+
+#if HAVE___HAS_C_ATTRIBUTE
+# if __has_c_attribute(maybe_unused)
+#  define ATTRIBUTE_MAYBE_UNUSED [[maybe_unused]]
+# endif
+#endif
+#ifndef ATTRIBUTE_MAYBE_UNUSED
+# if 2 < __GNUC__ + (7 <= __GNUC_MINOR__)
+#  define ATTRIBUTE_MAYBE_UNUSED __attribute__((unused))
+# else
+#  define ATTRIBUTE_MAYBE_UNUSED /* empty */
+# endif
+#endif
+
+#if HAVE___HAS_C_ATTRIBUTE
+# if __has_c_attribute(noreturn)
+#  define ATTRIBUTE_NORETURN [[noreturn]]
+# endif
+#endif
+#ifndef ATTRIBUTE_NORETURN
+# if 201112 <= __STDC_VERSION__
+#  define ATTRIBUTE_NORETURN _Noreturn
+# elif 2 < __GNUC__ + (8 <= __GNUC_MINOR__)
+#  define ATTRIBUTE_NORETURN __attribute__((noreturn))
+# else
+#  define ATTRIBUTE_NORETURN /* empty */
+# endif
+#endif
+
+#if HAVE___HAS_C_ATTRIBUTE
+# if __has_c_attribute(reproducible)
+#  define ATTRIBUTE_REPRODUCIBLE [[reproducible]]
+# endif
+#endif
+#ifndef ATTRIBUTE_REPRODUCIBLE
+# if 3 <= __GNUC__
+#  define ATTRIBUTE_REPRODUCIBLE __attribute__((pure))
+# else
+#  define ATTRIBUTE_REPRODUCIBLE /* empty */
+# endif
+#endif
+
+#if HAVE___HAS_C_ATTRIBUTE
+# if __has_c_attribute(unsequenced)
+#  define ATTRIBUTE_UNSEQUENCED [[unsequenced]]
+# endif
+#endif
+#ifndef ATTRIBUTE_UNSEQUENCED
+# if 3 <= __GNUC__
+#  define ATTRIBUTE_UNSEQUENCED __attribute__((const))
+# else
+#  define ATTRIBUTE_UNSEQUENCED /* empty */
+# endif
+#endif
+
+#if (__STDC_VERSION__ < 199901 && !defined restrict \
+     && (PORT_TO_C89 || defined _MSC_VER))
 # define restrict /* empty */
 #endif
 
@@ -505,11 +671,16 @@
 #  define altzone tz_altzone
 # endif
 
-char *asctime(struct tm const *);
+# if __STDC_VERSION__ < 202311
+#  define DEPRECATED_IN_C23 /* empty */
+# else
+#  define DEPRECATED_IN_C23 ATTRIBUTE_DEPRECATED
+# endif
+DEPRECATED_IN_C23 char *asctime(struct tm const *);
 char *asctime_r(struct tm const *restrict, char *restrict);
-char *ctime(time_t const *);
+DEPRECATED_IN_C23 char *ctime(time_t const *);
 char *ctime_r(time_t const *, char *);
-double difftime(time_t, time_t) ATTRIBUTE_CONST;
+ATTRIBUTE_UNSEQUENCED double difftime(time_t, time_t);
 size_t strftime(char *restrict, size_t, char const *restrict,
 		struct tm const *restrict);
 # if HAVE_STRFTIME_L
@@ -522,9 +693,24 @@
 struct tm *localtime_r(time_t const *restrict, struct tm *restrict);
 time_t mktime(struct tm *);
 time_t time(time_t *);
+time_t timegm(struct tm *);
 void tzset(void);
 #endif
 
+#ifndef HAVE_DECL_TIMEGM
+# if (202311 <= __STDC_VERSION__ \
+      || defined __GLIBC__ || defined __tm_zone /* musl */ \
+      || defined __FreeBSD__ || defined __NetBSD__ || defined __OpenBSD__ \
+      || (defined __APPLE__ && defined __MACH__))
+#  define HAVE_DECL_TIMEGM true
+# else
+#  define HAVE_DECL_TIMEGM false
+# endif
+#endif
+#if !HAVE_DECL_TIMEGM && !defined timegm
+time_t timegm(struct tm *);
+#endif
+
 #if !HAVE_DECL_ASCTIME_R && !defined asctime_r
 extern char *asctime_r(struct tm const *restrict, char *restrict);
 #endif
@@ -557,13 +743,13 @@
 ** declarations if time_tz is defined.
 */
 
-#ifdef STD_INSPIRED
+#ifndef STD_INSPIRED
+# define STD_INSPIRED 0
+#endif
+#if STD_INSPIRED
 # if TZ_TIME_T || !defined offtime
 struct tm *offtime(time_t const *, long);
 # endif
-# if TZ_TIME_T || !defined timegm
-time_t timegm(struct tm *);
-# endif
 # if TZ_TIME_T || !defined timelocal
 time_t timelocal(struct tm *);
 # endif
@@ -581,6 +767,7 @@
 /* Infer TM_ZONE on systems where this information is known, but suppress
    guessing if NO_TM_ZONE is defined.  Similarly for TM_GMTOFF.  */
 #if (defined __GLIBC__ \
+     || defined __tm_zone /* musl */ \
      || defined __FreeBSD__ || defined __NetBSD__ || defined __OpenBSD__ \
      || (defined __APPLE__ && defined __MACH__))
 # if !defined TM_GMTOFF && !defined NO_TM_GMTOFF
@@ -606,12 +793,12 @@
 time_t mktime_z(timezone_t restrict, struct tm *restrict);
 timezone_t tzalloc(char const *);
 void tzfree(timezone_t);
-# ifdef STD_INSPIRED
+# if STD_INSPIRED
 #  if TZ_TIME_T || !defined posix2time_z
-time_t posix2time_z(timezone_t, time_t) ATTRIBUTE_PURE;
+ATTRIBUTE_REPRODUCIBLE time_t posix2time_z(timezone_t, time_t);
 #  endif
 #  if TZ_TIME_T || !defined time2posix_z
-time_t time2posix_z(timezone_t, time_t) ATTRIBUTE_PURE;
+ATTRIBUTE_REPRODUCIBLE time_t time2posix_z(timezone_t, time_t);
 #  endif
 # endif
 #endif
@@ -620,18 +807,15 @@
 ** Finally, some convenience items.
 */
 
-#if HAVE_STDBOOL_H
-# include <stdbool.h>
-#else
-# define true 1
-# define false 0
-# define bool int
-#endif
-
-#define TYPE_BIT(type)	(sizeof(type) * CHAR_BIT)
+#define TYPE_BIT(type) (CHAR_BIT * (ptrdiff_t) sizeof(type))
 #define TYPE_SIGNED(type) (((type) -1) < 0)
 #define TWOS_COMPLEMENT(t) ((t) ~ (t) 0 < 0)
 
+/* Minimum and maximum of two values.  Use lower case to avoid
+   naming clashes with standard include files.  */
+#define max(a, b) ((a) > (b) ? (a) : (b))
+#define min(a, b) ((a) < (b) ? (a) : (b))
+
 /* Max and min values of the integer type T, of which only the bottom
    B bits are used, and where the highest-order used bit is considered
    to be a sign bit if T is signed.  */
@@ -651,7 +835,7 @@
    This implementation assumes no padding if time_t is signed and
    either the compiler lacks support for _Generic or time_t is not one
    of the standard signed integer types.  */
-#if HAVE_GENERIC
+#if HAVE__GENERIC
 # define TIME_T_MIN \
     _Generic((time_t) 0, \
 	     signed char: SCHAR_MIN, short: SHRT_MIN, \
@@ -664,10 +848,23 @@
 		int: INT_MAX, long: LONG_MAX, long long: LLONG_MAX, \
 		default: TIME_T_MAX_NO_PADDING)			    \
      : (time_t) -1)
+enum { SIGNED_PADDING_CHECK_NEEDED
+         = _Generic((time_t) 0,
+		    signed char: false, short: false,
+		    int: false, long: false, long long: false,
+		    default: true) };
 #else
 # define TIME_T_MIN TIME_T_MIN_NO_PADDING
 # define TIME_T_MAX TIME_T_MAX_NO_PADDING
+enum { SIGNED_PADDING_CHECK_NEEDED = true };
 #endif
+/* Try to check the padding assumptions.  Although TIME_T_MAX and the
+   following check can both have undefined behavior on oddball
+   platforms due to shifts exceeding widths of signed integers, these
+   platforms' compilers are likely to diagnose these issues in integer
+   constant expressions, so it shouldn't hurt to check statically.  */
+static_assert(! TYPE_SIGNED(time_t) || ! SIGNED_PADDING_CHECK_NEEDED
+	      || TIME_T_MAX >> (TYPE_BIT(time_t) - 2) == 1);
 
 /*
 ** 302 / 1000 is log10(2.0) rounded up.
@@ -689,21 +886,30 @@
 # define INITIALIZE(x)
 #endif
 
+/* Whether memory access must strictly follow the C standard.
+   If 0, it's OK to read uninitialized storage so long as the value is
+   not relied upon.  Defining it to 0 lets mktime access parts of
+   struct tm that might be uninitialized, as a heuristic when the
+   standard doesn't say what to return and when tm_gmtoff can help
+   mktime likely infer a better value.  */
 #ifndef UNINIT_TRAP
 # define UNINIT_TRAP 0
 #endif
 
 #ifdef DEBUG
-# define UNREACHABLE() abort()
-#elif 4 < __GNUC__ + (5 <= __GNUC_MINOR__)
-# define UNREACHABLE() __builtin_unreachable()
-#elif defined __has_builtin
-# if __has_builtin(__builtin_unreachable)
-#  define UNREACHABLE() __builtin_unreachable()
+# undef unreachable
+# define unreachable() abort()
+#elif !defined unreachable
+# ifdef __has_builtin
+#  if __has_builtin(__builtin_unreachable)
+#   define unreachable() __builtin_unreachable()
+#  endif
+# elif 4 < __GNUC__ + (5 <= __GNUC_MINOR__)
+#  define unreachable() __builtin_unreachable()
 # endif
-#endif
-#ifndef UNREACHABLE
-# define UNREACHABLE() ((void) 0)
+# ifndef unreachable
+#  define unreachable() ((void) 0)
+# endif
 #endif
 
 /*
@@ -725,53 +931,61 @@
 #if HAVE_INCOMPATIBLE_CTIME_R
 #undef asctime_r
 #undef ctime_r
-char *asctime_r(struct tm const *, char *);
+char *asctime_r(struct tm const *restrict, char *restrict);
 char *ctime_r(time_t const *, char *);
 #endif /* HAVE_INCOMPATIBLE_CTIME_R */
 
 /* Handy macros that are independent of tzfile implementation.  */
 
-#define SECSPERMIN	60
-#define MINSPERHOUR	60
-#define HOURSPERDAY	24
-#define DAYSPERWEEK	7
-#define DAYSPERNYEAR	365
-#define DAYSPERLYEAR	366
-#define SECSPERHOUR	(SECSPERMIN * MINSPERHOUR)
-#define SECSPERDAY	((int_fast32_t) SECSPERHOUR * HOURSPERDAY)
-#define MONSPERYEAR	12
+enum {
+  SECSPERMIN = 60,
+  MINSPERHOUR = 60,
+  SECSPERHOUR = SECSPERMIN * MINSPERHOUR,
+  HOURSPERDAY = 24,
+  DAYSPERWEEK = 7,
+  DAYSPERNYEAR = 365,
+  DAYSPERLYEAR = DAYSPERNYEAR + 1,
+  MONSPERYEAR = 12,
+  YEARSPERREPEAT = 400	/* years before a Gregorian repeat */
+};
 
-#define YEARSPERREPEAT		400	/* years before a Gregorian repeat */
+#define SECSPERDAY	((int_fast32_t) SECSPERHOUR * HOURSPERDAY)
+
 #define DAYSPERREPEAT		((int_fast32_t) 400 * 365 + 100 - 4 + 1)
 #define SECSPERREPEAT		((int_fast64_t) DAYSPERREPEAT * SECSPERDAY)
 #define AVGSECSPERYEAR		(SECSPERREPEAT / YEARSPERREPEAT)
 
-#define TM_SUNDAY	0
-#define TM_MONDAY	1
-#define TM_TUESDAY	2
-#define TM_WEDNESDAY	3
-#define TM_THURSDAY	4
-#define TM_FRIDAY	5
-#define TM_SATURDAY	6
+enum {
+  TM_SUNDAY,
+  TM_MONDAY,
+  TM_TUESDAY,
+  TM_WEDNESDAY,
+  TM_THURSDAY,
+  TM_FRIDAY,
+  TM_SATURDAY
+};
 
-#define TM_JANUARY	0
-#define TM_FEBRUARY	1
-#define TM_MARCH	2
-#define TM_APRIL	3
-#define TM_MAY		4
-#define TM_JUNE		5
-#define TM_JULY		6
-#define TM_AUGUST	7
-#define TM_SEPTEMBER	8
-#define TM_OCTOBER	9
-#define TM_NOVEMBER	10
-#define TM_DECEMBER	11
+enum {
+  TM_JANUARY,
+  TM_FEBRUARY,
+  TM_MARCH,
+  TM_APRIL,
+  TM_MAY,
+  TM_JUNE,
+  TM_JULY,
+  TM_AUGUST,
+  TM_SEPTEMBER,
+  TM_OCTOBER,
+  TM_NOVEMBER,
+  TM_DECEMBER
+};
 
-#define TM_YEAR_BASE	1900
-#define TM_WDAY_BASE	TM_MONDAY
-
-#define EPOCH_YEAR	1970
-#define EPOCH_WDAY	TM_THURSDAY
+enum {
+  TM_YEAR_BASE = 1900,
+  TM_WDAY_BASE = TM_MONDAY,
+  EPOCH_YEAR = 1970,
+  EPOCH_WDAY = TM_THURSDAY
+};
 
 #define isleap(y) (((y) % 4) == 0 && (((y) % 100) != 0 || ((y) % 400) == 0))
 
diff --git a/libc/tzcode/strftime.c b/libc/tzcode/strftime.c
index d04c5ba..4cde556 100644
--- a/libc/tzcode/strftime.c
+++ b/libc/tzcode/strftime.c
@@ -71,8 +71,6 @@
     const char *    date_fmt;
 };
 
-#define Locale  (&C_time_locale)
-
 static const struct lc_time_T   C_time_locale = {
     {
         "Jan", "Feb", "Mar", "Apr", "May", "Jun",
@@ -128,13 +126,14 @@
 static char *   _yconv(int, int, bool, bool, char *, const char *, int);
 
 #ifndef YEAR_2000_NAME
-#define YEAR_2000_NAME  "CHECK_STRFTIME_FORMATS_FOR_TWO_DIGIT_YEARS"
+# define YEAR_2000_NAME  "CHECK_STRFTIME_FORMATS_FOR_TWO_DIGIT_YEARS"
 #endif /* !defined YEAR_2000_NAME */
 
 #if HAVE_STRFTIME_L
 size_t
-strftime_l(char *s, size_t maxsize, char const *format, struct tm const *t,
-	   locale_t locale)
+strftime_l(char *restrict s, size_t maxsize, char const *restrict format,
+	   struct tm const *restrict t,
+	   ATTRIBUTE_MAYBE_UNUSED locale_t locale)
 {
   /* Just call strftime, as only the C locale is supported.  */
   return strftime(s, maxsize, format, t);
@@ -144,7 +143,8 @@
 #define FORCE_LOWER_CASE 0x100 /* Android extension. */
 
 size_t
-strftime(char *s, size_t maxsize, const char *format, const struct tm *t)
+strftime(char *restrict s, size_t maxsize, char const *restrict format,
+	 struct tm const *restrict t)
 {
     char *  p;
     int saved_errno = errno;
@@ -217,6 +217,8 @@
 _fmt(const char *format, const struct tm *t, char *pt,
         const char *ptlim, enum warn *warnp)
 {
+	struct lc_time_T const *Locale = &C_time_locale;
+
     for ( ; *format; ++format) {
         if (*format == '%') {
             int modifier = 0;
@@ -378,12 +380,21 @@
                     char buf[INT_STRLEN_MAXIMUM(time64_t) + 1] __attribute__((__uninitialized__));
                     time64_t    mkt;
 
-                    tm = *t;
+          					tm.tm_sec = t->tm_sec;
+					          tm.tm_min = t->tm_min;
+          					tm.tm_hour = t->tm_hour;
+					          tm.tm_mday = t->tm_mday;
+          					tm.tm_mon = t->tm_mon;
+					          tm.tm_year = t->tm_year;
+          					tm.tm_isdst = t->tm_isdst;
+#if defined TM_GMTOFF && ! UNINIT_TRAP
+					          tm.TM_GMTOFF = t->TM_GMTOFF;
+#endif
                     mkt = mktime64(&tm);
-					/* There is no portable, definitive
-					   test for whether whether mktime
-					   succeeded, so treat (time_t) -1 as
-					   the success that it might be.  */
+					/* If mktime fails, %s expands to the
+              value of (time_t) -1 as a failure
+              marker; this is better in practice
+              than strftime failing.  */
                     if (TYPE_SIGNED(time64_t)) {
                       intmax_t n = mkt;
                       sprintf(buf, "%"PRIdMAX, n);
@@ -607,19 +618,19 @@
 # endif
                 negative = diff < 0;
                 if (diff == 0) {
-#ifdef TM_ZONE
+# ifdef TM_ZONE
                   // Android-changed: do not use TM_ZONE as it is as it may be null.
                   {
                     const char* zone = _safe_tm_zone(t);
                     negative = zone[0] == '-';
                   }
-#else
+# else
                     negative = t->tm_isdst < 0;
-# if HAVE_TZNAME
+#  if HAVE_TZNAME
                     if (tzname[t->tm_isdst != 0][0] == '-')
                         negative = true;
+#  endif
 # endif
-#endif
                 }
                 if (negative) {
                     sign = "-";
@@ -748,7 +759,7 @@
     register int    lead;
     register int    trail;
 
-#define DIVISOR 100
+    int DIVISOR = 100;
     trail = a % DIVISOR + b % DIVISOR;
     lead = a / DIVISOR + b / DIVISOR + trail / DIVISOR;
     trail %= DIVISOR;
diff --git a/libc/tzcode/tzfile.h b/libc/tzcode/tzfile.h
index c5f9967..7ac8b51 100644
--- a/libc/tzcode/tzfile.h
+++ b/libc/tzcode/tzfile.h
@@ -22,15 +22,15 @@
 */
 
 #ifndef TZDIR
-#define TZDIR	"/usr/share/zoneinfo" /* Time zone object file directory */
+# define TZDIR "/usr/share/zoneinfo" /* Time zone object file directory */
 #endif /* !defined TZDIR */
 
 #ifndef TZDEFAULT
-#define TZDEFAULT	"/etc/localtime"
+# define TZDEFAULT "/etc/localtime"
 #endif /* !defined TZDEFAULT */
 
 #ifndef TZDEFRULES
-#define TZDEFRULES	"posixrules"
+# define TZDEFRULES "posixrules"
 #endif /* !defined TZDEFRULES */
 
 
@@ -103,21 +103,25 @@
 */
 
 #ifndef TZ_MAX_TIMES
-#define TZ_MAX_TIMES	2000
+/* This must be at least 242 for Europe/London with 'zic -b fat'.  */
+# define TZ_MAX_TIMES 2000
 #endif /* !defined TZ_MAX_TIMES */
 
 #ifndef TZ_MAX_TYPES
-/* This must be at least 17 for Europe/Samara and Europe/Vilnius.  */
-#define TZ_MAX_TYPES	256 /* Limited by what (unsigned char)'s can hold */
+/* This must be at least 18 for Europe/Vilnius with 'zic -b fat'.  */
+# define TZ_MAX_TYPES 256 /* Limited by what (unsigned char)'s can hold */
 #endif /* !defined TZ_MAX_TYPES */
 
 #ifndef TZ_MAX_CHARS
-#define TZ_MAX_CHARS	50	/* Maximum number of abbreviation characters */
+/* This must be at least 40 for America/Anchorage.  */
+# define TZ_MAX_CHARS 50	/* Maximum number of abbreviation characters */
 				/* (limited by what unsigned chars can hold) */
 #endif /* !defined TZ_MAX_CHARS */
 
 #ifndef TZ_MAX_LEAPS
-#define TZ_MAX_LEAPS	50	/* Maximum number of leap second corrections */
+/* This must be at least 27 for leap seconds from 1972 through mid-2023.
+   There's a plan to discontinue leap seconds by 2035.  */
+# define TZ_MAX_LEAPS 50	/* Maximum number of leap second corrections */
 #endif /* !defined TZ_MAX_LEAPS */
 
 #define SECSPERMIN	60
diff --git a/libdl/Android.bp b/libdl/Android.bp
index 4cdec44..fde3dfc 100644
--- a/libdl/Android.bp
+++ b/libdl/Android.bp
@@ -244,7 +244,7 @@
 
 genrule {
     name: "libdl.arm.map",
-    out: ["libdl.arm.map"],
+    out: ["libdl.arm.map.txt"],
     srcs: ["libdl.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm $(in) $(out)",
@@ -252,7 +252,7 @@
 
 genrule {
     name: "libdl.arm64.map",
-    out: ["libdl.arm64.map"],
+    out: ["libdl.arm64.map.txt"],
     srcs: ["libdl.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm64 $(in) $(out)",
@@ -260,7 +260,7 @@
 
 genrule {
     name: "libdl.riscv64.map",
-    out: ["libdl.riscv64.map"],
+    out: ["libdl.riscv64.map.txt"],
     srcs: ["libdl.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) riscv64 $(in) $(out)",
@@ -268,7 +268,7 @@
 
 genrule {
     name: "libdl.x86.map",
-    out: ["libdl.x86.map"],
+    out: ["libdl.x86.map.txt"],
     srcs: ["libdl.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86 $(in) $(out)",
@@ -276,7 +276,7 @@
 
 genrule {
     name: "libdl.x86_64.map",
-    out: ["libdl.x86_64.map"],
+    out: ["libdl.x86_64.map.txt"],
     srcs: ["libdl.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86_64 $(in) $(out)",
diff --git a/libm/Android.bp b/libm/Android.bp
index cc0d666..13fbf9a 100644
--- a/libm/Android.bp
+++ b/libm/Android.bp
@@ -94,8 +94,6 @@
         "upstream-freebsd/lib/msun/src/s_cbrtf.c",
         "upstream-freebsd/lib/msun/src/s_ccosh.c",
         "upstream-freebsd/lib/msun/src/s_ccoshf.c",
-        "upstream-freebsd/lib/msun/src/s_ceil.c",
-        "upstream-freebsd/lib/msun/src/s_ceilf.c",
         "upstream-freebsd/lib/msun/src/s_cexp.c",
         "upstream-freebsd/lib/msun/src/s_cexpf.c",
         "upstream-freebsd/lib/msun/src/s_cimag.c",
@@ -130,8 +128,6 @@
         "upstream-freebsd/lib/msun/src/s_fdim.c",
         "upstream-freebsd/lib/msun/src/s_finite.c",
         "upstream-freebsd/lib/msun/src/s_finitef.c",
-        "upstream-freebsd/lib/msun/src/s_floor.c",
-        "upstream-freebsd/lib/msun/src/s_floorf.c",
         "upstream-freebsd/lib/msun/src/s_fma.c",
         "upstream-freebsd/lib/msun/src/s_fmaf.c",
         "upstream-freebsd/lib/msun/src/s_fmax.c",
@@ -282,10 +278,8 @@
         arm: {
             srcs: [
                 "arm/fenv.c",
-            ],
-            exclude_srcs: [
-                "upstream-freebsd/lib/msun/src/s_floor.c",
-                "upstream-freebsd/lib/msun/src/s_floorf.c",
+                "upstream-freebsd/lib/msun/src/s_ceil.c",
+                "upstream-freebsd/lib/msun/src/s_ceilf.c",
             ],
             instruction_set: "arm",
             pack_relocations: false,
@@ -303,10 +297,6 @@
                 "arm64/fenv.c",
             ],
             exclude_srcs: [
-                "upstream-freebsd/lib/msun/src/s_ceil.c",
-                "upstream-freebsd/lib/msun/src/s_ceilf.c",
-                "upstream-freebsd/lib/msun/src/s_floor.c",
-                "upstream-freebsd/lib/msun/src/s_floorf.c",
                 "upstream-freebsd/lib/msun/src/s_fma.c",
                 "upstream-freebsd/lib/msun/src/s_fmaf.c",
                 "upstream-freebsd/lib/msun/src/s_fmax.c",
@@ -337,11 +327,6 @@
             ],
 
             exclude_srcs: [
-                // TODO: do the rest when our clang has https://reviews.llvm.org/D136508.
-                // TODO: "upstream-freebsd/lib/msun/src/s_ceil.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_ceilf.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_floor.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_floorf.c",
                 "upstream-freebsd/lib/msun/src/s_fma.c",
                 "upstream-freebsd/lib/msun/src/s_fmaf.c",
                 "upstream-freebsd/lib/msun/src/s_fmax.c",
@@ -356,12 +341,12 @@
                 "upstream-freebsd/lib/msun/src/s_lrintf.c",
                 "upstream-freebsd/lib/msun/src/s_lround.c",
                 "upstream-freebsd/lib/msun/src/s_lroundf.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_rint.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_rintf.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_round.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_roundf.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_trunc.c",
-                // TODO: "upstream-freebsd/lib/msun/src/s_truncf.c",
+                "upstream-freebsd/lib/msun/src/s_rint.c",
+                "upstream-freebsd/lib/msun/src/s_rintf.c",
+                "upstream-freebsd/lib/msun/src/s_round.c",
+                "upstream-freebsd/lib/msun/src/s_roundf.c",
+                "upstream-freebsd/lib/msun/src/s_trunc.c",
+                "upstream-freebsd/lib/msun/src/s_truncf.c",
             ],
             version_script: ":libm.riscv64.map",
         },
@@ -373,10 +358,6 @@
                 "x86/lrintf.S",
             ],
             exclude_srcs: [
-                "upstream-freebsd/lib/msun/src/s_ceil.c",
-                "upstream-freebsd/lib/msun/src/s_ceilf.c",
-                "upstream-freebsd/lib/msun/src/s_floor.c",
-                "upstream-freebsd/lib/msun/src/s_floorf.c",
                 "upstream-freebsd/lib/msun/src/s_lrint.c",
                 "upstream-freebsd/lib/msun/src/s_lrintf.c",
                 "upstream-freebsd/lib/msun/src/s_rint.c",
@@ -400,10 +381,6 @@
                 "x86_64/lrintf.S",
             ],
             exclude_srcs: [
-                "upstream-freebsd/lib/msun/src/s_ceil.c",
-                "upstream-freebsd/lib/msun/src/s_ceilf.c",
-                "upstream-freebsd/lib/msun/src/s_floor.c",
-                "upstream-freebsd/lib/msun/src/s_floorf.c",
                 "upstream-freebsd/lib/msun/src/s_llrint.c",
                 "upstream-freebsd/lib/msun/src/s_llrintf.c",
                 "upstream-freebsd/lib/msun/src/s_lrint.c",
@@ -496,7 +473,7 @@
 
 genrule {
     name: "libm.arm.map",
-    out: ["libm.arm.map"],
+    out: ["libm.arm.map.txt"],
     srcs: ["libm.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm $(in) $(out)",
@@ -504,7 +481,7 @@
 
 genrule {
     name: "libm.arm64.map",
-    out: ["libm.arm64.map"],
+    out: ["libm.arm64.map.txt"],
     srcs: ["libm.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) arm64 $(in) $(out)",
@@ -512,7 +489,7 @@
 
 genrule {
     name: "libm.riscv64.map",
-    out: ["libm.riscv64.map"],
+    out: ["libm.riscv64.map.txt"],
     srcs: ["libm.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) riscv64 $(in) $(out)",
@@ -520,7 +497,7 @@
 
 genrule {
     name: "libm.x86.map",
-    out: ["libm.x86.map"],
+    out: ["libm.x86.map.txt"],
     srcs: ["libm.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86 $(in) $(out)",
@@ -528,7 +505,7 @@
 
 genrule {
     name: "libm.x86_64.map",
-    out: ["libm.x86_64.map"],
+    out: ["libm.x86_64.map.txt"],
     srcs: ["libm.map.txt"],
     tools: ["generate-version-script"],
     cmd: "$(location generate-version-script) x86_64 $(in) $(out)",
diff --git a/libm/builtins.cpp b/libm/builtins.cpp
index 96c006d..41e145b 100644
--- a/libm/builtins.cpp
+++ b/libm/builtins.cpp
@@ -22,7 +22,7 @@
 float fabsf(float x) { return __builtin_fabsf(x); }
 long double fabsl(long double x) { return __builtin_fabsl(x); }
 
-#if defined(__aarch64__) || defined(__i386__) || defined(__x86_64__)
+#if defined(__aarch64__) || defined(__riscv) || defined(__i386__) || defined(__x86_64__)
 float ceilf(float x) { return __builtin_ceilf(x); }
 double ceil(double x) { return __builtin_ceil(x); }
 #if defined(__ILP32__)
@@ -46,7 +46,7 @@
 }
 float floorf(float x) { return s_floorf::floorf(x); }
 double floor(double x) { return s_floor::floor(x); }
-#elif defined(__arm__) || defined(__aarch64__) || defined(__i386__) || defined(__x86_64__)
+#else
 float floorf(float x) { return __builtin_floorf(x); }
 double floor(double x) { return __builtin_floor(x); }
 #if defined(__ILP32__)
@@ -79,7 +79,7 @@
 long long llroundf(float x) { return __builtin_llroundf(x); }
 #endif
 
-#if defined(__aarch64__) || defined(__i386__) || defined(__x86_64__)
+#if defined(__aarch64__) || defined(__riscv) || defined(__i386__) || defined(__x86_64__)
 float rintf(float x) { return __builtin_rintf(x); }
 double rint(double x) { return __builtin_rint(x); }
 #if defined(__ILP32__)
@@ -87,7 +87,7 @@
 #endif
 #endif
 
-#if defined(__aarch64__)
+#if defined(__aarch64__) || defined(__riscv)
 float roundf(float x) { return __builtin_roundf(x); }
 double round(double x) { return __builtin_round(x); }
 #endif
@@ -98,7 +98,7 @@
 __weak_reference(sqrt, sqrtl);
 #endif
 
-#if defined(__aarch64__) || defined(__i386__) || defined(__x86_64__)
+#if defined(__aarch64__) || defined(__riscv) || defined(__i386__) || defined(__x86_64__)
 float truncf(float x) { return __builtin_truncf(x); }
 double trunc(double x) { return __builtin_trunc(x); }
 #if defined(__ILP32__)
diff --git a/linker/Android.bp b/linker/Android.bp
index 83077c6..020bd7d 100644
--- a/linker/Android.bp
+++ b/linker/Android.bp
@@ -374,6 +374,11 @@
     ],
 
     symlinks: ["linker_asan"],
+    arch: {
+        arm64: {
+            symlinks: ["linker_hwasan"],
+        },
+    },
     multilib: {
         lib64: {
             suffix: "64",
diff --git a/linker/arch/arm64/tlsdesc_resolver.S b/linker/arch/arm64/tlsdesc_resolver.S
index 96eff8e..ad155e2 100644
--- a/linker/arch/arm64/tlsdesc_resolver.S
+++ b/linker/arch/arm64/tlsdesc_resolver.S
@@ -58,9 +58,9 @@
   cmp x21, x22
   b.lo .fallback
 
-  ldr x21, [x0, #8]             // TlsIndex::module
+  ldr x21, [x0, #8]             // TlsIndex::module_id
   ldr x22, [x0, #16]            // TlsIndex::offset
-  ldr x21, [x20, x21, lsl #3]   // TlsDtv::modules[module]
+  ldr x21, [x20, x21, lsl #3]   // TlsDtv::modules[module_id]
   cbz x21, .fallback
   add x0, x21, x22
   sub x0, x0, x19
diff --git a/linker/arch/riscv64/begin.S b/linker/arch/riscv64/begin.S
index f7509c6..21665cb 100644
--- a/linker/arch/riscv64/begin.S
+++ b/linker/arch/riscv64/begin.S
@@ -33,7 +33,7 @@
   .cfi_undefined ra
 
   mv a0, sp
-  jal __linker_init
+  call __linker_init
 
   // __linker_init returns the address of the entry point in the main image.
   jr a0
diff --git a/linker/linker.cpp b/linker/linker.cpp
index 6246f8c..17b574f 100644
--- a/linker/linker.cpp
+++ b/linker/linker.cpp
@@ -34,6 +34,7 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include <sys/auxv.h>
 #include <sys/mman.h>
 #include <sys/param.h>
 #include <sys/vfs.h>
@@ -133,6 +134,36 @@
   nullptr
 };
 
+#if defined(__aarch64__)
+static const char* const kHwasanSystemLibDir  = "/system/lib64/hwasan";
+static const char* const kHwasanOdmLibDir     = "/odm/lib64/hwasan";
+static const char* const kHwasanVendorLibDir  = "/vendor/lib64/hwasan";
+
+// HWASan is only supported on aarch64.
+static const char* const kHwsanDefaultLdPaths[] = {
+  kHwasanSystemLibDir,
+  kSystemLibDir,
+  kHwasanOdmLibDir,
+  kOdmLibDir,
+  kHwasanVendorLibDir,
+  kVendorLibDir,
+  nullptr
+};
+
+// Is HWASAN enabled?
+static bool g_is_hwasan = false;
+#else
+static const char* const kHwsanDefaultLdPaths[] = {
+  kSystemLibDir,
+  kOdmLibDir,
+  kVendorLibDir,
+  nullptr
+};
+
+// Never any HWASan. Help the compiler remove the code we don't need.
+constexpr bool g_is_hwasan = false;
+#endif
+
 // Is ASAN enabled?
 static bool g_is_asan = false;
 
@@ -2134,26 +2165,46 @@
   }
   // End Workaround for dlopen(/system/lib/<soname>) when .so is in /apex.
 
-  std::string asan_name_holder;
+  std::string translated_name_holder;
 
+  assert(!g_is_hwasan || !g_is_asan);
   const char* translated_name = name;
   if (g_is_asan && translated_name != nullptr && translated_name[0] == '/') {
     char original_path[PATH_MAX];
     if (realpath(name, original_path) != nullptr) {
-      asan_name_holder = std::string(kAsanLibDirPrefix) + original_path;
-      if (file_exists(asan_name_holder.c_str())) {
+      translated_name_holder = std::string(kAsanLibDirPrefix) + original_path;
+      if (file_exists(translated_name_holder.c_str())) {
         soinfo* si = nullptr;
         if (find_loaded_library_by_realpath(ns, original_path, true, &si)) {
           PRINT("linker_asan dlopen NOT translating \"%s\" -> \"%s\": library already loaded", name,
-                asan_name_holder.c_str());
+                translated_name_holder.c_str());
         } else {
           PRINT("linker_asan dlopen translating \"%s\" -> \"%s\"", name, translated_name);
-          translated_name = asan_name_holder.c_str();
+          translated_name = translated_name_holder.c_str();
+        }
+      }
+    }
+  } else if (g_is_hwasan && translated_name != nullptr && translated_name[0] == '/') {
+    char original_path[PATH_MAX];
+    if (realpath(name, original_path) != nullptr) {
+      // Keep this the same as CreateHwasanPath in system/linkerconfig/modules/namespace.cc.
+      std::string path(original_path);
+      auto slash = path.rfind('/');
+      if (slash != std::string::npos || slash != path.size() - 1) {
+        translated_name_holder = path.substr(0, slash) + "/hwasan" + path.substr(slash);
+      }
+      if (!translated_name_holder.empty() && file_exists(translated_name_holder.c_str())) {
+        soinfo* si = nullptr;
+        if (find_loaded_library_by_realpath(ns, original_path, true, &si)) {
+          PRINT("linker_hwasan dlopen NOT translating \"%s\" -> \"%s\": library already loaded", name,
+                translated_name_holder.c_str());
+        } else {
+          PRINT("linker_hwasan dlopen translating \"%s\" -> \"%s\"", name, translated_name);
+          translated_name = translated_name_holder.c_str();
         }
       }
     }
   }
-
   ProtectedDataGuard guard;
   soinfo* si = find_library(ns, translated_name, flags, extinfo, caller);
   loading_trace.End();
@@ -3142,6 +3193,14 @@
       case DT_AARCH64_VARIANT_PCS:
         // Ignored: AArch64 processor-specific dynamic array tags.
         break;
+      // TODO(mitchp): Add support to libc_init_mte to use these dynamic array entries instead of
+      // the Android-specific ELF note.
+      case DT_AARCH64_MEMTAG_MODE:
+      case DT_AARCH64_MEMTAG_HEAP:
+      case DT_AARCH64_MEMTAG_STACK:
+      case DT_AARCH64_MEMTAG_GLOBALS:
+      case DT_AARCH64_MEMTAG_GLOBALSSZ:
+        break;
 #endif
 
       default:
@@ -3327,9 +3386,10 @@
   return true;
 }
 
-static std::vector<android_namespace_t*> init_default_namespace_no_config(bool is_asan) {
+static std::vector<android_namespace_t*> init_default_namespace_no_config(bool is_asan, bool is_hwasan) {
   g_default_namespace.set_isolated(false);
-  auto default_ld_paths = is_asan ? kAsanDefaultLdPaths : kDefaultLdPaths;
+  auto default_ld_paths = is_asan ? kAsanDefaultLdPaths : (
+    is_hwasan ? kHwsanDefaultLdPaths : kDefaultLdPaths);
 
   char real_path[PATH_MAX];
   std::vector<std::string> ld_default_paths;
@@ -3433,6 +3493,7 @@
   return kLdConfigFilePath;
 }
 
+
 std::vector<android_namespace_t*> init_default_namespaces(const char* executable_path) {
   g_default_namespace.set_name("(default)");
 
@@ -3446,6 +3507,16 @@
               (strcmp(bname, "linker_asan") == 0 ||
                strcmp(bname, "linker_asan64") == 0);
 
+#if defined(__aarch64__)
+  // HWASan is only supported on AArch64.
+  // The AT_SECURE restriction is because this is a debug feature that does
+  // not need to work on secure binaries, it doesn't hurt to disallow the
+  // environment variable for them, as it impacts the program execution.
+  char* hwasan_env = getenv("LD_HWASAN");
+  g_is_hwasan = (bname != nullptr &&
+              strcmp(bname, "linker_hwasan64") == 0) ||
+              (hwasan_env != nullptr && !getauxval(AT_SECURE) && strcmp(hwasan_env, "1") == 0);
+#endif
   const Config* config = nullptr;
 
   {
@@ -3453,7 +3524,7 @@
     INFO("[ Reading linker config \"%s\" ]", ld_config_file_path.c_str());
     ScopedTrace trace(("linker config " + ld_config_file_path).c_str());
     std::string error_msg;
-    if (!Config::read_binary_config(ld_config_file_path.c_str(), executable_path, g_is_asan,
+    if (!Config::read_binary_config(ld_config_file_path.c_str(), executable_path, g_is_asan, g_is_hwasan,
                                     &config, &error_msg)) {
       if (!error_msg.empty()) {
         DL_WARN("Warning: couldn't read '%s' for '%s' (using default configuration instead): %s",
@@ -3464,7 +3535,7 @@
   }
 
   if (config == nullptr) {
-    return init_default_namespace_no_config(g_is_asan);
+    return init_default_namespace_no_config(g_is_asan, g_is_hwasan);
   }
 
   const auto& namespace_configs = config->namespace_configs();
diff --git a/linker/linker_config.cpp b/linker/linker_config.cpp
index 1771e87..ad40c50 100644
--- a/linker/linker_config.cpp
+++ b/linker/linker_config.cpp
@@ -463,6 +463,7 @@
 bool Config::read_binary_config(const char* ld_config_file_path,
                                       const char* binary_realpath,
                                       bool is_asan,
+                                      bool is_hwasan,
                                       const Config** config,
                                       std::string* error_msg) {
   g_config.clear();
@@ -579,6 +580,8 @@
     // these are affected by is_asan flag
     if (is_asan) {
       property_name_prefix += ".asan";
+    } else if (is_hwasan) {
+      property_name_prefix += ".hwasan";
     }
 
     // search paths are resolved (canonicalized). This is required mainly for
diff --git a/linker/linker_config.h b/linker/linker_config.h
index fe23ec1..09fea45 100644
--- a/linker/linker_config.h
+++ b/linker/linker_config.h
@@ -166,6 +166,7 @@
   static bool read_binary_config(const char* ld_config_file_path,
                                  const char* binary_realpath,
                                  bool is_asan,
+                                 bool is_hwasan,
                                  const Config** config,
                                  std::string* error_msg);
 
diff --git a/linker/linker_config_test.cpp b/linker/linker_config_test.cpp
index acdf641..7e947f3 100644
--- a/linker/linker_config_test.cpp
+++ b/linker/linker_config_test.cpp
@@ -40,6 +40,7 @@
 #include <android-base/file.h>
 #include <android-base/scopeguard.h>
 #include <android-base/stringprintf.h>
+#include <vector>
 
 #if defined(__LP64__)
 #define ARCH_SUFFIX "64"
@@ -64,6 +65,10 @@
   "namespace.default.asan.search.paths = /data\n"
   "namespace.default.asan.search.paths += /vendor/${LIB}\n"
   "namespace.default.asan.permitted.paths = /data:/vendor\n"
+  "namespace.default.hwasan.search.paths = /vendor/${LIB}/hwasan\n"
+  "namespace.default.hwasan.search.paths += /vendor/${LIB}\n"
+  "namespace.default.hwasan.permitted.paths = /vendor/${LIB}/hwasan\n"
+  "namespace.default.hwasan.permitted.paths += /vendor/${LIB}\n"
   "namespace.default.links = system\n"
   "namespace.default.links += vndk\n"
   // irregular whitespaces are added intentionally for testing purpose
@@ -77,11 +82,17 @@
   "namespace.system.permitted.paths = /system/${LIB}\n"
   "namespace.system.asan.search.paths = /data:/system/${LIB}\n"
   "namespace.system.asan.permitted.paths = /data:/system\n"
+  "namespace.system.hwasan.search.paths = /system/${LIB}/hwasan\n"
+  "namespace.system.hwasan.search.paths += /system/${LIB}\n"
+  "namespace.system.hwasan.permitted.paths = /system/${LIB}/hwasan\n"
+  "namespace.system.hwasan.permitted.paths += /system/${LIB}\n"
   "namespace.vndk.isolated = tr\n"
   "namespace.vndk.isolated += ue\n" // should be ignored and return as 'false'.
   "namespace.vndk.search.paths = /system/${LIB}/vndk\n"
   "namespace.vndk.asan.search.paths = /data\n"
   "namespace.vndk.asan.search.paths += /system/${LIB}/vndk\n"
+  "namespace.vndk.hwasan.search.paths = /system/${LIB}/vndk/hwasan\n"
+  "namespace.vndk.hwasan.search.paths += /system/${LIB}/vndk\n"
   "namespace.vndk.links = default\n"
   "namespace.vndk.link.default.allow_all_shared_libs = true\n"
   "namespace.vndk.link.vndk_in_system.allow_all_shared_libs = true\n"
@@ -107,26 +118,50 @@
   return resolved_paths;
 }
 
-static void run_linker_config_smoke_test(bool is_asan) {
-  const std::vector<std::string> kExpectedDefaultSearchPath =
-      resolve_paths(is_asan ? std::vector<std::string>({ "/data", "/vendor/lib" ARCH_SUFFIX }) :
-                              std::vector<std::string>({ "/vendor/lib" ARCH_SUFFIX }));
+enum class SmokeTestType {
+  None,
+  Asan,
+  Hwasan,
+};
 
-  const std::vector<std::string> kExpectedDefaultPermittedPath =
-      resolve_paths(is_asan ? std::vector<std::string>({ "/data", "/vendor" }) :
-                              std::vector<std::string>({ "/vendor/lib" ARCH_SUFFIX }));
+static void run_linker_config_smoke_test(SmokeTestType type) {
+  std::vector<std::string> expected_default_search_path;
+  std::vector<std::string> expected_default_permitted_path;
+  std::vector<std::string> expected_system_search_path;
+  std::vector<std::string> expected_system_permitted_path;
+  std::vector<std::string> expected_vndk_search_path;
 
-  const std::vector<std::string> kExpectedSystemSearchPath =
-      resolve_paths(is_asan ? std::vector<std::string>({ "/data", "/system/lib" ARCH_SUFFIX }) :
-                              std::vector<std::string>({ "/system/lib" ARCH_SUFFIX }));
+  switch (type) {
+    case SmokeTestType::None:
+      expected_default_search_path = { "/vendor/lib" ARCH_SUFFIX };
+      expected_default_permitted_path = { "/vendor/lib" ARCH_SUFFIX };
+      expected_system_search_path = { "/system/lib" ARCH_SUFFIX };
+      expected_system_permitted_path = { "/system/lib" ARCH_SUFFIX };
+      expected_vndk_search_path = { "/system/lib" ARCH_SUFFIX "/vndk" };
+      break;
+    case SmokeTestType::Asan:
+      expected_default_search_path = { "/data", "/vendor/lib" ARCH_SUFFIX };
+      expected_default_permitted_path = { "/data", "/vendor" };
+      expected_system_search_path = { "/data", "/system/lib" ARCH_SUFFIX };
+      expected_system_permitted_path = { "/data", "/system" };
+      expected_vndk_search_path = { "/data", "/system/lib" ARCH_SUFFIX "/vndk" };
+      break;
+    case SmokeTestType::Hwasan:
+      expected_default_search_path = { "/vendor/lib" ARCH_SUFFIX "/hwasan", "/vendor/lib" ARCH_SUFFIX };
+      expected_default_permitted_path = { "/vendor/lib" ARCH_SUFFIX "/hwasan", "/vendor/lib" ARCH_SUFFIX };
+      expected_system_search_path = { "/system/lib" ARCH_SUFFIX "/hwasan" , "/system/lib" ARCH_SUFFIX };
+      expected_system_permitted_path = { "/system/lib" ARCH_SUFFIX "/hwasan", "/system/lib" ARCH_SUFFIX };
+      expected_vndk_search_path = { "/system/lib" ARCH_SUFFIX "/vndk/hwasan", "/system/lib" ARCH_SUFFIX "/vndk" };
+      break;
+  }
 
-  const std::vector<std::string> kExpectedSystemPermittedPath =
-      resolve_paths(is_asan ? std::vector<std::string>({ "/data", "/system" }) :
-                              std::vector<std::string>({ "/system/lib" ARCH_SUFFIX }));
-
-  const std::vector<std::string> kExpectedVndkSearchPath =
-      resolve_paths(is_asan ? std::vector<std::string>({ "/data", "/system/lib" ARCH_SUFFIX "/vndk"}) :
-                              std::vector<std::string>({ "/system/lib" ARCH_SUFFIX "/vndk"}));
+  expected_default_search_path = resolve_paths(expected_default_search_path);
+  // expected_default_permitted_path is skipped on purpose, permitted paths
+  // do not get resolved in linker_config.cpp
+  expected_system_search_path = resolve_paths(expected_system_search_path);
+  // expected_system_permitted_path is skipped on purpose, permitted paths
+  // do not get resolved in linker_config.cpp
+  expected_vndk_search_path = resolve_paths(expected_vndk_search_path);
 
   TemporaryFile tmp_file;
   close(tmp_file.fd);
@@ -149,7 +184,8 @@
   std::string error_msg;
   ASSERT_TRUE(Config::read_binary_config(tmp_file.path,
                                          executable_path.c_str(),
-                                         is_asan,
+                                         type == SmokeTestType::Asan,
+                                         type == SmokeTestType::Hwasan,
                                          &config,
                                          &error_msg)) << error_msg;
   ASSERT_TRUE(config != nullptr);
@@ -162,8 +198,8 @@
 
   ASSERT_TRUE(default_ns_config->isolated());
   ASSERT_FALSE(default_ns_config->visible());
-  ASSERT_EQ(kExpectedDefaultSearchPath, default_ns_config->search_paths());
-  ASSERT_EQ(kExpectedDefaultPermittedPath, default_ns_config->permitted_paths());
+  ASSERT_EQ(expected_default_search_path, default_ns_config->search_paths());
+  ASSERT_EQ(expected_default_permitted_path, default_ns_config->permitted_paths());
 
   const auto& default_ns_links = default_ns_config->links();
   ASSERT_EQ(2U, default_ns_links.size());
@@ -202,14 +238,14 @@
 
   ASSERT_TRUE(ns_system->isolated());
   ASSERT_TRUE(ns_system->visible());
-  ASSERT_EQ(kExpectedSystemSearchPath, ns_system->search_paths());
-  ASSERT_EQ(kExpectedSystemPermittedPath, ns_system->permitted_paths());
+  ASSERT_EQ(expected_system_search_path, ns_system->search_paths());
+  ASSERT_EQ(expected_system_permitted_path, ns_system->permitted_paths());
 
   ASSERT_TRUE(ns_vndk != nullptr) << "vndk namespace was not found";
 
   ASSERT_FALSE(ns_vndk->isolated()); // malformed bool property
   ASSERT_FALSE(ns_vndk->visible()); // undefined bool property
-  ASSERT_EQ(kExpectedVndkSearchPath, ns_vndk->search_paths());
+  ASSERT_EQ(expected_vndk_search_path, ns_vndk->search_paths());
 
   const auto& ns_vndk_links = ns_vndk->links();
   ASSERT_EQ(1U, ns_vndk_links.size());
@@ -223,11 +259,15 @@
 }
 
 TEST(linker_config, smoke) {
-  run_linker_config_smoke_test(false);
+  run_linker_config_smoke_test(SmokeTestType::None);
 }
 
 TEST(linker_config, asan_smoke) {
-  run_linker_config_smoke_test(true);
+  run_linker_config_smoke_test(SmokeTestType::Asan);
+}
+
+TEST(linker_config, hwasan_smoke) {
+  run_linker_config_smoke_test(SmokeTestType::Hwasan);
 }
 
 TEST(linker_config, ns_link_shared_libs_invalid_settings) {
@@ -259,6 +299,7 @@
   ASSERT_FALSE(Config::read_binary_config(tmp_file.path,
                                           executable_path.c_str(),
                                           false,
+                                          false,
                                           &config,
                                           &error_msg));
   ASSERT_TRUE(config == nullptr);
@@ -304,6 +345,7 @@
   ASSERT_TRUE(Config::read_binary_config(tmp_file.path,
                                          executable_path.c_str(),
                                          false,
+                                         false,
                                          &config,
                                          &error_msg)) << error_msg;
 
diff --git a/linker/linker_main.cpp b/linker/linker_main.cpp
index 833157e..26e2228 100644
--- a/linker/linker_main.cpp
+++ b/linker/linker_main.cpp
@@ -43,7 +43,6 @@
 #include "linker_tls.h"
 #include "linker_utils.h"
 
-#include "private/bionic_auxv.h"
 #include "private/bionic_call_ifunc_resolver.h"
 #include "private/bionic_globals.h"
 #include "private/bionic_tls.h"
diff --git a/tests/Android.bp b/tests/Android.bp
index 8c6057f..281e29d 100644
--- a/tests/Android.bp
+++ b/tests/Android.bp
@@ -66,18 +66,20 @@
         "libcutils_headers",
         "gwp_asan_headers"
     ],
-    // Ensure that the tests exercise shadow call stack support and
-    // the hint space PAC/BTI instructions.
+    stl: "libc++",
+
+    // Ensure that the tests exercise shadow call stack support.
+    // We don't use `scs: true` here because that would give us a second
+    // variant of this library where we actually just want to say "this
+    // library should always be built this way".
     arch: {
         arm64: {
-            cflags: [
-                "-fsanitize=shadow-call-stack",
-                // Disable this option for now: see b/151372823
-                //"-mbranch-protection=standard",
-            ],
+            cflags: ["-fsanitize=shadow-call-stack"],
+        },
+        riscv64: {
+            cflags: ["-fsanitize=shadow-call-stack"],
         },
     },
-    stl: "libc++",
     sanitize: {
         address: false,
     },
@@ -501,6 +503,7 @@
         "sys_vfs_test.cpp",
         "sys_wait_test.cpp",
         "sys_xattr_test.cpp",
+        "syslog_test.cpp",
         "system_properties_test.cpp",
         "system_properties_test2.cpp",
         "termios_test.cpp",
@@ -512,6 +515,7 @@
         "unistd_test.cpp",
         "utils.cpp",
         "utmp_test.cpp",
+        "utmpx_test.cpp",
         "wchar_test.cpp",
         "wctype_test.cpp",
     ],
@@ -538,6 +542,10 @@
 
                 // unsupported relocation type 37
                 "ifunc_test.cpp",
+
+                // musl #defines utmp to utmpx, causing a collision with
+                // utmpx_test.cpp
+                "utmp_test.cpp",
             ],
         },
     },
@@ -1109,6 +1117,30 @@
 }
 
 cc_test {
+    name: "hwasan_test",
+    enabled: false,
+    // This does not use bionic_tests_defaults because it is not supported on
+    // host.
+    arch: {
+        arm64: {
+            enabled: true,
+        },
+    },
+    sanitize: {
+        hwaddress: true,
+    },
+    srcs: [
+        "hwasan_test.cpp",
+    ],
+    shared_libs: [
+        "libbase",
+    ],
+    data_libs: ["libtest_simple_hwasan", "libtest_simple_hwasan_nohwasan"],
+    header_libs: ["bionic_libc_platform_headers"],
+    test_suites: ["device-tests"],
+}
+
+cc_test {
     name: "bionic-stress-tests",
     defaults: [
         "bionic_tests_defaults",
diff --git a/tests/NOTICE b/tests/NOTICE
index 167f90b..cc99d20 100644
--- a/tests/NOTICE
+++ b/tests/NOTICE
@@ -426,3 +426,31 @@
 
 -------------------------------------------------------------------
 
+Copyright (C) 2023 The Android Open Source Project
+All rights reserved.
+
+Redistribution and use in source and binary forms, with or without
+modification, are permitted provided that the following conditions
+are met:
+ * Redistributions of source code must retain the above copyright
+   notice, this list of conditions and the following disclaimer.
+ * Redistributions in binary form must reproduce the above copyright
+   notice, this list of conditions and the following disclaimer in
+   the documentation and/or other materials provided with the
+   distribution.
+
+THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+SUCH DAMAGE.
+
+-------------------------------------------------------------------
+
diff --git a/tests/async_safe_test.cpp b/tests/async_safe_test.cpp
index f52387e..dc4db07 100644
--- a/tests/async_safe_test.cpp
+++ b/tests/async_safe_test.cpp
@@ -16,6 +16,8 @@
 
 #include <gtest/gtest.h>
 
+#include <errno.h>
+
 #if defined(__BIONIC__)
 #include <async_safe/log.h>
 #endif // __BIONIC__
@@ -227,3 +229,19 @@
   GTEST_SKIP() << "bionic-only test";
 #endif // __BIONIC__
 }
+
+// Verify that using %m is never cut off.
+TEST(async_safe_format_buffer, percent_m_fits_in_buffer) {
+#if defined(__BIONIC__)
+  for (int i = 0; i < 256; i++) {
+    errno = i;
+    char async_buf[256];
+    async_safe_format_buffer(async_buf, sizeof(async_buf), "%m");
+    char strerror_buf[1024];
+    strerror_r(errno, strerror_buf, sizeof(strerror_buf));
+    ASSERT_STREQ(strerror_buf, async_buf);
+  }
+#else   // __BIONIC__
+  GTEST_SKIP() << "bionic-only test";
+#endif  // __BIONIC__
+}
diff --git a/tests/dlfcn_test.cpp b/tests/dlfcn_test.cpp
index 3f70279..b68ee7b 100644
--- a/tests/dlfcn_test.cpp
+++ b/tests/dlfcn_test.cpp
@@ -971,9 +971,15 @@
 }
 
 #define ALTERNATE_PATH_TO_SYSTEM_LIB "/system/lib64/" ABI_STRING "/"
+#if __has_feature(hwaddress_sanitizer)
+#define PATH_TO_LIBC PATH_TO_SYSTEM_LIB "hwasan/libc.so"
+#define PATH_TO_BOOTSTRAP_LIBC PATH_TO_SYSTEM_LIB "bootstrap/hwasan/libc.so"
+#define ALTERNATE_PATH_TO_LIBC ALTERNATE_PATH_TO_SYSTEM_LIB "hwasan/libc.so"
+#else
 #define PATH_TO_LIBC PATH_TO_SYSTEM_LIB "libc.so"
 #define PATH_TO_BOOTSTRAP_LIBC PATH_TO_SYSTEM_LIB "bootstrap/libc.so"
 #define ALTERNATE_PATH_TO_LIBC ALTERNATE_PATH_TO_SYSTEM_LIB "libc.so"
+#endif
 
 TEST(dlfcn, dladdr_libc) {
 #if defined(__GLIBC__)
@@ -981,24 +987,25 @@
 #endif
 
   Dl_info info;
-  void* addr = reinterpret_cast<void*>(puts); // well-known libc function
+  void* addr = reinterpret_cast<void*>(puts);  // An arbitrary libc function.
   ASSERT_TRUE(dladdr(addr, &info) != 0);
 
-  char libc_realpath[PATH_MAX];
-
   // Check if libc is in canonical path or in alternate path.
+  const char* expected_path;
   if (strncmp(ALTERNATE_PATH_TO_SYSTEM_LIB,
               info.dli_fname,
               sizeof(ALTERNATE_PATH_TO_SYSTEM_LIB) - 1) == 0) {
     // Platform with emulated architecture.  Symlink on ARC++.
-    ASSERT_TRUE(realpath(ALTERNATE_PATH_TO_LIBC, libc_realpath) == libc_realpath);
+    expected_path = ALTERNATE_PATH_TO_LIBC;
   } else if (strncmp(PATH_TO_BOOTSTRAP_LIBC, info.dli_fname,
                      sizeof(PATH_TO_BOOTSTRAP_LIBC) - 1) == 0) {
-    ASSERT_TRUE(realpath(PATH_TO_BOOTSTRAP_LIBC, libc_realpath) == libc_realpath);
+    expected_path = PATH_TO_BOOTSTRAP_LIBC;
   } else {
     // /system/lib is symlink when this test is executed on host.
-    ASSERT_TRUE(realpath(PATH_TO_LIBC, libc_realpath) == libc_realpath);
+    expected_path = PATH_TO_LIBC;
   }
+  char libc_realpath[PATH_MAX];
+  ASSERT_TRUE(realpath(expected_path, libc_realpath) != nullptr) << strerror(errno);
 
   ASSERT_STREQ(libc_realpath, info.dli_fname);
   // TODO: add check for dfi_fbase
diff --git a/tests/fortify_test.cpp b/tests/fortify_test.cpp
index 4abee67..cc3080d 100644
--- a/tests/fortify_test.cpp
+++ b/tests/fortify_test.cpp
@@ -670,6 +670,10 @@
   ASSERT_FORTIFY(readlinkat(AT_FDCWD, "/dev/null", buf, ct));
 }
 
+TEST(TEST_NAME, snprintf_nullptr_valid) {
+  ASSERT_EQ(10, snprintf(nullptr, 0, "0123456789"));
+}
+
 extern "C" char* __strncat_chk(char*, const char*, size_t, size_t);
 extern "C" char* __strcat_chk(char*, const char*, size_t);
 
diff --git a/tests/gwp_asan_test.cpp b/tests/gwp_asan_test.cpp
index 8b12bec..c31f48c 100644
--- a/tests/gwp_asan_test.cpp
+++ b/tests/gwp_asan_test.cpp
@@ -143,6 +143,16 @@
   EXPECT_DEATH({ *x = 7; }, "");
 }
 
+// A weaker version of the above tests, only checking that GWP-ASan is enabled
+// for any pointer, not *our* pointer. This allows us to test the system_default
+// sysprops without potentially OOM-ing other random processes:
+// b/273904016#comment5
+TEST(gwp_asan_integration, DISABLED_assert_gwp_asan_enabled_weaker) {
+  std::string maps;
+  EXPECT_TRUE(android::base::ReadFileToString("/proc/self/maps", &maps));
+  EXPECT_TRUE(maps.find("GWP-ASan") != std::string::npos) << maps;
+}
+
 TEST(gwp_asan_integration, DISABLED_assert_gwp_asan_disabled) {
   std::string maps;
   EXPECT_TRUE(android::base::ReadFileToString("/proc/self/maps", &maps));
@@ -184,32 +194,6 @@
   RunSubtestNoEnv("gwp_asan_integration.DISABLED_assert_gwp_asan_enabled");
 }
 
-TEST(gwp_asan_integration, sysprops_system) {
-  // Do not override HWASan with GWP ASan.
-  SKIP_WITH_HWASAN;
-
-  SyspropRestorer restorer;
-
-  __system_property_set("libc.debug.gwp_asan.sample_rate.system_default", "1");
-  __system_property_set("libc.debug.gwp_asan.process_sampling.system_default", "1");
-  __system_property_set("libc.debug.gwp_asan.max_allocs.system_default", "40000");
-
-  RunSubtestNoEnv("gwp_asan_integration.DISABLED_assert_gwp_asan_enabled");
-}
-
-TEST(gwp_asan_integration, sysprops_persist_system) {
-  // Do not override HWASan with GWP ASan.
-  SKIP_WITH_HWASAN;
-
-  SyspropRestorer restorer;
-
-  __system_property_set("persist.libc.debug.gwp_asan.sample_rate.system_default", "1");
-  __system_property_set("persist.libc.debug.gwp_asan.process_sampling.system_default", "1");
-  __system_property_set("persist.libc.debug.gwp_asan.max_allocs.system_default", "40000");
-
-  RunSubtestNoEnv("gwp_asan_integration.DISABLED_assert_gwp_asan_enabled");
-}
-
 TEST(gwp_asan_integration, sysprops_non_persist_overrides_persist) {
   // Do not override HWASan with GWP ASan.
   SKIP_WITH_HWASAN;
@@ -218,13 +202,18 @@
 
   __system_property_set("libc.debug.gwp_asan.sample_rate.system_default", "1");
   __system_property_set("libc.debug.gwp_asan.process_sampling.system_default", "1");
-  __system_property_set("libc.debug.gwp_asan.max_allocs.system_default", "40000");
+  // Note, any processes launched elsewhere on the system right now will have
+  // GWP-ASan enabled. Make sure that we only use a single slot, otherwise we
+  // could end up causing said badly-timed processes to use up to 163MiB extra
+  // penalty that 40,000 allocs would cause. See b/273904016#comment5 for more
+  // context.
+  __system_property_set("libc.debug.gwp_asan.max_allocs.system_default", "1");
 
   __system_property_set("persist.libc.debug.gwp_asan.sample_rate.system_default", "0");
   __system_property_set("persist.libc.debug.gwp_asan.process_sampling.system_default", "0");
   __system_property_set("persist.libc.debug.gwp_asan.max_allocs.system_default", "0");
 
-  RunSubtestNoEnv("gwp_asan_integration.DISABLED_assert_gwp_asan_enabled");
+  RunSubtestNoEnv("gwp_asan_integration.DISABLED_assert_gwp_asan_enabled_weaker");
 }
 
 TEST(gwp_asan_integration, sysprops_program_specific_overrides_default) {
diff --git a/tests/headers/posix/README.md b/tests/headers/posix/README.md
new file mode 100644
index 0000000..e7c171a
--- /dev/null
+++ b/tests/headers/posix/README.md
@@ -0,0 +1,8 @@
+# POSIX header tests
+
+These compile-time tests check that each POSIX header contains _at
+least_ what POSIX says. Every POSIX header file gets a corresponding
+`.c` file in this directory. Every constant, macro, type, struct field,
+and function in the header gets a corresponding assertion in the file.
+
+See `header_checks.h` for the implementation of the assertions.
diff --git a/tests/headers/posix/utmpx_h.c b/tests/headers/posix/utmpx_h.c
new file mode 100644
index 0000000..44dfac9
--- /dev/null
+++ b/tests/headers/posix/utmpx_h.c
@@ -0,0 +1,63 @@
+/*
+ * Copyright (C) 2023 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <utmpx.h>
+
+#include "header_checks.h"
+
+static void utmpx_h() {
+  TYPE(struct utmpx);
+  STRUCT_MEMBER_ARRAY(struct utmpx, char/*[]*/, ut_user);
+  STRUCT_MEMBER_ARRAY(struct utmpx, char/*[]*/, ut_id);
+  STRUCT_MEMBER_ARRAY(struct utmpx, char/*[]*/, ut_line);
+  STRUCT_MEMBER(struct utmpx, pid_t, ut_pid);
+  STRUCT_MEMBER(struct utmpx, short, ut_type);
+#if !defined(__GLIBC__)
+  // POSIX says struct timeval, but glibc has an anonymous struct.
+  STRUCT_MEMBER(struct utmpx, struct timeval, ut_tv);
+#endif
+
+  TYPE(pid_t);
+  TYPE(struct timeval);
+
+  MACRO(EMPTY);
+  MACRO(BOOT_TIME);
+  MACRO(OLD_TIME);
+  MACRO(NEW_TIME);
+  MACRO(USER_PROCESS);
+  MACRO(INIT_PROCESS);
+  MACRO(LOGIN_PROCESS);
+  MACRO(DEAD_PROCESS);
+
+  FUNCTION(endutxent, void (*f)(void));
+  FUNCTION(getutxent, struct utmpx* (*f)(void));
+  FUNCTION(getutxid, struct utmpx* (*f)(const struct utmpx*));
+  FUNCTION(getutxline, struct utmpx* (*f)(const struct utmpx*));
+  FUNCTION(pututxline, struct utmpx* (*f)(const struct utmpx*));
+  FUNCTION(setutxent, void (*f)(void));
+}
diff --git a/tests/heap_tagging_level_test.cpp b/tests/heap_tagging_level_test.cpp
index ae678b7..917be37 100644
--- a/tests/heap_tagging_level_test.cpp
+++ b/tests/heap_tagging_level_test.cpp
@@ -26,6 +26,7 @@
 
 #include "SignalUtils.h"
 
+#include <android-base/properties.h>
 #include <android-base/test_utils.h>
 #include <bionic/malloc_tagged_pointers.h>
 
@@ -223,6 +224,9 @@
 TEST_P(MemtagNoteTest, SEGV) {
 #if defined(__BIONIC__) && defined(__aarch64__)
   SKIP_WITH_NATIVE_BRIDGE;  // http://b/242170715
+  if (android::base::GetProperty("persist.arm64.memtag.default", "") != "") {
+    GTEST_SKIP() << "not supported when overriding memtag mode with property";
+  }
   // Note that we do not check running_with_hwasan() - what matters here is whether the test binary
   // itself is built with HWASan.
   bool withHWASAN = __has_feature(hwaddress_sanitizer);
diff --git a/tests/hwasan_test.cpp b/tests/hwasan_test.cpp
new file mode 100644
index 0000000..e32534e
--- /dev/null
+++ b/tests/hwasan_test.cpp
@@ -0,0 +1,79 @@
+/*
+ * Copyright (C) 2023 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <dlfcn.h>
+#include <stdlib.h>
+
+#include <gtest/gtest.h>
+
+#include <android-base/silent_death_test.h>
+#include <android-base/test_utils.h>
+
+using HwasanDeathTest = SilentDeathTest;
+
+TEST_F(HwasanDeathTest, UseAfterFree) {
+  EXPECT_DEATH(
+      {
+        void* m = malloc(1);
+        volatile char* x = const_cast<volatile char*>(reinterpret_cast<char*>(m));
+        *x = 1;
+        free(m);
+        *x = 2;
+      },
+      "use-after-free");
+}
+
+TEST_F(HwasanDeathTest, OutOfBounds) {
+  EXPECT_DEATH(
+      {
+        void* m = malloc(1);
+        volatile char* x = const_cast<volatile char*>(reinterpret_cast<char*>(m));
+        x[1] = 1;
+      },
+      "buffer-overflow");
+}
+
+// Check whether dlopen of /foo/bar.so checks /foo/hwasan/bar.so first.
+TEST(HwasanTest, DlopenAbsolutePath) {
+  std::string path = android::base::GetExecutableDirectory() + "/libtest_simple_hwasan.so";
+  ASSERT_EQ(0, access(path.c_str(), F_OK));  // Verify test setup.
+  std::string hwasan_path =
+      android::base::GetExecutableDirectory() + "/hwasan/libtest_simple_hwasan.so";
+  ASSERT_EQ(0, access(hwasan_path.c_str(), F_OK));  // Verify test setup.
+
+  void* handle = dlopen(path.c_str(), RTLD_NOW);
+  ASSERT_TRUE(handle != nullptr);
+  uint32_t* compiled_with_hwasan =
+      reinterpret_cast<uint32_t*>(dlsym(handle, "dlopen_testlib_compiled_with_hwasan"));
+  EXPECT_TRUE(*compiled_with_hwasan);
+  dlclose(handle);
+}
+
+TEST(HwasanTest, IsRunningWithHWasan) {
+  EXPECT_TRUE(running_with_hwasan());
+}
diff --git a/tests/libs/Android.bp b/tests/libs/Android.bp
index 8ae2257..a2fbe55 100644
--- a/tests/libs/Android.bp
+++ b/tests/libs/Android.bp
@@ -243,6 +243,38 @@
 }
 
 // -----------------------------------------------------------------------------
+// Libraries used by hwasan_test
+// -----------------------------------------------------------------------------
+cc_test_library {
+    name: "libtest_simple_hwasan",
+    arch: {
+        arm64: {
+            enabled: true,
+        },
+    },
+    sanitize: {
+        hwaddress: true,
+    },
+    relative_install_path: "hwasan",
+    enabled: false,
+    srcs: ["dlopen_testlib_simple_hwasan.cpp"],
+}
+
+cc_test_library {
+    // A weird name. This is the vanilla (non-HWASan) copy of the library that
+    // is used for the hwasan test.
+    name: "libtest_simple_hwasan_nohwasan",
+    arch: {
+        arm64: {
+            enabled: true,
+        },
+    },
+    stem: "libtest_simple_hwasan",
+    enabled: false,
+    srcs: ["dlopen_testlib_simple_hwasan.cpp"],
+}
+
+// -----------------------------------------------------------------------------
 // Library used by dlext direct unload on the namespace boundary tests
 // -----------------------------------------------------------------------------
 cc_test_library {
diff --git a/libc/bionic/timespec_get.cpp b/tests/libs/dlopen_testlib_simple_hwasan.cpp
similarity index 79%
copy from libc/bionic/timespec_get.cpp
copy to tests/libs/dlopen_testlib_simple_hwasan.cpp
index 7fc2182..ddf8a31 100644
--- a/libc/bionic/timespec_get.cpp
+++ b/tests/libs/dlopen_testlib_simple_hwasan.cpp
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018 The Android Open Source Project
+ * Copyright (C) 2023 The Android Open Source Project
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -26,8 +26,14 @@
  * SUCH DAMAGE.
  */
 
-#include <time.h>
+#include <stdint.h>
 
-int timespec_get(timespec* ts, int base) {
-  return (base == TIME_UTC && clock_gettime(CLOCK_REALTIME, ts) != -1) ? base : 0;
+#if __has_feature(hwaddress_sanitizer)
+extern "C" uint32_t dlopen_testlib_compiled_with_hwasan = true;
+#else
+extern "C" uint32_t dlopen_testlib_compiled_with_hwasan = false;
+#endif
+
+extern "C" bool dlopen_testlib_simple_hwasan_func() {
+  return true;
 }
diff --git a/tests/malloc_test.cpp b/tests/malloc_test.cpp
index 63ad99d..22905f4 100644
--- a/tests/malloc_test.cpp
+++ b/tests/malloc_test.cpp
@@ -36,7 +36,10 @@
 #include <algorithm>
 #include <atomic>
 #include <functional>
+#include <string>
 #include <thread>
+#include <unordered_map>
+#include <utility>
 #include <vector>
 
 #include <tinyxml2.h>
@@ -695,6 +698,44 @@
 #endif
 }
 
+TEST(malloc, mallopt_purge_all) {
+#if defined(__BIONIC__)
+  SKIP_WITH_HWASAN << "hwasan does not implement mallopt";
+  errno = 0;
+  ASSERT_EQ(1, mallopt(M_PURGE_ALL, 0));
+#else
+  GTEST_SKIP() << "bionic-only test";
+#endif
+}
+
+// Verify that all of the mallopt values are unique.
+TEST(malloc, mallopt_unique_params) {
+#if defined(__BIONIC__)
+  std::vector<std::pair<int, std::string>> params{
+      std::make_pair(M_DECAY_TIME, "M_DECAY_TIME"),
+      std::make_pair(M_PURGE, "M_PURGE"),
+      std::make_pair(M_PURGE_ALL, "M_PURGE_ALL"),
+      std::make_pair(M_MEMTAG_TUNING, "M_MEMTAG_TUNING"),
+      std::make_pair(M_THREAD_DISABLE_MEM_INIT, "M_THREAD_DISABLE_MEM_INIT"),
+      std::make_pair(M_CACHE_COUNT_MAX, "M_CACHE_COUNT_MAX"),
+      std::make_pair(M_CACHE_SIZE_MAX, "M_CACHE_SIZE_MAX"),
+      std::make_pair(M_TSDS_COUNT_MAX, "M_TSDS_COUNT_MAX"),
+      std::make_pair(M_BIONIC_ZERO_INIT, "M_BIONIC_ZERO_INIT"),
+      std::make_pair(M_BIONIC_SET_HEAP_TAGGING_LEVEL, "M_BIONIC_SET_HEAP_TAGGING_LEVEL"),
+  };
+
+  std::unordered_map<int, std::string> all_params;
+  for (const auto& param : params) {
+    EXPECT_TRUE(all_params.count(param.first) == 0)
+        << "mallopt params " << all_params[param.first] << " and " << param.second
+        << " have the same value " << param.first;
+    all_params.insert(param);
+  }
+#else
+  GTEST_SKIP() << "bionic-only test";
+#endif
+}
+
 #if defined(__BIONIC__)
 static void GetAllocatorVersion(bool* allocator_scudo) {
   TemporaryFile tf;
@@ -1572,6 +1613,7 @@
 }
 
 // Verify that small and medium allocations are always zero.
+// @CddTest = 9.7/C-4-1
 TEST(malloc, zeroed_allocations_small_medium_sizes) {
 #if !defined(__BIONIC__)
   GTEST_SKIP() << "Only valid on bionic";
@@ -1601,6 +1643,7 @@
 }
 
 // Verify that large allocations are always zero.
+// @CddTest = 9.7/C-4-1
 TEST(malloc, zeroed_allocations_large_sizes) {
 #if !defined(__BIONIC__)
   GTEST_SKIP() << "Only valid on bionic";
@@ -1629,6 +1672,8 @@
       "posix_memalign", test_sizes, kMaxAllocations);
 }
 
+// Verify that reallocs are zeroed when expanded.
+// @CddTest = 9.7/C-4-1
 TEST(malloc, zeroed_allocations_realloc) {
 #if !defined(__BIONIC__)
   GTEST_SKIP() << "Only valid on bionic";
diff --git a/tests/pthread_test.cpp b/tests/pthread_test.cpp
index 06a0f3d..aad2a4d 100644
--- a/tests/pthread_test.cpp
+++ b/tests/pthread_test.cpp
@@ -195,12 +195,12 @@
   SKIP_WITH_HWASAN; // TODO(b/148982147): Re-enable when fixed.
 
   size_t stack_size = 640 * 1024;
-  std::vector<char> stack_vec(stack_size, '\xff');
-  void* stack = stack_vec.data();
+  std::unique_ptr<char[]> stack(new (std::align_val_t(getpagesize())) char[stack_size]);
+  memset(stack.get(), '\xff', stack_size);
 
   pthread_attr_t attr;
   ASSERT_EQ(0, pthread_attr_init(&attr));
-  ASSERT_EQ(0, pthread_attr_setstack(&attr, stack, stack_size));
+  ASSERT_EQ(0, pthread_attr_setstack(&attr, stack.get(), stack_size));
 
   pthread_t t;
   ASSERT_EQ(0, pthread_create(&t, &attr, FnWithStackFrame, nullptr));
diff --git a/tests/sched_test.cpp b/tests/sched_test.cpp
index 03e8062..fa1a07f 100644
--- a/tests/sched_test.cpp
+++ b/tests/sched_test.cpp
@@ -303,5 +303,8 @@
 }
 
 TEST(sched, sched_getaffinity_failure) {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
   ASSERT_EQ(-1, sched_getaffinity(getpid(), 0, nullptr));
+#pragma clang diagnostic pop
 }
diff --git a/tests/scs_test.cpp b/tests/scs_test.cpp
index 24cb347..0776a43 100644
--- a/tests/scs_test.cpp
+++ b/tests/scs_test.cpp
@@ -14,8 +14,6 @@
  * limitations under the License.
  */
 
-#if __has_feature(shadow_call_stack)
-
 #include <gtest/gtest.h>
 
 #include "private/bionic_constants.h"
@@ -33,7 +31,9 @@
 }
 
 TEST(scs_test, stack_overflow) {
+#if defined(__aarch64__) || defined(__riscv)
   ASSERT_EXIT(recurse1(SCS_SIZE), testing::KilledBySignal(SIGSEGV), "");
-}
-
+#else
+  GTEST_SKIP() << "no SCS on this architecture";
 #endif
+}
diff --git a/tests/semaphore_test.cpp b/tests/semaphore_test.cpp
index f3f6020..6f8797f 100644
--- a/tests/semaphore_test.cpp
+++ b/tests/semaphore_test.cpp
@@ -165,8 +165,10 @@
 TEST_F(semaphore_DeathTest, sem_timedwait_null_timeout) {
   sem_t s;
   ASSERT_EQ(0, sem_init(&s, 0, 0));
-
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
   ASSERT_EXIT(sem_timedwait(&s, nullptr), testing::KilledBySignal(SIGSEGV), "");
+#pragma clang diagnostic pop
 }
 
 TEST(semaphore, sem_getvalue) {
diff --git a/tests/setjmp_test.cpp b/tests/setjmp_test.cpp
index 2f891ec..6ae8bfd 100644
--- a/tests/setjmp_test.cpp
+++ b/tests/setjmp_test.cpp
@@ -278,7 +278,6 @@
 }
 
 TEST(setjmp, bug_152210274) {
-  SKIP_WITH_HWASAN; // b/227390656
   // Ensure that we never have a mangled value in the stack pointer.
 #if defined(__BIONIC__)
   struct sigaction sa = {.sa_flags = SA_SIGINFO, .sa_sigaction = [](int, siginfo_t*, void*) {}};
@@ -299,15 +298,19 @@
         perror("setjmp");
         abort();
       }
-      if (*static_cast<pid_t*>(arg) == 100) longjmp(buf, 1);
+      // This will never be true, but the compiler doesn't know that, so the
+      // setjmp won't be removed by DCE. With HWASan/MTE this also acts as a
+      // kind of enforcement that the threads are done before leaving the test.
+      if (*static_cast<size_t*>(arg) != 123) longjmp(buf, 1);
     }
     return nullptr;
   };
+  pthread_t threads[kNumThreads];
   pid_t tids[kNumThreads] = {};
+  size_t var = 123;
   for (size_t i = 0; i < kNumThreads; ++i) {
-    pthread_t t;
-    ASSERT_EQ(0, pthread_create(&t, nullptr, jumper, &tids[i]));
-    tids[i] = pthread_gettid_np(t);
+    ASSERT_EQ(0, pthread_create(&threads[i], nullptr, jumper, &var));
+    tids[i] = pthread_gettid_np(threads[i]);
   }
 
   // Start the interrupter thread.
@@ -327,6 +330,9 @@
   pthread_t t;
   ASSERT_EQ(0, pthread_create(&t, nullptr, interrupter, tids));
   pthread_join(t, nullptr);
+  for (size_t i = 0; i < kNumThreads; i++) {
+    pthread_join(threads[i], nullptr);
+  }
 #else
   GTEST_SKIP() << "tests uses functions not in glibc";
 #endif
diff --git a/tests/spawn_test.cpp b/tests/spawn_test.cpp
index a9563b8..ab3e877 100644
--- a/tests/spawn_test.cpp
+++ b/tests/spawn_test.cpp
@@ -232,18 +232,28 @@
 }
 
 TEST(spawn, posix_spawn_file_actions) {
+#if !defined(__GLIBC__)
   int fds[2];
   ASSERT_NE(-1, pipe(fds));
 
   posix_spawn_file_actions_t fa;
   ASSERT_EQ(0, posix_spawn_file_actions_init(&fa));
 
+  // Test addclose and adddup2 by redirecting output to the pipe created above.
   ASSERT_EQ(0, posix_spawn_file_actions_addclose(&fa, fds[0]));
   ASSERT_EQ(0, posix_spawn_file_actions_adddup2(&fa, fds[1], 1));
   ASSERT_EQ(0, posix_spawn_file_actions_addclose(&fa, fds[1]));
   // Check that close(2) failures are ignored by closing the same fd again.
   ASSERT_EQ(0, posix_spawn_file_actions_addclose(&fa, fds[1]));
+  // Open a file directly, to test addopen.
   ASSERT_EQ(0, posix_spawn_file_actions_addopen(&fa, 56, "/proc/version", O_RDONLY, 0));
+  // Test addfchdir by opening the same file a second way...
+  ASSERT_EQ(0, posix_spawn_file_actions_addopen(&fa, 57, "/proc", O_PATH, 0));
+  ASSERT_EQ(0, posix_spawn_file_actions_addfchdir_np(&fa, 57));
+  ASSERT_EQ(0, posix_spawn_file_actions_addopen(&fa, 58, "version", O_RDONLY, 0));
+  // Test addchdir by opening the same file a third way...
+  ASSERT_EQ(0, posix_spawn_file_actions_addchdir_np(&fa, "/"));
+  ASSERT_EQ(0, posix_spawn_file_actions_addopen(&fa, 59, "proc/version", O_RDONLY, 0));
 
   ExecTestHelper eth;
   eth.SetArgs({"ls", "-l", "/proc/self/fd", nullptr});
@@ -259,12 +269,21 @@
   AssertChildExited(pid, 0);
 
   // We'll know the dup2 worked if we see any ls(1) output in our pipe.
-  // The open we can check manually...
+  // The opens we can check manually (and they implicitly check the chdirs)...
   bool open_to_fd_56_worked = false;
+  bool open_to_fd_58_worked = false;
+  bool open_to_fd_59_worked = false;
   for (const auto& line : android::base::Split(content, "\n")) {
     if (line.find(" 56 -> /proc/version") != std::string::npos) open_to_fd_56_worked = true;
+    if (line.find(" 58 -> /proc/version") != std::string::npos) open_to_fd_58_worked = true;
+    if (line.find(" 59 -> /proc/version") != std::string::npos) open_to_fd_59_worked = true;
   }
-  ASSERT_TRUE(open_to_fd_56_worked);
+  ASSERT_TRUE(open_to_fd_56_worked) << content;
+  ASSERT_TRUE(open_to_fd_58_worked) << content;
+  ASSERT_TRUE(open_to_fd_59_worked) << content;
+#else
+  GTEST_SKIP() << "our old glibc doesn't have the chdirs; newer versions and musl do.";
+#endif
 }
 
 static void CatFileToString(posix_spawnattr_t* sa, const char* path, std::string* content) {
diff --git a/tests/stdio_test.cpp b/tests/stdio_test.cpp
index fb6bce9..b85edfb 100644
--- a/tests/stdio_test.cpp
+++ b/tests/stdio_test.cpp
@@ -36,6 +36,7 @@
 
 #include <android-base/file.h>
 #include <android-base/silent_death_test.h>
+#include <android-base/strings.h>
 #include <android-base/test_utils.h>
 #include <android-base/unique_fd.h>
 
@@ -98,6 +99,27 @@
   ASSERT_EQ(nullptr, fgets(line, sizeof(line), fp)) << "junk at end of file: " << line;
 }
 
+#define EXPECT_SNPRINTF_N(expected, n, fmt, ...)                        \
+  {                                                                     \
+    char buf[BUFSIZ];                                                   \
+    int w = snprintf(buf, sizeof(buf), fmt __VA_OPT__(, ) __VA_ARGS__); \
+    EXPECT_EQ(n, w);                                                    \
+    EXPECT_STREQ(expected, buf);                                        \
+  }
+
+#define EXPECT_SNPRINTF(expected, fmt, ...) \
+  EXPECT_SNPRINTF_N(expected, static_cast<int>(strlen(expected)), fmt __VA_OPT__(, ) __VA_ARGS__)
+
+#define EXPECT_SWPRINTF_N(expected, n, fmt, ...)                        \
+  {                                                                     \
+    wchar_t buf[BUFSIZ];                                                \
+    int w = swprintf(buf, sizeof(buf), fmt __VA_OPT__(, ) __VA_ARGS__); \
+    EXPECT_EQ(n, w);                                                    \
+    EXPECT_EQ(std::wstring(expected), std::wstring(buf, w));            \
+  }
+#define EXPECT_SWPRINTF(expected, fmt, ...) \
+  EXPECT_SWPRINTF_N(expected, static_cast<int>(wcslen(expected)), fmt __VA_OPT__(, ) __VA_ARGS__)
+
 TEST(STDIO_TEST, flockfile_18208568_stderr) {
   // Check that we have a _recursive_ mutex for flockfile.
   flockfile(stderr);
@@ -140,6 +162,22 @@
   fclose(fp);
 }
 
+TEST(STDIO_TEST, tmpfile_TMPDIR) {
+  TemporaryDir td;
+  setenv("TMPDIR", td.path, 1);
+
+  FILE* fp = tmpfile();
+  ASSERT_TRUE(fp != nullptr);
+
+  std::string fd_path = android::base::StringPrintf("/proc/self/fd/%d", fileno(fp));
+  char path[PATH_MAX];
+  ASSERT_GT(readlink(fd_path.c_str(), path, sizeof(path)), 0);
+  // $TMPDIR influenced where our temporary file ended up?
+  ASSERT_TRUE(android::base::StartsWith(path, td.path)) << path;
+  // And we used O_TMPFILE, right?
+  ASSERT_TRUE(android::base::EndsWith(path, " (deleted)")) << path;
+}
+
 TEST(STDIO_TEST, dprintf) {
   TemporaryFile tf;
 
@@ -292,21 +330,23 @@
   // error: format '%zd' expects argument of type 'signed size_t',
   //     but argument 4 has type 'ssize_t {aka long int}' [-Werror=format]
   ssize_t v = 1;
-  char buf[32];
-  snprintf(buf, sizeof(buf), "%zd", v);
+  EXPECT_SNPRINTF("1", "%zd", v);
+  EXPECT_SWPRINTF(L"1", L"%zd", v);
 }
 
 // https://code.google.com/p/android/issues/detail?id=64886
 TEST(STDIO_TEST, snprintf_a) {
-  char buf[BUFSIZ];
-  EXPECT_EQ(23, snprintf(buf, sizeof(buf), "<%a>", 9990.235));
-  EXPECT_STREQ("<0x1.3831e147ae148p+13>", buf);
+  EXPECT_SNPRINTF("<0x1.3831e147ae148p+13>", "<%a>", 9990.235);
+}
+
+// https://code.google.com/p/android/issues/detail?id=64886
+TEST(STDIO_TEST, swprintf_a) {
+  EXPECT_SWPRINTF(L"<0x1.3831e147ae148p+13>", L"<%a>", 9990.235);
 }
 
 // http://b/152588929
 TEST(STDIO_TEST, snprintf_La) {
 #if defined(__LP64__)
-  char buf[BUFSIZ];
   union {
     uint64_t a[2];
     long double v;
@@ -314,59 +354,98 @@
 
   u.a[0] = UINT64_C(0x9b9b9b9b9b9b9b9b);
   u.a[1] = UINT64_C(0xdfdfdfdfdfdfdfdf);
-  EXPECT_EQ(41, snprintf(buf, sizeof(buf), "<%La>", u.v));
-  EXPECT_STREQ("<-0x1.dfdfdfdfdfdf9b9b9b9b9b9b9b9bp+8160>", buf);
+  EXPECT_SNPRINTF("<-0x1.dfdfdfdfdfdf9b9b9b9b9b9b9b9bp+8160>", "<%La>", u.v);
 
   u.a[0] = UINT64_C(0xffffffffffffffff);
   u.a[1] = UINT64_C(0x7ffeffffffffffff);
-  EXPECT_EQ(41, snprintf(buf, sizeof(buf), "<%La>", u.v));
-  EXPECT_STREQ("<0x1.ffffffffffffffffffffffffffffp+16383>", buf);
+  EXPECT_SNPRINTF("<0x1.ffffffffffffffffffffffffffffp+16383>", "<%La>", u.v);
 
   u.a[0] = UINT64_C(0x0000000000000000);
   u.a[1] = UINT64_C(0x0000000000000000);
-  EXPECT_EQ(8, snprintf(buf, sizeof(buf), "<%La>", u.v));
-  EXPECT_STREQ("<0x0p+0>", buf);
+  EXPECT_SNPRINTF("<0x0p+0>", "<%La>", u.v);
+#else
+  GTEST_SKIP() << "no ld128";
+#endif
+}
+
+// http://b/152588929
+TEST(STDIO_TEST, swprintf_La) {
+#if defined(__LP64__)
+  union {
+    uint64_t a[2];
+    long double v;
+  } u;
+
+  u.a[0] = UINT64_C(0x9b9b9b9b9b9b9b9b);
+  u.a[1] = UINT64_C(0xdfdfdfdfdfdfdfdf);
+  EXPECT_SWPRINTF(L"<-0x1.dfdfdfdfdfdf9b9b9b9b9b9b9b9bp+8160>", L"<%La>", u.v);
+
+  u.a[0] = UINT64_C(0xffffffffffffffff);
+  u.a[1] = UINT64_C(0x7ffeffffffffffff);
+  EXPECT_SWPRINTF(L"<0x1.ffffffffffffffffffffffffffffp+16383>", L"<%La>", u.v);
+
+  u.a[0] = UINT64_C(0x0000000000000000);
+  u.a[1] = UINT64_C(0x0000000000000000);
+  EXPECT_SWPRINTF(L"<0x0p+0>", L"<%La>", u.v);
 #else
   GTEST_SKIP() << "no ld128";
 #endif
 }
 
 TEST(STDIO_TEST, snprintf_lc) {
-  char buf[BUFSIZ];
   wint_t wc = L'a';
-  EXPECT_EQ(3, snprintf(buf, sizeof(buf), "<%lc>", wc));
-  EXPECT_STREQ("<a>", buf);
+  EXPECT_SNPRINTF("<a>", "<%lc>", wc);
 }
 
-TEST(STDIO_TEST, snprintf_C) { // Synonym for %lc.
-  char buf[BUFSIZ];
+TEST(STDIO_TEST, swprintf_lc) {
+  wint_t wc = L'a';
+  EXPECT_SWPRINTF(L"<a>", L"<%lc>", wc);
+}
+
+TEST(STDIO_TEST, snprintf_C) {  // Synonym for %lc.
   wchar_t wc = L'a';
-  EXPECT_EQ(3, snprintf(buf, sizeof(buf), "<%C>", wc));
-  EXPECT_STREQ("<a>", buf);
+  EXPECT_SNPRINTF("<a>", "<%C>", wc);
+}
+
+TEST(STDIO_TEST, swprintf_C) {  // Synonym for %lc.
+  wchar_t wc = L'a';
+  EXPECT_SWPRINTF(L"<a>", L"<%C>", wc);
+}
+
+TEST(STDIO_TEST, snprintf_ls_null) {
+  EXPECT_SNPRINTF("<(null)>", "<%ls>", static_cast<wchar_t*>(nullptr));
+}
+
+TEST(STDIO_TEST, swprintf_ls_null) {
+  EXPECT_SWPRINTF(L"<(null)>", L"<%ls>", static_cast<wchar_t*>(nullptr));
 }
 
 TEST(STDIO_TEST, snprintf_ls) {
-  char buf[BUFSIZ];
-  wchar_t* ws = nullptr;
-  EXPECT_EQ(8, snprintf(buf, sizeof(buf), "<%ls>", ws));
-  EXPECT_STREQ("<(null)>", buf);
+  static const wchar_t chars[] = L"Hello\u0666 World";
+  EXPECT_SNPRINTF("<Hello\xd9\xa6 World>", "<%ls>", chars);
+}
 
-  wchar_t chars[] = { L'h', L'i', 0 };
-  ws = chars;
-  EXPECT_EQ(4, snprintf(buf, sizeof(buf), "<%ls>", ws));
-  EXPECT_STREQ("<hi>", buf);
+TEST(STDIO_TEST, swprintf_ls) {
+  static const wchar_t chars[] = L"Hello\u0666 World";
+  EXPECT_SWPRINTF(L"<Hello\u0666 World>", L"<%ls>", chars);
+}
+
+TEST(STDIO_TEST, snprintf_S_nullptr) {  // Synonym for %ls.
+  EXPECT_SNPRINTF("<(null)>", "<%S>", static_cast<wchar_t*>(nullptr));
+}
+
+TEST(STDIO_TEST, swprintf_S_nullptr) {  // Synonym for %ls.
+  EXPECT_SWPRINTF(L"<(null)>", L"<%S>", static_cast<wchar_t*>(nullptr));
 }
 
 TEST(STDIO_TEST, snprintf_S) { // Synonym for %ls.
-  char buf[BUFSIZ];
-  wchar_t* ws = nullptr;
-  EXPECT_EQ(8, snprintf(buf, sizeof(buf), "<%S>", ws));
-  EXPECT_STREQ("<(null)>", buf);
+  static const wchar_t chars[] = L"Hello\u0666 World";
+  EXPECT_SNPRINTF("<Hello\xd9\xa6 World>", "<%S>", chars);
+}
 
-  wchar_t chars[] = { L'h', L'i', 0 };
-  ws = chars;
-  EXPECT_EQ(4, snprintf(buf, sizeof(buf), "<%S>", ws));
-  EXPECT_STREQ("<hi>", buf);
+TEST(STDIO_TEST, swprintf_S) {  // Synonym for %ls.
+  static const wchar_t chars[] = L"Hello\u0666 World";
+  EXPECT_SWPRINTF(L"<Hello\u0666 World>", L"<%S>", chars);
 }
 
 TEST_F(STDIO_DEATHTEST, snprintf_n) {
@@ -383,106 +462,111 @@
 #endif
 }
 
+TEST_F(STDIO_DEATHTEST, swprintf_n) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat"
+  // http://b/14492135 and http://b/31832608.
+  wchar_t buf[32];
+  int i = 1234;
+  EXPECT_DEATH(swprintf(buf, sizeof(buf), L"a %n b", &i), "%n not allowed on Android");
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "glibc does allow %n";
+#endif
+}
+
 TEST(STDIO_TEST, snprintf_measure) {
-  char buf[16];
+  char buf[1] = {'x'};
   ASSERT_EQ(11, snprintf(buf, 0, "Hello %s", "world"));
+  ASSERT_EQ('x', buf[0]);
+}
+
+// Unlike snprintf(), you *can't* use swprintf() to measure.
+TEST(STDIO_TEST, swprintf_measure) {
+  wchar_t buf[1] = {L'x'};
+  ASSERT_EQ(-1, swprintf(buf, 0, L"Hello %S", L"world"));
+  ASSERT_EQ(L'x', buf[0]);
 }
 
 TEST(STDIO_TEST, snprintf_smoke) {
-  char buf[BUFSIZ];
+  EXPECT_SNPRINTF("a", "a");
+  EXPECT_SNPRINTF("%", "%%");
+  EXPECT_SNPRINTF("01234", "01234");
+  EXPECT_SNPRINTF("a01234b", "a%sb", "01234");
 
-  snprintf(buf, sizeof(buf), "a");
-  EXPECT_STREQ("a", buf);
+  EXPECT_SNPRINTF("a(null)b", "a%sb", static_cast<char*>(nullptr));
+  EXPECT_SNPRINTF("aabbcc", "aa%scc", "bb");
+  EXPECT_SNPRINTF("abc", "a%cc", 'b');
+  EXPECT_SNPRINTF("a1234b", "a%db", 1234);
+  EXPECT_SNPRINTF("a-8123b", "a%db", -8123);
+  EXPECT_SNPRINTF("a16b", "a%hdb", static_cast<short>(0x7fff0010));
+  EXPECT_SNPRINTF("a16b", "a%hhdb", static_cast<char>(0x7fffff10));
+  EXPECT_SNPRINTF("a68719476736b", "a%lldb", 0x1000000000LL);
+  EXPECT_SNPRINTF("a70000b", "a%ldb", 70000L);
+  EXPECT_SNPRINTF("a0xb0001234b", "a%pb", reinterpret_cast<void*>(0xb0001234));
+  EXPECT_SNPRINTF("a12abz", "a%xz", 0x12ab);
+  EXPECT_SNPRINTF("a12ABz", "a%Xz", 0x12ab);
+  EXPECT_SNPRINTF("a00123456z", "a%08xz", 0x123456);
+  EXPECT_SNPRINTF("a 1234z", "a%5dz", 1234);
+  EXPECT_SNPRINTF("a01234z", "a%05dz", 1234);
+  EXPECT_SNPRINTF("a    1234z", "a%8dz", 1234);
+  EXPECT_SNPRINTF("a1234    z", "a%-8dz", 1234);
+  EXPECT_SNPRINTF("Aabcdef     Z", "A%-11sZ", "abcdef");
+  EXPECT_SNPRINTF("Ahello:1234Z", "A%s:%dZ", "hello", 1234);
+  EXPECT_SNPRINTF("a005:5:05z", "a%03d:%d:%02dz", 5, 5, 5);
 
-  snprintf(buf, sizeof(buf), "%%");
-  EXPECT_STREQ("%", buf);
-
-  snprintf(buf, sizeof(buf), "01234");
-  EXPECT_STREQ("01234", buf);
-
-  snprintf(buf, sizeof(buf), "a%sb", "01234");
-  EXPECT_STREQ("a01234b", buf);
-
-  char* s = nullptr;
-  snprintf(buf, sizeof(buf), "a%sb", s);
-  EXPECT_STREQ("a(null)b", buf);
-
-  snprintf(buf, sizeof(buf), "aa%scc", "bb");
-  EXPECT_STREQ("aabbcc", buf);
-
-  snprintf(buf, sizeof(buf), "a%cc", 'b');
-  EXPECT_STREQ("abc", buf);
-
-  snprintf(buf, sizeof(buf), "a%db", 1234);
-  EXPECT_STREQ("a1234b", buf);
-
-  snprintf(buf, sizeof(buf), "a%db", -8123);
-  EXPECT_STREQ("a-8123b", buf);
-
-  snprintf(buf, sizeof(buf), "a%hdb", static_cast<short>(0x7fff0010));
-  EXPECT_STREQ("a16b", buf);
-
-  snprintf(buf, sizeof(buf), "a%hhdb", static_cast<char>(0x7fffff10));
-  EXPECT_STREQ("a16b", buf);
-
-  snprintf(buf, sizeof(buf), "a%lldb", 0x1000000000LL);
-  EXPECT_STREQ("a68719476736b", buf);
-
-  snprintf(buf, sizeof(buf), "a%ldb", 70000L);
-  EXPECT_STREQ("a70000b", buf);
-
-  snprintf(buf, sizeof(buf), "a%pb", reinterpret_cast<void*>(0xb0001234));
-  EXPECT_STREQ("a0xb0001234b", buf);
-
-  snprintf(buf, sizeof(buf), "a%xz", 0x12ab);
-  EXPECT_STREQ("a12abz", buf);
-
-  snprintf(buf, sizeof(buf), "a%Xz", 0x12ab);
-  EXPECT_STREQ("a12ABz", buf);
-
-  snprintf(buf, sizeof(buf), "a%08xz", 0x123456);
-  EXPECT_STREQ("a00123456z", buf);
-
-  snprintf(buf, sizeof(buf), "a%5dz", 1234);
-  EXPECT_STREQ("a 1234z", buf);
-
-  snprintf(buf, sizeof(buf), "a%05dz", 1234);
-  EXPECT_STREQ("a01234z", buf);
-
-  snprintf(buf, sizeof(buf), "a%8dz", 1234);
-  EXPECT_STREQ("a    1234z", buf);
-
-  snprintf(buf, sizeof(buf), "a%-8dz", 1234);
-  EXPECT_STREQ("a1234    z", buf);
-
-  snprintf(buf, sizeof(buf), "A%-11sZ", "abcdef");
-  EXPECT_STREQ("Aabcdef     Z", buf);
-
-  snprintf(buf, sizeof(buf), "A%s:%dZ", "hello", 1234);
-  EXPECT_STREQ("Ahello:1234Z", buf);
-
-  snprintf(buf, sizeof(buf), "a%03d:%d:%02dz", 5, 5, 5);
-  EXPECT_STREQ("a005:5:05z", buf);
-
-  void* p = nullptr;
-  snprintf(buf, sizeof(buf), "a%d,%pz", 5, p);
 #if defined(__BIONIC__)
-  EXPECT_STREQ("a5,0x0z", buf);
+  EXPECT_SNPRINTF("a5,0x0z", "a%d,%pz", 5, static_cast<void*>(nullptr));
 #else // __BIONIC__
-  EXPECT_STREQ("a5,(nil)z", buf);
+  EXPECT_SNPRINTF("a5,(nil)z", "a%d,%pz", 5, static_cast<void*>(nullptr));
 #endif // __BIONIC__
 
-  snprintf(buf, sizeof(buf), "a%lld,%d,%d,%dz", 0x1000000000LL, 6, 7, 8);
-  EXPECT_STREQ("a68719476736,6,7,8z", buf);
+  EXPECT_SNPRINTF("a68719476736,6,7,8z", "a%lld,%d,%d,%dz", 0x1000000000LL, 6, 7, 8);
 
-  snprintf(buf, sizeof(buf), "a_%f_b", 1.23f);
-  EXPECT_STREQ("a_1.230000_b", buf);
+  EXPECT_SNPRINTF("a_1.230000_b", "a_%f_b", 1.23f);
+  EXPECT_SNPRINTF("a_3.14_b", "a_%g_b", 3.14);
+  EXPECT_SNPRINTF("print_me_twice print_me_twice", "%1$s %1$s", "print_me_twice");
+}
 
-  snprintf(buf, sizeof(buf), "a_%g_b", 3.14);
-  EXPECT_STREQ("a_3.14_b", buf);
+TEST(STDIO_TEST, swprintf_smoke) {
+  EXPECT_SWPRINTF(L"a", L"a");
+  EXPECT_SWPRINTF(L"%", L"%%");
+  EXPECT_SWPRINTF(L"01234", L"01234");
+  EXPECT_SWPRINTF(L"a01234b", L"a%sb", "01234");
 
-  snprintf(buf, sizeof(buf), "%1$s %1$s", "print_me_twice");
-  EXPECT_STREQ("print_me_twice print_me_twice", buf);
+  EXPECT_SWPRINTF(L"a(null)b", L"a%sb", static_cast<char*>(nullptr));
+  EXPECT_SWPRINTF(L"aabbcc", L"aa%scc", "bb");
+  EXPECT_SWPRINTF(L"abc", L"a%cc", 'b');
+  EXPECT_SWPRINTF(L"a1234b", L"a%db", 1234);
+  EXPECT_SWPRINTF(L"a-8123b", L"a%db", -8123);
+  EXPECT_SWPRINTF(L"a16b", L"a%hdb", static_cast<short>(0x7fff0010));
+  EXPECT_SWPRINTF(L"a16b", L"a%hhdb", static_cast<char>(0x7fffff10));
+  EXPECT_SWPRINTF(L"a68719476736b", L"a%lldb", 0x1000000000LL);
+  EXPECT_SWPRINTF(L"a70000b", L"a%ldb", 70000L);
+  EXPECT_SWPRINTF(L"a0xb0001234b", L"a%pb", reinterpret_cast<void*>(0xb0001234));
+  EXPECT_SWPRINTF(L"a12abz", L"a%xz", 0x12ab);
+  EXPECT_SWPRINTF(L"a12ABz", L"a%Xz", 0x12ab);
+  EXPECT_SWPRINTF(L"a00123456z", L"a%08xz", 0x123456);
+  EXPECT_SWPRINTF(L"a 1234z", L"a%5dz", 1234);
+  EXPECT_SWPRINTF(L"a01234z", L"a%05dz", 1234);
+  EXPECT_SWPRINTF(L"a    1234z", L"a%8dz", 1234);
+  EXPECT_SWPRINTF(L"a1234    z", L"a%-8dz", 1234);
+  EXPECT_SWPRINTF(L"Aabcdef     Z", L"A%-11sZ", "abcdef");
+  EXPECT_SWPRINTF(L"Ahello:1234Z", L"A%s:%dZ", "hello", 1234);
+  EXPECT_SWPRINTF(L"a005:5:05z", L"a%03d:%d:%02dz", 5, 5, 5);
+
+#if defined(__BIONIC__)
+  EXPECT_SWPRINTF(L"a5,0x0z", L"a%d,%pz", 5, static_cast<void*>(nullptr));
+#else   // __BIONIC__
+  EXPECT_SWPRINTF(L"a5,(nil)z", L"a%d,%pz", 5, static_cast<void*>(nullptr));
+#endif  // __BIONIC__
+
+  EXPECT_SWPRINTF(L"a68719476736,6,7,8z", L"a%lld,%d,%d,%dz", 0x1000000000LL, 6, 7, 8);
+
+  EXPECT_SWPRINTF(L"a_1.230000_b", L"a_%f_b", 1.23f);
+  EXPECT_SWPRINTF(L"a_3.14_b", L"a_%g_b", 3.14);
+  EXPECT_SWPRINTF(L"print_me_twice print_me_twice", L"%1$s %1$s", "print_me_twice");
 }
 
 template <typename T>
@@ -617,227 +701,164 @@
               L"[-NAN]", L"[NAN]", L"[+NAN]");
 }
 
-TEST(STDIO_TEST, swprintf) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  ASSERT_EQ(2, swprintf(buf, nchars, L"ab")) << strerror(errno);
-  ASSERT_EQ(std::wstring(L"ab"), buf);
-  ASSERT_EQ(5, swprintf(buf, nchars, L"%s", "abcde"));
-  ASSERT_EQ(std::wstring(L"abcde"), buf);
-
-  // Unlike swprintf(), swprintf() returns -1 in case of truncation
-  // and doesn't necessarily zero-terminate the output!
-  ASSERT_EQ(-1, swprintf(buf, 4, L"%s", "abcde"));
-
-  const char kString[] = "Hello, World";
-  ASSERT_EQ(12, swprintf(buf, nchars, L"%s", kString));
-  ASSERT_EQ(std::wstring(L"Hello, World"), buf);
-  ASSERT_EQ(12, swprintf(buf, 13, L"%s", kString));
-  ASSERT_EQ(std::wstring(L"Hello, World"), buf);
-}
-
-TEST(STDIO_TEST, swprintf_a) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  ASSERT_EQ(20, swprintf(buf, nchars, L"%a", 3.1415926535));
-  ASSERT_EQ(std::wstring(L"0x1.921fb54411744p+1"), buf);
-}
-
-TEST(STDIO_TEST, swprintf_lc) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  wint_t wc = L'a';
-  EXPECT_EQ(3, swprintf(buf, nchars, L"<%lc>", wc));
-  EXPECT_EQ(std::wstring(L"<a>"), buf);
-}
-
-TEST(STDIO_TEST, swprintf_C) { // Synonym for %lc.
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  wint_t wc = L'a';
-  EXPECT_EQ(3, swprintf(buf, nchars, L"<%C>", wc));
-  EXPECT_EQ(std::wstring(L"<a>"), buf);
+TEST(STDIO_TEST, snprintf_jd_INTMAX_MAX) {
+  EXPECT_SNPRINTF("9223372036854775807", "%jd", INTMAX_MAX);
 }
 
 TEST(STDIO_TEST, swprintf_jd_INTMAX_MAX) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  swprintf(buf, nchars, L"%jd", INTMAX_MAX);
-  EXPECT_EQ(std::wstring(L"9223372036854775807"), buf);
-}
-
-TEST(STDIO_TEST, swprintf_jd_INTMAX_MIN) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  swprintf(buf, nchars, L"%jd", INTMAX_MIN);
-  EXPECT_EQ(std::wstring(L"-9223372036854775808"), buf);
-}
-
-TEST(STDIO_TEST, swprintf_ju_UINTMAX_MAX) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  swprintf(buf, nchars, L"%ju", UINTMAX_MAX);
-  EXPECT_EQ(std::wstring(L"18446744073709551615"), buf);
-}
-
-TEST(STDIO_TEST, swprintf_1$ju_UINTMAX_MAX) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  swprintf(buf, nchars, L"%1$ju", UINTMAX_MAX);
-  EXPECT_EQ(std::wstring(L"18446744073709551615"), buf);
-}
-
-TEST(STDIO_TEST, swprintf_ls) {
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  static const wchar_t kWideString[] = L"Hello\uff41 World";
-  ASSERT_EQ(12, swprintf(buf, nchars, L"%ls", kWideString));
-  ASSERT_EQ(std::wstring(kWideString), buf);
-  ASSERT_EQ(12, swprintf(buf, 13, L"%ls", kWideString));
-  ASSERT_EQ(std::wstring(kWideString), buf);
-}
-
-TEST(STDIO_TEST, swprintf_S) { // Synonym for %ls.
-  constexpr size_t nchars = 32;
-  wchar_t buf[nchars];
-
-  static const wchar_t kWideString[] = L"Hello\uff41 World";
-  ASSERT_EQ(12, swprintf(buf, nchars, L"%S", kWideString));
-  ASSERT_EQ(std::wstring(kWideString), buf);
-  ASSERT_EQ(12, swprintf(buf, 13, L"%S", kWideString));
-  ASSERT_EQ(std::wstring(kWideString), buf);
-}
-
-TEST(STDIO_TEST, snprintf_d_INT_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%d", INT_MAX);
-  EXPECT_STREQ("2147483647", buf);
-}
-
-TEST(STDIO_TEST, snprintf_d_INT_MIN) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%d", INT_MIN);
-  EXPECT_STREQ("-2147483648", buf);
-}
-
-TEST(STDIO_TEST, snprintf_jd_INTMAX_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%jd", INTMAX_MAX);
-  EXPECT_STREQ("9223372036854775807", buf);
+  EXPECT_SWPRINTF(L"9223372036854775807", L"%jd", INTMAX_MAX);
 }
 
 TEST(STDIO_TEST, snprintf_jd_INTMAX_MIN) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%jd", INTMAX_MIN);
-  EXPECT_STREQ("-9223372036854775808", buf);
+  EXPECT_SNPRINTF("-9223372036854775808", "%jd", INTMAX_MIN);
+}
+
+TEST(STDIO_TEST, swprintf_jd_INTMAX_MIN) {
+  EXPECT_SWPRINTF(L"-9223372036854775808", L"%jd", INTMAX_MIN);
 }
 
 TEST(STDIO_TEST, snprintf_ju_UINTMAX_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%ju", UINTMAX_MAX);
-  EXPECT_STREQ("18446744073709551615", buf);
+  EXPECT_SNPRINTF("18446744073709551615", "%ju", UINTMAX_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_ju_UINTMAX_MAX) {
+  EXPECT_SWPRINTF(L"18446744073709551615", L"%ju", UINTMAX_MAX);
 }
 
 TEST(STDIO_TEST, snprintf_1$ju_UINTMAX_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%1$ju", UINTMAX_MAX);
-  EXPECT_STREQ("18446744073709551615", buf);
+  EXPECT_SNPRINTF("18446744073709551615", "%1$ju", UINTMAX_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_1$ju_UINTMAX_MAX) {
+  EXPECT_SWPRINTF(L"18446744073709551615", L"%1$ju", UINTMAX_MAX);
+}
+
+TEST(STDIO_TEST, snprintf_d_INT_MAX) {
+  EXPECT_SNPRINTF("2147483647", "%d", INT_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_d_INT_MAX) {
+  EXPECT_SWPRINTF(L"2147483647", L"%d", INT_MAX);
+}
+
+TEST(STDIO_TEST, snprintf_d_INT_MIN) {
+  EXPECT_SNPRINTF("-2147483648", "%d", INT_MIN);
+}
+
+TEST(STDIO_TEST, swprintf_d_INT_MIN) {
+  EXPECT_SWPRINTF(L"-2147483648", L"%d", INT_MIN);
 }
 
 TEST(STDIO_TEST, snprintf_ld_LONG_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%ld", LONG_MAX);
 #if defined(__LP64__)
-  EXPECT_STREQ("9223372036854775807", buf);
+  EXPECT_SNPRINTF("9223372036854775807", "%ld", LONG_MAX);
 #else
-  EXPECT_STREQ("2147483647", buf);
+  EXPECT_SNPRINTF("2147483647", "%ld", LONG_MAX);
+#endif
+}
+
+TEST(STDIO_TEST, swprintf_ld_LONG_MAX) {
+#if defined(__LP64__)
+  EXPECT_SWPRINTF(L"9223372036854775807", L"%ld", LONG_MAX);
+#else
+  EXPECT_SWPRINTF(L"2147483647", L"%ld", LONG_MAX);
 #endif
 }
 
 TEST(STDIO_TEST, snprintf_ld_LONG_MIN) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%ld", LONG_MIN);
 #if defined(__LP64__)
-  EXPECT_STREQ("-9223372036854775808", buf);
+  EXPECT_SNPRINTF("-9223372036854775808", "%ld", LONG_MIN);
 #else
-  EXPECT_STREQ("-2147483648", buf);
+  EXPECT_SNPRINTF("-2147483648", "%ld", LONG_MIN);
+#endif
+}
+
+TEST(STDIO_TEST, swprintf_ld_LONG_MIN) {
+#if defined(__LP64__)
+  EXPECT_SWPRINTF(L"-9223372036854775808", L"%ld", LONG_MIN);
+#else
+  EXPECT_SWPRINTF(L"-2147483648", L"%ld", LONG_MIN);
 #endif
 }
 
 TEST(STDIO_TEST, snprintf_lld_LLONG_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%lld", LLONG_MAX);
-  EXPECT_STREQ("9223372036854775807", buf);
+  EXPECT_SNPRINTF("9223372036854775807", "%lld", LLONG_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_lld_LLONG_MAX) {
+  EXPECT_SWPRINTF(L"9223372036854775807", L"%lld", LLONG_MAX);
 }
 
 TEST(STDIO_TEST, snprintf_lld_LLONG_MIN) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%lld", LLONG_MIN);
-  EXPECT_STREQ("-9223372036854775808", buf);
+  EXPECT_SNPRINTF("-9223372036854775808", "%lld", LLONG_MIN);
+}
+
+TEST(STDIO_TEST, swprintf_lld_LLONG_MIN) {
+  EXPECT_SWPRINTF(L"-9223372036854775808", L"%lld", LLONG_MIN);
 }
 
 TEST(STDIO_TEST, snprintf_o_UINT_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%o", UINT_MAX);
-  EXPECT_STREQ("37777777777", buf);
+  EXPECT_SNPRINTF("37777777777", "%o", UINT_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_o_UINT_MAX) {
+  EXPECT_SWPRINTF(L"37777777777", L"%o", UINT_MAX);
 }
 
 TEST(STDIO_TEST, snprintf_u_UINT_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%u", UINT_MAX);
-  EXPECT_STREQ("4294967295", buf);
+  EXPECT_SNPRINTF("4294967295", "%u", UINT_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_u_UINT_MAX) {
+  EXPECT_SWPRINTF(L"4294967295", L"%u", UINT_MAX);
 }
 
 TEST(STDIO_TEST, snprintf_x_UINT_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%x", UINT_MAX);
-  EXPECT_STREQ("ffffffff", buf);
+  EXPECT_SNPRINTF("ffffffff", "%x", UINT_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_x_UINT_MAX) {
+  EXPECT_SWPRINTF(L"ffffffff", L"%x", UINT_MAX);
 }
 
 TEST(STDIO_TEST, snprintf_X_UINT_MAX) {
-  char buf[BUFSIZ];
-  snprintf(buf, sizeof(buf), "%X", UINT_MAX);
-  EXPECT_STREQ("FFFFFFFF", buf);
+  EXPECT_SNPRINTF("FFFFFFFF", "%X", UINT_MAX);
+}
+
+TEST(STDIO_TEST, swprintf_X_UINT_MAX) {
+  EXPECT_SWPRINTF(L"FFFFFFFF", L"%X", UINT_MAX);
 }
 
 TEST(STDIO_TEST, snprintf_e) {
-  char buf[BUFSIZ];
+  EXPECT_SNPRINTF("1.500000e+00", "%e", 1.5);
+  EXPECT_SNPRINTF("1.500000e+00", "%Le", 1.5L);
+}
 
-  snprintf(buf, sizeof(buf), "%e", 1.5);
-  EXPECT_STREQ("1.500000e+00", buf);
-
-  snprintf(buf, sizeof(buf), "%Le", 1.5L);
-  EXPECT_STREQ("1.500000e+00", buf);
+TEST(STDIO_TEST, swprintf_e) {
+  EXPECT_SWPRINTF(L"1.500000e+00", L"%e", 1.5);
+  EXPECT_SWPRINTF(L"1.500000e+00", L"%Le", 1.5L);
 }
 
 TEST(STDIO_TEST, snprintf_negative_zero_5084292) {
-  char buf[BUFSIZ];
+  EXPECT_SNPRINTF("-0.000000e+00", "%e", -0.0);
+  EXPECT_SNPRINTF("-0.000000E+00", "%E", -0.0);
+  EXPECT_SNPRINTF("-0.000000", "%f", -0.0);
+  EXPECT_SNPRINTF("-0.000000", "%F", -0.0);
+  EXPECT_SNPRINTF("-0", "%g", -0.0);
+  EXPECT_SNPRINTF("-0", "%G", -0.0);
+  EXPECT_SNPRINTF("-0x0p+0", "%a", -0.0);
+  EXPECT_SNPRINTF("-0X0P+0", "%A", -0.0);
+}
 
-  snprintf(buf, sizeof(buf), "%e", -0.0);
-  EXPECT_STREQ("-0.000000e+00", buf);
-  snprintf(buf, sizeof(buf), "%E", -0.0);
-  EXPECT_STREQ("-0.000000E+00", buf);
-  snprintf(buf, sizeof(buf), "%f", -0.0);
-  EXPECT_STREQ("-0.000000", buf);
-  snprintf(buf, sizeof(buf), "%F", -0.0);
-  EXPECT_STREQ("-0.000000", buf);
-  snprintf(buf, sizeof(buf), "%g", -0.0);
-  EXPECT_STREQ("-0", buf);
-  snprintf(buf, sizeof(buf), "%G", -0.0);
-  EXPECT_STREQ("-0", buf);
-  snprintf(buf, sizeof(buf), "%a", -0.0);
-  EXPECT_STREQ("-0x0p+0", buf);
-  snprintf(buf, sizeof(buf), "%A", -0.0);
-  EXPECT_STREQ("-0X0P+0", buf);
+TEST(STDIO_TEST, swprintf_negative_zero_5084292) {
+  EXPECT_SWPRINTF(L"-0.000000e+00", L"%e", -0.0);
+  EXPECT_SWPRINTF(L"-0.000000E+00", L"%E", -0.0);
+  EXPECT_SWPRINTF(L"-0.000000", L"%f", -0.0);
+  EXPECT_SWPRINTF(L"-0.000000", L"%F", -0.0);
+  EXPECT_SWPRINTF(L"-0", L"%g", -0.0);
+  EXPECT_SWPRINTF(L"-0", L"%G", -0.0);
+  EXPECT_SWPRINTF(L"-0x0p+0", L"%a", -0.0);
+  EXPECT_SWPRINTF(L"-0X0P+0", L"%A", -0.0);
 }
 
 TEST(STDIO_TEST, snprintf_utf8_15439554) {
@@ -898,18 +919,36 @@
   ASSERT_EQ(ENOMEM, errno);
 }
 
+TEST(STDIO_TEST, swprintf_asterisk_overflow) {
+  wchar_t buf[128];
+  ASSERT_EQ(5, swprintf(buf, sizeof(buf), L"%.*s%c", 4, "hello world", '!'));
+  ASSERT_EQ(12, swprintf(buf, sizeof(buf), L"%.*s%c", INT_MAX / 2, "hello world", '!'));
+  ASSERT_EQ(12, swprintf(buf, sizeof(buf), L"%.*s%c", INT_MAX - 1, "hello world", '!'));
+  ASSERT_EQ(12, swprintf(buf, sizeof(buf), L"%.*s%c", INT_MAX, "hello world", '!'));
+  ASSERT_EQ(12, swprintf(buf, sizeof(buf), L"%.*s%c", -1, "hello world", '!'));
+
+  // INT_MAX-1, INT_MAX, INT_MAX+1.
+  ASSERT_EQ(12, swprintf(buf, sizeof(buf), L"%.2147483646s%c", "hello world", '!'));
+  ASSERT_EQ(12, swprintf(buf, sizeof(buf), L"%.2147483647s%c", "hello world", '!'));
+  ASSERT_EQ(-1, swprintf(buf, sizeof(buf), L"%.2147483648s%c", "hello world", '!'));
+  ASSERT_EQ(ENOMEM, errno);
+}
+
 // Inspired by https://github.com/landley/toybox/issues/163.
 TEST(STDIO_TEST, printf_NULL) {
-  char buf[128];
   char* null = nullptr;
-  EXPECT_EQ(4, snprintf(buf, sizeof(buf), "<%*.*s>", 2, 2, null));
-  EXPECT_STREQ("<(n>", buf);
-  EXPECT_EQ(8, snprintf(buf, sizeof(buf), "<%*.*s>", 2, 8, null));
-  EXPECT_STREQ("<(null)>", buf);
-  EXPECT_EQ(10, snprintf(buf, sizeof(buf), "<%*.*s>", 8, 2, null));
-  EXPECT_STREQ("<      (n>", buf);
-  EXPECT_EQ(10, snprintf(buf, sizeof(buf), "<%*.*s>", 8, 8, null));
-  EXPECT_STREQ("<  (null)>", buf);
+  EXPECT_SNPRINTF("<(n>", "<%*.*s>", 2, 2, null);
+  EXPECT_SNPRINTF("<(null)>", "<%*.*s>", 2, 8, null);
+  EXPECT_SNPRINTF("<      (n>", "<%*.*s>", 8, 2, null);
+  EXPECT_SNPRINTF("<  (null)>", "<%*.*s>", 8, 8, null);
+}
+
+TEST(STDIO_TEST, wprintf_NULL) {
+  char* null = nullptr;
+  EXPECT_SWPRINTF(L"<(n>", L"<%*.*s>", 2, 2, null);
+  EXPECT_SWPRINTF(L"<(null)>", L"<%*.*s>", 2, 8, null);
+  EXPECT_SWPRINTF(L"<      (n>", L"<%*.*s>", 8, 2, null);
+  EXPECT_SWPRINTF(L"<  (null)>", L"<%*.*s>", 8, 8, null);
 }
 
 TEST(STDIO_TEST, fprintf) {
@@ -2452,7 +2491,7 @@
 }
 
 TEST_F(STDIO_DEATHTEST, snprintf_30445072_unknown_buffer_size) {
-  std::string buf = "world";
+  std::string buf = "hello";  // So the compiler doesn't know the buffer size.
   ASSERT_EXIT(snprintf(&buf[0], atol("-1"), "hello"),
               testing::KilledBySignal(SIGABRT),
               "FORTIFY: vsnprintf: size .* > SSIZE_MAX");
@@ -2465,48 +2504,36 @@
 }
 
 TEST(STDIO_TEST, printf_m) {
-  char buf[BUFSIZ];
   errno = 0;
-  snprintf(buf, sizeof(buf), "<%m>");
-  ASSERT_STREQ("<Success>", buf);
+  EXPECT_SNPRINTF("<Success>", "<%m>");
   errno = -1;
-  snprintf(buf, sizeof(buf), "<%m>");
-  ASSERT_STREQ("<Unknown error -1>", buf);
+  EXPECT_SNPRINTF("<Unknown error -1>", "<%m>");
   errno = EINVAL;
-  snprintf(buf, sizeof(buf), "<%m>");
-  ASSERT_STREQ("<Invalid argument>", buf);
-}
-
-TEST(STDIO_TEST, printf_m_does_not_clobber_strerror) {
-  char buf[BUFSIZ];
-  const char* m = strerror(-1);
-  ASSERT_STREQ("Unknown error -1", m);
-  errno = -2;
-  snprintf(buf, sizeof(buf), "<%m>");
-  ASSERT_STREQ("<Unknown error -2>", buf);
-  ASSERT_STREQ("Unknown error -1", m);
+  EXPECT_SNPRINTF("<Invalid argument>", "<%m>");
 }
 
 TEST(STDIO_TEST, wprintf_m) {
-  wchar_t buf[BUFSIZ];
   errno = 0;
-  swprintf(buf, sizeof(buf), L"<%m>");
-  ASSERT_EQ(std::wstring(L"<Success>"), buf);
+  EXPECT_SWPRINTF(L"<Success>", L"<%m>");
   errno = -1;
-  swprintf(buf, sizeof(buf), L"<%m>");
-  ASSERT_EQ(std::wstring(L"<Unknown error -1>"), buf);
+  EXPECT_SWPRINTF(L"<Unknown error -1>", L"<%m>");
   errno = EINVAL;
-  swprintf(buf, sizeof(buf), L"<%m>");
-  ASSERT_EQ(std::wstring(L"<Invalid argument>"), buf);
+  EXPECT_SWPRINTF(L"<Invalid argument>", L"<%m>");
 }
 
-TEST(STDIO_TEST, wprintf_m_does_not_clobber_strerror) {
-  wchar_t buf[BUFSIZ];
+TEST(STDIO_TEST, printf_m_does_not_clobber_strerror) {
   const char* m = strerror(-1);
   ASSERT_STREQ("Unknown error -1", m);
   errno = -2;
-  swprintf(buf, sizeof(buf), L"<%m>");
-  ASSERT_EQ(std::wstring(L"<Unknown error -2>"), buf);
+  EXPECT_SNPRINTF("<Unknown error -2>", "<%m>");
+  ASSERT_STREQ("Unknown error -1", m);
+}
+
+TEST(STDIO_TEST, wprintf_m_does_not_clobber_strerror) {
+  const char* m = strerror(-1);
+  ASSERT_STREQ("Unknown error -1", m);
+  errno = -2;
+  EXPECT_SWPRINTF(L"<Unknown error -2>", L"<%m>");
   ASSERT_STREQ("Unknown error -1", m);
 }
 
@@ -2983,60 +3010,84 @@
 #endif
 }
 
-TEST(STDIO_TEST, snprintf_b) {
-  char buf[BUFSIZ];
-  EXPECT_EQ(5, snprintf(buf, sizeof(buf), "<%b>", 5));
-  EXPECT_STREQ("<101>", buf);
-  EXPECT_EQ(10, snprintf(buf, sizeof(buf), "<%08b>", 5));
-  EXPECT_STREQ("<00000101>", buf);
-  EXPECT_EQ(34, snprintf(buf, sizeof(buf), "<%b>", 0xaaaaaaaa));
-  EXPECT_STREQ("<10101010101010101010101010101010>", buf);
-  EXPECT_EQ(36, snprintf(buf, sizeof(buf), "<%#b>", 0xaaaaaaaa));
-  EXPECT_STREQ("<0b10101010101010101010101010101010>", buf);
-  EXPECT_EQ(3, snprintf(buf, sizeof(buf), "<%#b>", 0));
-  EXPECT_STREQ("<0>", buf);
+TEST(STDIO_TEST, snprintf_b_B) {
+#if defined(__BIONIC__)
+  uint8_t b = 5;
+  EXPECT_SNPRINTF("<101>", "<%" PRIb8 ">", b);
+  EXPECT_SNPRINTF("<101>", "<%" PRIB8 ">", b);
+  EXPECT_SNPRINTF("<00000101>", "<%08" PRIb8 ">", b);
+  EXPECT_SNPRINTF("<00000101>", "<%08" PRIB8 ">", b);
+
+  uint16_t s = 0xaaaa;
+  EXPECT_SNPRINTF("<1010101010101010>", "<%" PRIb16 ">", s);
+  EXPECT_SNPRINTF("<1010101010101010>", "<%" PRIB16 ">", s);
+  EXPECT_SNPRINTF("<0b1010101010101010>", "<%#" PRIb16 ">", s);
+  EXPECT_SNPRINTF("<0B1010101010101010>", "<%#" PRIB16 ">", s);
+
+  EXPECT_SNPRINTF("<10101010101010101010101010101010>", "<%" PRIb32 ">", 0xaaaaaaaa);
+  EXPECT_SNPRINTF("<10101010101010101010101010101010>", "<%" PRIB32 ">", 0xaaaaaaaa);
+  EXPECT_SNPRINTF("<0b10101010101010101010101010101010>", "<%#" PRIb32 ">", 0xaaaaaaaa);
+  EXPECT_SNPRINTF("<0B10101010101010101010101010101010>", "<%#" PRIB32 ">", 0xaaaaaaaa);
+
+  // clang doesn't like "%lb" (https://github.com/llvm/llvm-project/issues/62247)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat"
+  EXPECT_SNPRINTF("<1010101010101010101010101010101010101010101010101010101010101010>",
+                  "<%" PRIb64 ">", 0xaaaaaaaa'aaaaaaaa);
+  EXPECT_SNPRINTF("<1010101010101010101010101010101010101010101010101010101010101010>",
+                  "<%" PRIB64 ">", 0xaaaaaaaa'aaaaaaaa);
+  EXPECT_SNPRINTF("<0b1010101010101010101010101010101010101010101010101010101010101010>",
+                  "<%#" PRIb64 ">", 0xaaaaaaaa'aaaaaaaa);
+  EXPECT_SNPRINTF("<0B1010101010101010101010101010101010101010101010101010101010101010>",
+                  "<%#" PRIB64 ">", 0xaaaaaaaa'aaaaaaaa);
+#pragma clang diagnostic pop
+
+  EXPECT_SNPRINTF("<0>", "<%#b>", 0);
+  EXPECT_SNPRINTF("<0>", "<%#B>", 0);
+#else
+  GTEST_SKIP() << "no %b in glibc";
+#endif
 }
 
-TEST(STDIO_TEST, snprintf_B) {
-  char buf[BUFSIZ];
-  EXPECT_EQ(5, snprintf(buf, sizeof(buf), "<%B>", 5));
-  EXPECT_STREQ("<101>", buf);
-  EXPECT_EQ(10, snprintf(buf, sizeof(buf), "<%08B>", 5));
-  EXPECT_STREQ("<00000101>", buf);
-  EXPECT_EQ(34, snprintf(buf, sizeof(buf), "<%B>", 0xaaaaaaaa));
-  EXPECT_STREQ("<10101010101010101010101010101010>", buf);
-  EXPECT_EQ(36, snprintf(buf, sizeof(buf), "<%#B>", 0xaaaaaaaa));
-  EXPECT_STREQ("<0B10101010101010101010101010101010>", buf);
-  EXPECT_EQ(3, snprintf(buf, sizeof(buf), "<%#B>", 0));
-  EXPECT_STREQ("<0>", buf);
-}
+TEST(STDIO_TEST, swprintf_b_B) {
+#if defined(__BIONIC__)
+  uint8_t b = 5;
+  EXPECT_SWPRINTF(L"<101>", L"<%" PRIb8 ">", b);
+  EXPECT_SWPRINTF(L"<101>", L"<%" PRIB8 ">", b);
+  EXPECT_SWPRINTF(L"<0b101>", L"<%#" PRIb8 ">", b);
+  EXPECT_SWPRINTF(L"<0B101>", L"<%#" PRIB8 ">", b);
+  EXPECT_SWPRINTF(L"<00000101>", L"<%08" PRIb8 ">", b);
+  EXPECT_SWPRINTF(L"<00000101>", L"<%08" PRIB8 ">", b);
 
-TEST(STDIO_TEST, swprintf_b) {
-  wchar_t buf[BUFSIZ];
-  EXPECT_EQ(5, swprintf(buf, sizeof(buf), L"<%b>", 5));
-  EXPECT_EQ(std::wstring(L"<101>"), buf);
-  EXPECT_EQ(10, swprintf(buf, sizeof(buf), L"<%08b>", 5));
-  EXPECT_EQ(std::wstring(L"<00000101>"), buf);
-  EXPECT_EQ(34, swprintf(buf, sizeof(buf), L"<%b>", 0xaaaaaaaa));
-  EXPECT_EQ(std::wstring(L"<10101010101010101010101010101010>"), buf);
-  EXPECT_EQ(36, swprintf(buf, sizeof(buf), L"<%#b>", 0xaaaaaaaa));
-  EXPECT_EQ(std::wstring(L"<0b10101010101010101010101010101010>"), buf);
-  EXPECT_EQ(3, swprintf(buf, sizeof(buf), L"<%#b>", 0));
-  EXPECT_EQ(std::wstring(L"<0>"), buf);
-}
+  uint16_t s = 0xaaaa;
+  EXPECT_SWPRINTF(L"<1010101010101010>", L"<%" PRIb16 ">", s);
+  EXPECT_SWPRINTF(L"<1010101010101010>", L"<%" PRIB16 ">", s);
+  EXPECT_SWPRINTF(L"<0b1010101010101010>", L"<%#" PRIb16 ">", s);
+  EXPECT_SWPRINTF(L"<0B1010101010101010>", L"<%#" PRIB16 ">", s);
 
-TEST(STDIO_TEST, swprintf_B) {
-  wchar_t buf[BUFSIZ];
-  EXPECT_EQ(5, swprintf(buf, sizeof(buf), L"<%B>", 5));
-  EXPECT_EQ(std::wstring(L"<101>"), buf);
-  EXPECT_EQ(10, swprintf(buf, sizeof(buf), L"<%08B>", 5));
-  EXPECT_EQ(std::wstring(L"<00000101>"), buf);
-  EXPECT_EQ(34, swprintf(buf, sizeof(buf), L"<%B>", 0xaaaaaaaa));
-  EXPECT_EQ(std::wstring(L"<10101010101010101010101010101010>"), buf);
-  EXPECT_EQ(36, swprintf(buf, sizeof(buf), L"<%#B>", 0xaaaaaaaa));
-  EXPECT_EQ(std::wstring(L"<0B10101010101010101010101010101010>"), buf);
-  EXPECT_EQ(3, swprintf(buf, sizeof(buf), L"<%#B>", 0));
-  EXPECT_EQ(std::wstring(L"<0>"), buf);
+  EXPECT_SWPRINTF(L"<10101010101010101010101010101010>", L"<%" PRIb32 ">", 0xaaaaaaaa);
+  EXPECT_SWPRINTF(L"<10101010101010101010101010101010>", L"<%" PRIB32 ">", 0xaaaaaaaa);
+  EXPECT_SWPRINTF(L"<0b10101010101010101010101010101010>", L"<%#" PRIb32 ">", 0xaaaaaaaa);
+  EXPECT_SWPRINTF(L"<0B10101010101010101010101010101010>", L"<%#" PRIB32 ">", 0xaaaaaaaa);
+
+  // clang doesn't like "%lb" (https://github.com/llvm/llvm-project/issues/62247)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat"
+  EXPECT_SWPRINTF(L"<1010101010101010101010101010101010101010101010101010101010101010>",
+                  L"<%" PRIb64 ">", 0xaaaaaaaa'aaaaaaaa);
+  EXPECT_SWPRINTF(L"<1010101010101010101010101010101010101010101010101010101010101010>",
+                  L"<%" PRIB64 ">", 0xaaaaaaaa'aaaaaaaa);
+  EXPECT_SWPRINTF(L"<0b1010101010101010101010101010101010101010101010101010101010101010>",
+                  L"<%#" PRIb64 ">", 0xaaaaaaaa'aaaaaaaa);
+  EXPECT_SWPRINTF(L"<0B1010101010101010101010101010101010101010101010101010101010101010>",
+                  L"<%#" PRIB64 ">", 0xaaaaaaaa'aaaaaaaa);
+#pragma clang diagnostic pop
+
+  EXPECT_SWPRINTF(L"<0>", L"<%#b>", 0);
+  EXPECT_SWPRINTF(L"<0>", L"<%#B>", 0);
+#else
+  GTEST_SKIP() << "no %b in glibc";
+#endif
 }
 
 TEST(STDIO_TEST, scanf_i_decimal) {
@@ -3164,3 +3215,274 @@
   EXPECT_EQ(0, i);
   EXPECT_EQ('b', ch);
 }
+
+TEST(STDIO_TEST, snprintf_w_base) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+#pragma clang diagnostic ignored "-Wconstant-conversion"
+  int8_t a = 0b101;
+  EXPECT_SNPRINTF("<101>", "<%w8b>", a);
+  int8_t b1 = 0xFF;
+  EXPECT_SNPRINTF("<-1>", "<%w8d>", b1);
+  int8_t b2 = 0x1FF;
+  EXPECT_SNPRINTF("<-1>", "<%w8d>", b2);
+  int16_t c = 0xFFFF;
+  EXPECT_SNPRINTF("<-1>", "<%w16i>", c);
+  int32_t d = 021;
+  EXPECT_SNPRINTF("<21>", "<%w32o>", d);
+  uint32_t e = -1;
+  EXPECT_SNPRINTF("<4294967295>", "<%w32u>", e);
+  int64_t f = 0x3b;
+  EXPECT_SNPRINTF("<3b>", "<%w64x>", f);
+  EXPECT_SNPRINTF("<3B>", "<%w64X>", f);
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, swprintf_w_base) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+#pragma clang diagnostic ignored "-Wconstant-conversion"
+  int8_t a = 0b101;
+  EXPECT_SWPRINTF(L"<101>", L"<%w8b>", a);
+  int8_t b1 = 0xFF;
+  EXPECT_SWPRINTF(L"<-1>", L"<%w8d>", b1);
+  int8_t b2 = 0x1FF;
+  EXPECT_SWPRINTF(L"<-1>", L"<%w8d>", b2);
+  int16_t c = 0xFFFF;
+  EXPECT_SWPRINTF(L"<-1>", L"<%w16i>", c);
+  int32_t d = 021;
+  EXPECT_SWPRINTF(L"<21>", L"<%w32o>", d);
+  uint32_t e = -1;
+  EXPECT_SWPRINTF(L"<4294967295>", L"<%w32u>", e);
+  int64_t f = 0x3b;
+  EXPECT_SWPRINTF(L"<3b>", L"<%w64x>", f);
+  EXPECT_SWPRINTF(L"<3B>", L"<%w64X>", f);
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, snprintf_w_arguments_reordering) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+#pragma clang diagnostic ignored "-Wformat-extra-args"
+  int32_t a = 0xaaaaaaaa;
+  int64_t b = 0x11111111'22222222;
+  int64_t c = 0x33333333'44444444;
+  int64_t d = 0xaaaaaaaa'aaaaaaaa;
+  EXPECT_SNPRINTF("<10101010101010101010101010101010 --- 3333333344444444>",
+                  "<%2$w32b --- %1$w64x>", c, a);
+  EXPECT_SNPRINTF(
+      "<1010101010101010101010101010101010101010101010101010101010101010 --- 1111111122222222 --- "
+      "3333333344444444>",
+      "<%3$w64b --- %1$w64x --- %2$w64x>", b, c, d);
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, swprintf_w_arguments_reordering) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+#pragma clang diagnostic ignored "-Wformat-extra-args"
+  int32_t a = 0xaaaaaaaa;
+  int64_t b = 0x11111111'22222222;
+  int64_t c = 0x33333333'44444444;
+  int64_t d = 0xaaaaaaaa'aaaaaaaa;
+  EXPECT_SWPRINTF(L"<10101010101010101010101010101010 --- 3333333344444444>",
+                  L"<%2$w32b --- %1$w64x>", c, a);
+  EXPECT_SWPRINTF(
+      L"<1010101010101010101010101010101010101010101010101010101010101010 --- 1111111122222222 --- "
+      L"3333333344444444>",
+      L"<%3$w64b --- %1$w64x --- %2$w64x>", b, c, d);
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, snprintf_invalid_w_width) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  char buf[BUFSIZ];
+  int32_t a = 100;
+  EXPECT_DEATH(snprintf(buf, sizeof(buf), "%w20d", &a), "%w20 is unsupported");
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, swprintf_invalid_w_width) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  wchar_t buf[BUFSIZ];
+  int32_t a = 100;
+  EXPECT_DEATH(swprintf(buf, sizeof(buf), L"%w20d", &a), "%w20 is unsupported");
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, snprintf_wf_base) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wconstant-conversion"
+#pragma clang diagnostic ignored "-Wformat"
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  int_fast8_t a = 0b101;
+  EXPECT_SNPRINTF("<101>", "<%wf8b>", a);
+  int_fast8_t b = 0x12341234'12341234;
+  EXPECT_SNPRINTF("<34>", "<%wf8x>", b);
+  uint_fast16_t c = 0x11111111'22222222;
+#if defined(__LP64__)
+  EXPECT_SNPRINTF("<1111111122222222>", "<%wf16x>", c);
+#else
+  EXPECT_SNPRINTF("<22222222>", "<%wf16x>", c);
+#endif
+  int_fast32_t d = 0x33333333'44444444;
+#if defined(__LP64__)
+  EXPECT_SNPRINTF("<3333333344444444>", "<%wf32x>", d);
+#else
+  EXPECT_SNPRINTF("<44444444>", "<%wf32x>", d);
+#endif
+  int_fast64_t e = 0xaaaaaaaa'aaaaaaaa;
+  EXPECT_SNPRINTF("<aaaaaaaaaaaaaaaa>", "<%wf64x>", e);
+  EXPECT_SNPRINTF("<AAAAAAAAAAAAAAAA>", "<%wf64X>", e);
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %wf in glibc";
+#endif
+}
+TEST(STDIO_TEST, swprintf_wf_base) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wconstant-conversion"
+#pragma clang diagnostic ignored "-Wformat"
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  int_fast8_t a = 0b101;
+  EXPECT_SWPRINTF(L"<101>", L"<%wf8b>", a);
+  int_fast8_t b = 0x12341234'12341234;
+  EXPECT_SWPRINTF(L"<34>", L"<%wf8x>", b);
+  uint_fast16_t c = 0x11111111'22222222;
+#if defined(__LP64__)
+  EXPECT_SWPRINTF(L"<1111111122222222>", L"<%wf16x>", c);
+#else
+  EXPECT_SWPRINTF(L"<22222222>", L"<%wf16x>", c);
+#endif
+  int_fast32_t d = 0x33333333'44444444;
+#if defined(__LP64__)
+  EXPECT_SWPRINTF(L"<3333333344444444>", L"<%wf32x>", d);
+#else
+  EXPECT_SWPRINTF(L"<44444444>", L"<%wf32x>", d);
+#endif
+  int_fast64_t e = 0xaaaaaaaa'aaaaaaaa;
+  EXPECT_SWPRINTF(L"<aaaaaaaaaaaaaaaa>", L"<%wf64x>", e);
+  EXPECT_SWPRINTF(L"<AAAAAAAAAAAAAAAA>", L"<%wf64X>", e);
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %wf in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, snprintf_wf_arguments_reordering) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wconstant-conversion"
+#pragma clang diagnostic ignored "-Wformat"
+#pragma clang diagnostic ignored "-Wformat-extra-args"
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  int_fast16_t a = 0x11111111'22222222;
+  int_fast32_t b = 0x33333333'44444444;
+  int_fast32_t c = 0xaaaaaaaa'aaaaaaaa;
+#if defined(__LP64__)
+  EXPECT_SNPRINTF(
+      "<3333333344444444 --- 1010101010101010101010101010101010101010101010101010101010101010>",
+      "<%2$wf32x --- %1$wf32b>", c, b);
+
+  EXPECT_SNPRINTF(
+      "<1010101010101010101010101010101010101010101010101010101010101010 --- 1111111122222222 --- "
+      "3333333344444444>",
+      "<%3$wf32b --- %1$wf16x --- %2$wf32x>", a, b, c);
+#else
+  EXPECT_SNPRINTF("<44444444 --- 10101010101010101010101010101010>", "<%2$wf32x --- %1$wf32b>", c,
+                  b);
+  EXPECT_SNPRINTF("<10101010101010101010101010101010 --- 22222222 --- 44444444>",
+                  "<%3$wf32b --- %1$wf16x --- %2$wf32x>", a, b, c);
+#endif
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, swprintf_wf_arguments_reordering) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wconstant-conversion"
+#pragma clang diagnostic ignored "-Wformat"
+#pragma clang diagnostic ignored "-Wformat-extra-args"
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  int_fast16_t a = 0x11111111'22222222;
+  int_fast32_t b = 0x33333333'44444444;
+  int_fast32_t c = 0xaaaaaaaa'aaaaaaaa;
+#if defined(__LP64__)
+  EXPECT_SWPRINTF(
+      L"<3333333344444444 --- 1010101010101010101010101010101010101010101010101010101010101010>",
+      L"<%2$wf32x --- %1$wf32b>", c, b);
+
+  EXPECT_SWPRINTF(
+      L"<1010101010101010101010101010101010101010101010101010101010101010 --- 1111111122222222 --- "
+      L"3333333344444444>",
+      L"<%3$wf32b --- %1$wf16x --- %2$wf32x>", a, b, c);
+#else
+  EXPECT_SWPRINTF(L"<44444444 --- 10101010101010101010101010101010>", L"<%2$wf32x --- %1$wf32b>", c,
+                  b);
+  EXPECT_SWPRINTF(L"<10101010101010101010101010101010 --- 22222222 --- 44444444>",
+                  L"<%3$wf32b --- %1$wf16x --- %2$wf32x>", a, b, c);
+#endif
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, snprintf_invalid_wf_width) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat"
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  char buf[BUFSIZ];
+  int_fast32_t a = 100;
+  EXPECT_DEATH(snprintf(buf, sizeof(buf), "%wf20d", &a), "%wf20 is unsupported");
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
+
+TEST(STDIO_TEST, swprintf_invalid_wf_width) {
+#if defined(__BIONIC__)
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat"
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  wchar_t buf[BUFSIZ];
+  int_fast32_t a = 100;
+  EXPECT_DEATH(swprintf(buf, sizeof(buf), L"%wf20d", &a), "%wf20 is unsupported");
+#pragma clang diagnostic pop
+#else
+  GTEST_SKIP() << "no %w in glibc";
+#endif
+}
diff --git a/tests/struct_layout_test.cpp b/tests/struct_layout_test.cpp
index 10c100a..0123ed9 100644
--- a/tests/struct_layout_test.cpp
+++ b/tests/struct_layout_test.cpp
@@ -30,7 +30,7 @@
 #define CHECK_OFFSET(name, field, offset) \
     check_offset(#name, #field, offsetof(name, field), offset);
 #ifdef __LP64__
-  CHECK_SIZE(pthread_internal_t, 784);
+  CHECK_SIZE(pthread_internal_t, 776);
   CHECK_OFFSET(pthread_internal_t, next, 0);
   CHECK_OFFSET(pthread_internal_t, prev, 8);
   CHECK_OFFSET(pthread_internal_t, tid, 16);
@@ -55,7 +55,6 @@
   CHECK_OFFSET(pthread_internal_t, dlerror_buffer, 248);
   CHECK_OFFSET(pthread_internal_t, bionic_tls, 760);
   CHECK_OFFSET(pthread_internal_t, errno_value, 768);
-  CHECK_OFFSET(pthread_internal_t, vfork_child_stack_bottom, 776);
   CHECK_SIZE(bionic_tls, 12200);
   CHECK_OFFSET(bionic_tls, key_data, 0);
   CHECK_OFFSET(bionic_tls, locale, 2080);
@@ -73,7 +72,7 @@
   CHECK_OFFSET(bionic_tls, bionic_systrace_disabled, 12193);
   CHECK_OFFSET(bionic_tls, padding, 12194);
 #else
-  CHECK_SIZE(pthread_internal_t, 672);
+  CHECK_SIZE(pthread_internal_t, 668);
   CHECK_OFFSET(pthread_internal_t, next, 0);
   CHECK_OFFSET(pthread_internal_t, prev, 4);
   CHECK_OFFSET(pthread_internal_t, tid, 8);
@@ -98,7 +97,6 @@
   CHECK_OFFSET(pthread_internal_t, dlerror_buffer, 148);
   CHECK_OFFSET(pthread_internal_t, bionic_tls, 660);
   CHECK_OFFSET(pthread_internal_t, errno_value, 664);
-  CHECK_OFFSET(pthread_internal_t, vfork_child_stack_bottom, 668);
   CHECK_SIZE(bionic_tls, 11080);
   CHECK_OFFSET(bionic_tls, key_data, 0);
   CHECK_OFFSET(bionic_tls, locale, 1040);
diff --git a/tests/sys_msg_test.cpp b/tests/sys_msg_test.cpp
index 200f654..da45087 100644
--- a/tests/sys_msg_test.cpp
+++ b/tests/sys_msg_test.cpp
@@ -74,9 +74,12 @@
 }
 
 TEST(sys_msg, msgctl_failure) {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
   errno = 0;
   ASSERT_EQ(-1, msgctl(-1, IPC_STAT, nullptr));
   ASSERT_TRUE(errno == EINVAL || errno == ENOSYS);
+#pragma clang diagnostic pop
 }
 
 TEST(sys_msg, msgget_failure) {
@@ -86,9 +89,12 @@
 }
 
 TEST(sys_msg, msgrcv_failure) {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
   errno = 0;
   ASSERT_EQ(-1, msgrcv(-1, nullptr, 0, 0, 0));
   ASSERT_TRUE(errno == EINVAL || errno == ENOSYS);
+#pragma clang diagnostic pop
 }
 
 TEST(sys_msg, msgsnd_failure) {
diff --git a/tests/sys_random_test.cpp b/tests/sys_random_test.cpp
index 2e2665b..e0cbf78 100644
--- a/tests/sys_random_test.cpp
+++ b/tests/sys_random_test.cpp
@@ -48,6 +48,8 @@
 }
 
 TEST(sys_random, getentropy_EFAULT) {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
 #if defined(HAVE_SYS_RANDOM)
   errno = 0;
   ASSERT_EQ(-1, getentropy(nullptr, 1));
@@ -55,6 +57,7 @@
 #else
   GTEST_SKIP() << "<sys/random.h> not available";
 #endif
+#pragma clang diagnostic pop
 }
 
 TEST(sys_random, getentropy_EIO) {
@@ -84,6 +87,8 @@
 }
 
 TEST(sys_random, getrandom_EFAULT) {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
 #if defined(HAVE_SYS_RANDOM)
   errno = 0;
   ASSERT_EQ(-1, getrandom(nullptr, 256, 0));
@@ -91,6 +96,7 @@
 #else
   GTEST_SKIP() << "<sys/random.h> not available";
 #endif
+#pragma clang diagnostic pop
 }
 
 TEST(sys_random, getrandom_EINVAL) {
diff --git a/tests/sys_sem_test.cpp b/tests/sys_sem_test.cpp
index b98926b..4bac92f 100644
--- a/tests/sys_sem_test.cpp
+++ b/tests/sys_sem_test.cpp
@@ -87,15 +87,21 @@
 }
 
 TEST(sys_sem, semop_failure) {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
   errno = 0;
   ASSERT_EQ(-1, semop(-1, nullptr, 0));
   ASSERT_TRUE(errno == EINVAL || errno == ENOSYS);
+#pragma clang diagnostic pop
 }
 
 TEST(sys_sem, semtimedop_failure) {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
   errno = 0;
   ASSERT_EQ(-1, semtimedop(-1, nullptr, 0, nullptr));
   ASSERT_TRUE(errno == EINVAL || errno == ENOSYS);
+#pragma clang diagnostic pop
 }
 
 TEST(sys_sem, union_semun) {
diff --git a/tests/sys_timex_test.cpp b/tests/sys_timex_test.cpp
index 1340ea4..44b73c9 100644
--- a/tests/sys_timex_test.cpp
+++ b/tests/sys_timex_test.cpp
@@ -27,21 +27,9 @@
   ASSERT_NE(-1, adjtimex(&t));
 }
 
-TEST(sys_timex, adjtimex_EFAULT) {
-  errno = 0;
-  ASSERT_EQ(-1, adjtimex(nullptr));
-  ASSERT_EQ(EFAULT, errno);
-}
-
 TEST(sys_timex, clock_adjtime_smoke) {
   timex t;
   memset(&t, 0, sizeof(t));
   // adjtimex/clock_adjtime return the clock state on success, -1 on failure.
   ASSERT_NE(-1, clock_adjtime(CLOCK_REALTIME, &t));
 }
-
-TEST(sys_timex, clock_adjtime_EFAULT) {
-  errno = 0;
-  ASSERT_EQ(-1, clock_adjtime(CLOCK_REALTIME, nullptr));
-  ASSERT_EQ(EFAULT, errno);
-}
diff --git a/tests/sys_wait_test.cpp b/tests/sys_wait_test.cpp
index c006972..200fabe 100644
--- a/tests/sys_wait_test.cpp
+++ b/tests/sys_wait_test.cpp
@@ -42,3 +42,22 @@
   ASSERT_EQ(66, si.si_status);
   ASSERT_EQ(CLD_EXITED, si.si_code);
 }
+
+// https://github.com/android/ndk/issues/1878
+TEST(sys_wait, macros) {
+#if defined(__GLIBC__)
+  // glibc before 2016 requires an lvalue.
+#else
+  ASSERT_FALSE(WIFEXITED(0x7f));
+  ASSERT_TRUE(WIFSTOPPED(0x7f));
+  ASSERT_FALSE(WIFCONTINUED(0x7f));
+
+  ASSERT_TRUE(WIFEXITED(0x80));
+  ASSERT_FALSE(WIFSTOPPED(0x80));
+  ASSERT_FALSE(WIFCONTINUED(0x80));
+
+  ASSERT_FALSE(WIFEXITED(0xffff));
+  ASSERT_FALSE(WIFSTOPPED(0xffff));
+  ASSERT_TRUE(WIFCONTINUED(0xffff));
+#endif
+}
diff --git a/tests/syslog_test.cpp b/tests/syslog_test.cpp
new file mode 100644
index 0000000..3ec3337
--- /dev/null
+++ b/tests/syslog_test.cpp
@@ -0,0 +1,74 @@
+/*
+ * Copyright (C) 2023 The Android Open Source Project
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *  * Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ *  * Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in
+ *    the documentation and/or other materials provided with the
+ *    distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
+ * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
+ * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
+ * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
+ * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <syslog.h>
+
+#include <errno.h>
+#include <gtest/gtest.h>
+
+#include "utils.h"
+
+TEST(syslog, syslog_percent_m) {
+  ExecTestHelper eth;
+  eth.Run(
+      [&]() {
+        openlog("foo", LOG_PERROR, LOG_AUTH);
+        errno = EINVAL;
+        syslog(LOG_ERR, "a b c: %m");
+        closelog();
+        exit(0);
+      },
+      0, "foo: a b c: Invalid argument\n");
+}
+
+TEST(syslog, syslog_empty) {
+  ExecTestHelper eth;
+  eth.Run(
+      [&]() {
+        openlog("foo", LOG_PERROR, LOG_AUTH);
+        errno = EINVAL;
+        syslog(LOG_ERR, "");
+        closelog();
+        exit(0);
+      },
+      0, "foo: \n");
+}
+
+TEST(syslog, syslog_truncation) {
+  ExecTestHelper eth;
+  eth.Run(
+      [&]() {
+        openlog("bar", LOG_PERROR, LOG_AUTH);
+        char too_long[2048] = {};
+        memset(too_long, 'x', sizeof(too_long) - 1);
+        syslog(LOG_ERR, "%s", too_long);
+        closelog();
+        exit(0);
+      },
+      0, "bar: x{1023}\n");
+}
diff --git a/tests/time_test.cpp b/tests/time_test.cpp
index f0ad937..d16600c 100644
--- a/tests/time_test.cpp
+++ b/tests/time_test.cpp
@@ -181,10 +181,25 @@
   ASSERT_NE(static_cast<time_t>(-1), mktime(&t));
   ASSERT_EQ(0, errno);
 
-  // This will overflow for LP32 or LP64.
+  // This will overflow for LP32.
   t.tm_year = INT_MAX;
 
   errno = 0;
+#if !defined(__LP64__)
+  ASSERT_EQ(static_cast<time_t>(-1), mktime(&t));
+  ASSERT_EQ(EOVERFLOW, errno);
+#else
+  ASSERT_EQ(static_cast<time_t>(67768036166016000U), mktime(&t));
+  ASSERT_EQ(0, errno);
+#endif
+
+  // This will overflow for LP32 or LP64.
+  // tm_year is int, this t struct points to INT_MAX + 1 no matter what TZ is.
+  t.tm_year = INT_MAX;
+  t.tm_mon = 11;
+  t.tm_mday = 45;
+
+  errno = 0;
   ASSERT_EQ(static_cast<time_t>(-1), mktime(&t));
   ASSERT_EQ(EOVERFLOW, errno);
 }
@@ -1254,8 +1269,39 @@
 TEST(time, timespec_get) {
 #if __BIONIC__
   timespec ts = {};
-  ASSERT_EQ(0, timespec_get(&ts, 123));
   ASSERT_EQ(TIME_UTC, timespec_get(&ts, TIME_UTC));
+  ASSERT_EQ(TIME_MONOTONIC, timespec_get(&ts, TIME_MONOTONIC));
+  ASSERT_EQ(TIME_ACTIVE, timespec_get(&ts, TIME_ACTIVE));
+  ASSERT_EQ(TIME_THREAD_ACTIVE, timespec_get(&ts, TIME_THREAD_ACTIVE));
+#else
+  GTEST_SKIP() << "glibc doesn't have timespec_get until 2.21";
+#endif
+}
+
+TEST(time, timespec_get_invalid) {
+#if __BIONIC__
+  timespec ts = {};
+  ASSERT_EQ(0, timespec_get(&ts, 123));
+#else
+  GTEST_SKIP() << "glibc doesn't have timespec_get until 2.21";
+#endif
+}
+
+TEST(time, timespec_getres) {
+#if __BIONIC__
+  timespec ts = {};
+  ASSERT_EQ(TIME_UTC, timespec_getres(&ts, TIME_UTC));
+  ASSERT_EQ(1, ts.tv_nsec);
+  ASSERT_EQ(0, ts.tv_sec);
+#else
+  GTEST_SKIP() << "glibc doesn't have timespec_get until 2.21";
+#endif
+}
+
+TEST(time, timespec_getres_invalid) {
+#if __BIONIC__
+  timespec ts = {};
+  ASSERT_EQ(0, timespec_getres(&ts, 123));
 #else
   GTEST_SKIP() << "glibc doesn't have timespec_get until 2.21";
 #endif
diff --git a/tests/unistd_test.cpp b/tests/unistd_test.cpp
index 2a36460..4c21627 100644
--- a/tests/unistd_test.cpp
+++ b/tests/unistd_test.cpp
@@ -589,9 +589,10 @@
   TestGetTidCachingWithFork(CloneAndSetTid, exit);
 }
 
+__attribute__((no_sanitize("hwaddress", "memtag")))
 static int CloneStartRoutine(int (*start_routine)(void*)) {
   void* child_stack[1024];
-  return clone(start_routine, untag_address(&child_stack[1024]), SIGCHLD, nullptr);
+  return clone(start_routine, &child_stack[1024], SIGCHLD, nullptr);
 }
 
 static int GetPidCachingCloneStartRoutine(void*) {
diff --git a/tests/utmp_test.cpp b/tests/utmp_test.cpp
index b024818..459f9c3 100644
--- a/tests/utmp_test.cpp
+++ b/tests/utmp_test.cpp
@@ -25,6 +25,7 @@
 }
 
 TEST(utmp, smoke) {
+  // The rest of <utmp.h> is just no-op implementations, so testing is trivial.
   ASSERT_EQ(-1, utmpname("hello"));
   setutent();
   ASSERT_EQ(NULL, getutent());
diff --git a/libc/bionic/timespec_get.cpp b/tests/utmpx_test.cpp
similarity index 76%
copy from libc/bionic/timespec_get.cpp
copy to tests/utmpx_test.cpp
index 7fc2182..55427a6 100644
--- a/libc/bionic/timespec_get.cpp
+++ b/tests/utmpx_test.cpp
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2018 The Android Open Source Project
+ * Copyright (C) 2023 The Android Open Source Project
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -26,8 +26,17 @@
  * SUCH DAMAGE.
  */
 
-#include <time.h>
+#include <gtest/gtest.h>
 
-int timespec_get(timespec* ts, int base) {
-  return (base == TIME_UTC && clock_gettime(CLOCK_REALTIME, ts) != -1) ? base : 0;
+#include <utmpx.h>
+
+TEST(utmpx, smoke) {
+  // Our utmpx "implementation" just calls the utmp no-op functions.
+  setutxent();
+  utmpx empty = {.ut_type = EMPTY};
+  ASSERT_EQ(NULL, getutxent());
+  ASSERT_EQ(NULL, getutxid(&empty));
+  ASSERT_EQ(NULL, getutxline(&empty));
+  endutxent();
+  ASSERT_EQ(NULL, pututxline(&empty));
 }
diff --git a/tests/wchar_test.cpp b/tests/wchar_test.cpp
index 16d4348..8716810 100644
--- a/tests/wchar_test.cpp
+++ b/tests/wchar_test.cpp
@@ -714,7 +714,8 @@
 #if defined(__BIONIC__)
   wchar_t* p;
   size_t size;
-
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wnonnull"
   // Invalid buffer.
   errno = 0;
   ASSERT_EQ(nullptr, open_wmemstream(nullptr, &size));
@@ -724,6 +725,7 @@
   errno = 0;
   ASSERT_EQ(nullptr, open_wmemstream(&p, nullptr));
   ASSERT_EQ(EINVAL, errno);
+#pragma clang diagnostic pop
 #else
   GTEST_SKIP() << "This test is bionic-specific";
 #endif