diff --git a/CMakeLists.txt b/CMakeLists.txt
index 921dc30593af5..e3131c42bccfd 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -265,11 +265,11 @@ set(SWIFT_ANDROID_DEPLOY_DEVICE_PATH "" CACHE STRING
   "Path on an Android device where build products will be pushed. These are used when running the test suite against the device")
 
 #
-# User-configurable ICU specific options for Android, FreeBSD, Linux and Haiku.
+# User-configurable ICU specific options for Android, FreeBSD, Linux, Haiku, and WebAssembly/WASI.
 #
 
-foreach(sdk ANDROID;FREEBSD;LINUX;WINDOWS;HAIKU)
-  foreach(arch aarch64;armv6;armv7;i686;powerpc64;powerpc64le;s390x;x86_64)
+foreach(sdk ANDROID;FREEBSD;LINUX;WINDOWS;HAIKU;WASI)
+  foreach(arch aarch64;armv6;armv7;i686;powerpc64;powerpc64le;s390x;wasm32;x86_64)
     set(SWIFT_${sdk}_${arch}_ICU_UC "" CACHE STRING
         "Path to a directory containing the icuuc library for ${sdk}")
     set(SWIFT_${sdk}_${arch}_ICU_UC_INCLUDE "" CACHE STRING
@@ -599,6 +599,8 @@ else()
     set(SWIFT_HOST_VARIANT_ARCH_default "powerpc64le")
   elseif("${CMAKE_SYSTEM_PROCESSOR}" STREQUAL "s390x")
     set(SWIFT_HOST_VARIANT_ARCH_default "s390x")
+  elseif("${CMAKE_SYSTEM_PROCESSOR}" STREQUAL "wasm32")
+    set(SWIFT_HOST_VARIANT_ARCH_default "wasm32")
   # FIXME: Only matches v6l/v7l - by far the most common variants
   elseif("${CMAKE_SYSTEM_PROCESSOR}" STREQUAL "armv6l")
     set(SWIFT_HOST_VARIANT_ARCH_default "armv6")
@@ -783,6 +785,14 @@ if(swift_build_windows AND NOT "${CMAKE_SYSTEM_NAME}" STREQUAL "Windows")
   configure_sdk_windows("Windows" "msvc" "${SWIFT_SDK_WINDOWS_ARCHITECTURES}")
 endif()
 
+is_sdk_requested(WASI swift_build_wasi)
+if(swift_build_wasi AND NOT "${SWIFT_HOST_VARIANT_SDK}" STREQUAL "WASI")
+  if("${SWIFT_SDK_WASI_ARCHITECTURES}" STREQUAL "")
+    set(SWIFT_SDK_WASI_ARCHITECTURES wasm32)
+  endif()
+  configure_sdk_unix("WASI" "${SWIFT_SDK_WASI_ARCHITECTURES}")
+endif()
+
 if("${SWIFT_SDKS}" STREQUAL "")
   set(SWIFT_SDKS "${SWIFT_CONFIGURED_SDKS}")
 endif()
diff --git a/cmake/modules/SwiftConfigureSDK.cmake b/cmake/modules/SwiftConfigureSDK.cmake
index f2fee24e5567d..a2c43e5b42cb6 100644
--- a/cmake/modules/SwiftConfigureSDK.cmake
+++ b/cmake/modules/SwiftConfigureSDK.cmake
@@ -214,6 +214,8 @@ macro(configure_sdk_unix name architectures)
   set(SWIFT_SDK_${prefix}_ARCHITECTURES "${architectures}")
   if("${prefix}" STREQUAL "CYGWIN")
     set(SWIFT_SDK_${prefix}_OBJECT_FORMAT "COFF")
+  elseif("${prefix}" STREQUAL "WASI")
+    set(SWIFT_SDK_${prefix}_OBJECT_FORMAT "WASM")
   else()
     set(SWIFT_SDK_${prefix}_OBJECT_FORMAT "ELF")
   endif()
@@ -330,6 +332,14 @@ macro(configure_sdk_unix name architectures)
           message(FATAL_ERROR "unsupported arch for Haiku: ${arch}")
         endif()
         set(SWIFT_SDK_HAIKU_ARCH_x86_64_TRIPLE "x86_64-unknown-haiku")
+      elseif("${prefix}" STREQUAL "WASI")
+        if(NOT arch STREQUAL wasm32)
+          message(FATAL_ERROR "unsupported arch for WASI: ${arch}")
+        endif()
+        set(SWIFT_SDK_WASI_ARCH_wasm32_PATH "${SWIFT_WASI_SYSROOT}")
+        set(SWIFT_SDK_WASI_ARCH_wasm32_TRIPLE "wasm32-unknown-wasi")
+        set(SWIFT_SDK_WASI_ARCH_wasm32_LIBC_INCLUDE_DIRECTORY "${SWIFT_WASI_SYSROOT}/include")
+        set(SWIFT_SDK_WASI_ARCH_wasm32_LIBC_ARCHITECTURE_INCLUDE_DIRECTORY "${SWIFT_WASI_SYSROOT}/include")
       else()
         message(FATAL_ERROR "unknown Unix OS: ${prefix}")
       endif()
diff --git a/cmake/modules/SwiftSetIfArchBitness.cmake b/cmake/modules/SwiftSetIfArchBitness.cmake
index 9983cad817169..b48a6388f01b3 100644
--- a/cmake/modules/SwiftSetIfArchBitness.cmake
+++ b/cmake/modules/SwiftSetIfArchBitness.cmake
@@ -12,7 +12,8 @@ function(set_if_arch_bitness var_name)
      "${SIA_ARCH}" STREQUAL "armv6" OR
      "${SIA_ARCH}" STREQUAL "armv7" OR
      "${SIA_ARCH}" STREQUAL "armv7k" OR
-     "${SIA_ARCH}" STREQUAL "armv7s")
+     "${SIA_ARCH}" STREQUAL "armv7s" OR
+     "${SIA_ARCH}" STREQUAL "wasm32")
     set("${var_name}" "${SIA_CASE_32_BIT}" PARENT_SCOPE)
   elseif("${SIA_ARCH}" STREQUAL "x86_64" OR
          "${SIA_ARCH}" STREQUAL "arm64" OR
diff --git a/stdlib/private/SwiftPrivateThreadExtras/CMakeLists.txt b/stdlib/private/SwiftPrivateThreadExtras/CMakeLists.txt
index 4e9b794a716c3..aaa11024605d9 100644
--- a/stdlib/private/SwiftPrivateThreadExtras/CMakeLists.txt
+++ b/stdlib/private/SwiftPrivateThreadExtras/CMakeLists.txt
@@ -14,6 +14,7 @@ add_swift_target_library(swiftSwiftPrivateThreadExtras ${SWIFT_STDLIB_LIBRARY_BU
   SWIFT_MODULE_DEPENDS_FREEBSD Glibc
   SWIFT_MODULE_DEPENDS_CYGWIN Glibc
   SWIFT_MODULE_DEPENDS_HAIKU Glibc
+  SWIFT_MODULE_DEPENDS_WASI Glibc
   SWIFT_MODULE_DEPENDS_WINDOWS MSVCRT WinSDK
   SWIFT_COMPILE_FLAGS ${SWIFT_STANDARD_LIBRARY_SWIFT_FLAGS}
   TARGET_SDKS ALL_APPLE_PLATFORMS CYGWIN FREEBSD HAIKU LINUX WINDOWS ANDROID
diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt
index d721eed76cd57..5f1567768d7dc 100644
--- a/test/CMakeLists.txt
+++ b/test/CMakeLists.txt
@@ -94,7 +94,8 @@ function(get_test_dependencies SDK result_var_name)
      ("${SDK}" STREQUAL "FREEBSD") OR
      ("${SDK}" STREQUAL "ANDROID") OR
      ("${SDK}" STREQUAL "WINDOWS") OR
-     ("${SDK}" STREQUAL "HAIKU"))
+     ("${SDK}" STREQUAL "HAIKU") OR
+     ("${SDK}" STREQUAL "WASI"))
     # No extra dependencies.
   else()
     message(FATAL_ERROR "Unknown SDK: ${SDK}")
diff --git a/utils/build-script b/utils/build-script
index aa79436709f7f..1ecfdfeb508e1 100755
--- a/utils/build-script
+++ b/utils/build-script
@@ -317,6 +317,14 @@ def apply_default_arguments(toolchain, args):
             args.stdlib_deployment_targets.append(
                 StdlibDeploymentTarget.Android.aarch64.name)
 
+    if args.wasi:
+        args.build_swift_static_stdlib = True
+        args.build_dynamic_stdlib = False
+        args.build_swift_static_sdk_overlay = True
+        args.build_swift_dynamic_sdk_overlay = False
+        args.stdlib_deployment_targets.append(
+            StdlibDeploymentTarget.WASI.wasm32.name)
+
     # Infer platform flags from manually-specified configure targets.
     # This doesn't apply to Darwin platforms, as they are
     # already configured. No building without the platform flag, though.
@@ -588,6 +596,8 @@ class BuildScriptInvocation(object):
             impl_args += ["--skip-build-watchos-simulator"]
         if not args.build_android:
             impl_args += ["--skip-build-android"]
+        if not args.build_wasi:
+            impl_args += ["--skip-build-wasi"]
         if not args.build_clang_tools_extra:
             impl_args += ["--skip-build-clang-tools-extra"]
 
@@ -629,6 +639,8 @@ class BuildScriptInvocation(object):
             impl_args += ["--skip-test-android"]
         if not args.test_android_host:
             impl_args += ["--skip-test-android-host"]
+        if not args.test_wasi:
+            impl_args += ["--skip-test-wasi"]
         if args.build_runtime_with_host_compiler:
             impl_args += ["--build-runtime-with-host-compiler"]
         if args.validation_test:
diff --git a/utils/build-script-impl b/utils/build-script-impl
index febc5d8647805..e4d95e5606227 100755
--- a/utils/build-script-impl
+++ b/utils/build-script-impl
@@ -153,6 +153,7 @@ KNOWN_SETTINGS=(
     skip-test-osx                                 ""                "set to skip testing Swift stdlibs for OS X"
     skip-test-tvos-host                           ""                "set to skip testing the host parts of the tvOS toolchain"
     skip-test-tvos-simulator                      ""                "set to skip testing Swift stdlibs for tvOS simulators (i.e. test devices only)"
+    skip-test-wasi                                ""                "set to skip testing Swift stdlibs for WebAssembly/WASI"
     skip-test-watchos-host                        ""                "set to skip testing the host parts of the watchOS toolchain"
     skip-test-watchos-simulator                   ""                "set to skip testing Swift stdlibs for Apple watchOS simulators (i.e. test devices only)"
     skip-test-benchmarks                          ""                "set to skip running Swift Benchmark Suite"
diff --git a/utils/build_swift/build_swift/driver_arguments.py b/utils/build_swift/build_swift/driver_arguments.py
index ba5d6385a02b6..062c15cc9827a 100644
--- a/utils/build_swift/build_swift/driver_arguments.py
+++ b/utils/build_swift/build_swift/driver_arguments.py
@@ -147,6 +147,9 @@ def _apply_default_arguments(args):
     if not args.android or not args.build_android:
         args.build_android = False
 
+    if not args.wasi or not args.build_wasi:
+        args.build_wasi = False
+
     # --test-paths implies --test and/or --validation-test
     # depending on what directories/files have been specified.
     if args.test_paths:
@@ -183,6 +186,7 @@ def _apply_default_arguments(args):
         args.test_tvos = False
         args.test_watchos = False
         args.test_android = False
+        args.test_wasi = False
         args.test_swiftpm = False
         args.test_swiftsyntax = False
         args.test_indexstoredb = False
@@ -233,6 +237,12 @@ def _apply_default_arguments(args):
     if not args.test_android:
         args.test_android_host = False
 
+    if not args.build_wasi:
+        args.test_wasi = False
+
+    if not args.test_wasi:
+        args.test_wasi = False
+
     if not args.host_test:
         args.test_ios_host = False
         args.test_tvos_host = False
@@ -326,6 +336,9 @@ def create_argument_parser():
     option('--android', toggle_true,
            help='also build for Android')
 
+    option('--wasi', toggle_true,
+           help='also build for WebAssembly/WASI')
+
     option('--swift-analyze-code-coverage', store,
            choices=['false', 'not-merged', 'merged'],
            # so CMake can see the inert mode as a false value
@@ -932,6 +945,9 @@ def create_argument_parser():
     option('--skip-build-android', toggle_false('build_android'),
            help='skip building Swift stdlibs for Android')
 
+    option('--skip-build-wasi', toggle_false('build_wasi'),
+           help='skip building Swift stdlibs for WebAssembly/WASI')
+
     option('--skip-build-benchmarks', toggle_false('build_benchmarks'),
            help='skip building Swift Benchmark Suite')
 
@@ -988,6 +1004,10 @@ def create_argument_parser():
            help='skip testing Android device targets on the host machine (the '
                 'phone itself)')
 
+    option('--skip-test-wasi',
+           toggle_false('test_wasi'),
+           help='skip testing all WebAssembly/WASI targets.')
+
     option('--skip-test-swiftpm', toggle_false('test_swiftpm'),
            help='skip testing swiftpm')
     option('--skip-test-swiftsyntax', toggle_false('test_swiftsyntax'),
@@ -1011,7 +1031,7 @@ def create_argument_parser():
     in_group('Build settings specific for LLVM')
 
     option('--llvm-targets-to-build', store,
-           default='X86;ARM;AArch64;PowerPC;SystemZ;Mips',
+           default='X86;ARM;AArch64;PowerPC;SystemZ;Mips;WebAssembly',
            help='LLVM target generators to build')
 
     # -------------------------------------------------------------------------
diff --git a/utils/swift_build_support/swift_build_support/host_specific_configuration.py b/utils/swift_build_support/swift_build_support/host_specific_configuration.py
index ad50abbac5213..a5d0075e2ac82 100644
--- a/utils/swift_build_support/swift_build_support/host_specific_configuration.py
+++ b/utils/swift_build_support/swift_build_support/host_specific_configuration.py
@@ -243,6 +243,8 @@ def __platforms_to_skip_test(self, args):
                 StdlibDeploymentTarget.AppleWatchSimulator)
         if not args.test_android:
             platforms_to_skip_test.add(StdlibDeploymentTarget.Android)
+        if not args.test_wasi:
+            platforms_to_skip_test.add(StdlibDeploymentTarget.WASI)
 
         return platforms_to_skip_test
 
diff --git a/utils/swift_build_support/swift_build_support/targets.py b/utils/swift_build_support/swift_build_support/targets.py
index 18721d60eb0dd..f29bc1b5427a8 100644
--- a/utils/swift_build_support/swift_build_support/targets.py
+++ b/utils/swift_build_support/swift_build_support/targets.py
@@ -158,6 +158,8 @@ class StdlibDeploymentTarget(object):
 
     Haiku = Platform("haiku", archs=["x86_64"])
 
+    WASI = Platform("wasi", archs=["wasm32"])
+
     # The list of known platforms.
     known_platforms = [
         OSX,
@@ -169,7 +171,8 @@ class StdlibDeploymentTarget(object):
         Cygwin,
         Android,
         Windows,
-        Haiku]
+        Haiku,
+        WASI]
 
     # Cache of targets by name.
     _targets_by_name = dict((target.name, target)
@@ -233,6 +236,10 @@ def host_target():
             if machine == 'x86_64':
                 return StdlibDeploymentTarget.Haiku.x86_64
 
+        elif system == 'WASI':
+            if machine == 'wasm32':
+                return StdlibDeploymentTarget.WASI.wasm32
+
         raise NotImplementedError('System "%s" with architecture "%s" is not '
                                   'supported' % (system, machine))