diff --git a/core/modules/simpletest/src/Tests/BrowserTest.php b/core/modules/simpletest/src/Tests/BrowserTest.php
index 7cde7e0d316b9a795b3dcaf527654cf764627755..b20ab75fe5ade95dd1de2e408d05d725aaa3b24e 100644
--- a/core/modules/simpletest/src/Tests/BrowserTest.php
+++ b/core/modules/simpletest/src/Tests/BrowserTest.php
@@ -8,6 +8,7 @@
  * Tests the internal browser of the testing framework.
  *
  * @group simpletest
+ * @group WebTestBase
  */
 class BrowserTest extends WebTestBase {
 
diff --git a/core/modules/simpletest/src/Tests/InstallationProfileModuleTestsTest.php b/core/modules/simpletest/src/Tests/InstallationProfileModuleTestsTest.php
deleted file mode 100644
index 113748f18d5ec2bb0c4fedb337c83cceebb2b29f..0000000000000000000000000000000000000000
--- a/core/modules/simpletest/src/Tests/InstallationProfileModuleTestsTest.php
+++ /dev/null
@@ -1,70 +0,0 @@
-<?php
-
-namespace Drupal\simpletest\Tests;
-
-use Drupal\simpletest\WebTestBase;
-
-/**
- * Verifies that tests bundled with installation profile modules are found.
- *
- * @group simpletest
- */
-class InstallationProfileModuleTestsTest extends WebTestBase {
-
-  /**
-   * Modules to enable.
-   *
-   * @var array
-   */
-  public static $modules = ['simpletest'];
-
-  /**
-   * An administrative user with permission to administer unit tests.
-   *
-   * @var \Drupal\user\UserInterface
-   */
-  protected $adminUser;
-
-  /**
-   * Use the Testing profile.
-   *
-   * The Testing profile contains drupal_system_listing_compatible_test.test,
-   * which attempts to:
-   * - run tests using the Minimal profile (which does not contain the
-   *   drupal_system_listing_compatible_test.module)
-   * - but still install the drupal_system_listing_compatible_test.module
-   *   contained in the Testing profile.
-   *
-   * @see \Drupal\Tests\drupal_system_listing_compatible_test\Kernel\SystemListingCrossProfileCompatibleTest
-   *
-   * @var string
-   */
-  protected $profile = 'testing';
-
-  protected function setUp() {
-    parent::setUp();
-
-    $this->adminUser = $this->drupalCreateUser(['administer unit tests']);
-    $this->drupalLogin($this->adminUser);
-  }
-
-  /**
-   * Tests existence of test case located in an installation profile module.
-   */
-  public function testInstallationProfileTests() {
-    $this->drupalGet('admin/config/development/testing');
-    $this->assertText('Drupal\Tests\drupal_system_listing_compatible_test\Kernel\SystemListingCrossProfileCompatibleTest');
-    $edit = [
-      'tests[Drupal\Tests\drupal_system_listing_compatible_test\Kernel\SystemListingCrossProfileCompatibleTest]' => TRUE,
-    ];
-    $this->drupalPostForm(NULL, $edit, t('Run tests'));
-
-    // Verifies that tests in installation profile modules are passed.
-    $element = $this->xpath('//tr[contains(@class, :class)]/td[contains(text(), :value)]', [
-      ':class' => 'simpletest-pass',
-      ':value' => 'Drupal\Tests\drupal_system_listing_compatible_test\Kernel\SystemListingCrossProfileCompatibleTest',
-    ]);
-    $this->assertTrue(!empty($element));
-  }
-
-}
diff --git a/core/modules/simpletest/src/Tests/MissingCheckedRequirementsTest.php b/core/modules/simpletest/src/Tests/MissingCheckedRequirementsTest.php
index d6fe19964a09f0eda764906154f7c462fcde1332..ae9d6f7291ceb3dcef6f36af1505300154ea8980 100644
--- a/core/modules/simpletest/src/Tests/MissingCheckedRequirementsTest.php
+++ b/core/modules/simpletest/src/Tests/MissingCheckedRequirementsTest.php
@@ -8,6 +8,7 @@
  * Tests a test case with missing requirements.
  *
  * @group simpletest
+ * @group WebTestBase
  */
 class MissingCheckedRequirementsTest extends WebTestBase {
 
diff --git a/core/modules/simpletest/src/Tests/SimpleTestBrowserTest.php b/core/modules/simpletest/src/Tests/SimpleTestBrowserTest.php
index 8131227a55076ed538e59ea6989a17555abfbc96..0aeceaf58cba73cd2752bb9144d7e0b5efec6762 100644
--- a/core/modules/simpletest/src/Tests/SimpleTestBrowserTest.php
+++ b/core/modules/simpletest/src/Tests/SimpleTestBrowserTest.php
@@ -4,12 +4,12 @@
 
 use Drupal\Core\Url;
 use Drupal\simpletest\WebTestBase;
-use Drupal\Tests\simpletest\Functional\ThroughUITest;
 
 /**
- * Tests the Simpletest UI internal browser.
+ * Tests the WebTestBase internal browser.
  *
  * @group simpletest
+ * @group WebTestBase
  */
 class SimpleTestBrowserTest extends WebTestBase {
 
@@ -116,33 +116,4 @@ public function testUserAgentValidation() {
     $this->assertResponse(403, 'Requesting https.php with a normal User-Agent fails.');
   }
 
-  /**
-   * Tests that PHPUnit and KernelTestBase tests work through the UI.
-   */
-  public function testTestingThroughUI() {
-    $this->drupalGet('admin/config/development/testing');
-    $this->assertTrue(strpos($this->drupalSettings['simpleTest']['images'][0], 'core/misc/menu-collapsed.png') > 0, 'drupalSettings contains a link to core/misc/menu-collapsed.png.');
-    // We can not test WebTestBase tests here since they require a valid .htkey
-    // to be created. However this scenario is covered by the testception of
-    // \Drupal\simpletest\Tests\SimpleTestTest.
-
-    $tests = [
-      // A KernelTestBase test.
-      'Drupal\KernelTests\KernelTestBaseTest',
-      // A PHPUnit unit test.
-      'Drupal\Tests\action\Unit\Menu\ActionLocalTasksTest',
-      // A PHPUnit functional test.
-      ThroughUITest::class,
-    ];
-
-    foreach ($tests as $test) {
-      $this->drupalGet('admin/config/development/testing');
-      $edit = [
-        "tests[$test]" => TRUE,
-      ];
-      $this->drupalPostForm(NULL, $edit, t('Run tests'));
-      $this->assertText('0 fails, 0 exceptions');
-    }
-  }
-
 }
diff --git a/core/modules/simpletest/src/Tests/SimpleTestInstallBatchTest.php b/core/modules/simpletest/src/Tests/SimpleTestInstallBatchTest.php
index 5663ad9cdc780d096688da3978aa23bdea267fe0..18f86bef2fa080fcc4c3c41cca355ad3a1c8b3ca 100644
--- a/core/modules/simpletest/src/Tests/SimpleTestInstallBatchTest.php
+++ b/core/modules/simpletest/src/Tests/SimpleTestInstallBatchTest.php
@@ -12,6 +12,10 @@
  * installation when running tests.
  *
  * @group simpletest
+ * @group WebTestBase
+ * @group FunctionalTestSetupTrait
+ *
+ * @see \Drupal\FunctionalTests\Core\Test\ModuleInstallBatchTest
  */
 class SimpleTestInstallBatchTest extends WebTestBase {
 
@@ -20,10 +24,10 @@ class SimpleTestInstallBatchTest extends WebTestBase {
    *
    * @var array
    */
-  public static $modules = ['simpletest', 'simpletest_test', 'entity_test'];
+  public static $modules = ['test_batch_test', 'entity_test'];
 
   /**
-   * Tests loading entities created in a batch in simpletest_test_install().
+   * Tests loading entities created in a batch in test_batch_test_install().
    */
   public function testLoadingEntitiesCreatedInBatch() {
     $entity1 = EntityTest::load(1);
diff --git a/core/modules/simpletest/src/Tests/SimpleTestTest.php b/core/modules/simpletest/src/Tests/SimpleTestTest.php
index 42759c255ae2d7daaf04b00ce6d4ebf098ac8f77..942902c9888a15321bef14fd8bb90c2bc52b75bc 100644
--- a/core/modules/simpletest/src/Tests/SimpleTestTest.php
+++ b/core/modules/simpletest/src/Tests/SimpleTestTest.php
@@ -12,6 +12,7 @@
  * internal browser and APIs implicitly.
  *
  * @group simpletest
+ * @group WebTestBase
  */
 class SimpleTestTest extends WebTestBase {
 
diff --git a/core/modules/simpletest/src/Tests/SkipRequiredModulesTest.php b/core/modules/simpletest/src/Tests/SkipRequiredModulesTest.php
index c68237c4dccaf4af71d95a7db4e0cf40c3dd0761..907d4672e53576ff9376bcae5597fb2a302c59f7 100644
--- a/core/modules/simpletest/src/Tests/SkipRequiredModulesTest.php
+++ b/core/modules/simpletest/src/Tests/SkipRequiredModulesTest.php
@@ -11,9 +11,13 @@
  * This means that if you specify this test to run-tests.sh with --class or
  * --file, this test will run and fail.
  *
+ * Only WebTestBase tests are skipped by TestDiscovery. Other tests use the
+ * PHPUnit @-require module annotation.
+ *
  * @dependencies module_does_not_exist
  *
  * @group simpletest
+ * @group WebTestBase
  *
  * @todo Change or remove this test when Simpletest-based tests are able to skip
  *       themselves based on requirements.
diff --git a/core/modules/simpletest/src/Tests/TimeZoneTest.php b/core/modules/simpletest/src/Tests/TimeZoneTest.php
index 9a98c790205645ce2df7c755349f04c6e65ca50f..8f16ec5d9410b036852f5826a8a013c52038f07f 100644
--- a/core/modules/simpletest/src/Tests/TimeZoneTest.php
+++ b/core/modules/simpletest/src/Tests/TimeZoneTest.php
@@ -5,9 +5,10 @@
 use Drupal\simpletest\WebTestBase;
 
 /**
- * This test will check SimpleTest's default time zone handling.
+ * This test will check WebTestBase's default time zone handling.
  *
  * @group simpletest
+ * @group WebTestBase
  */
 class TimeZoneTest extends WebTestBase {
 
diff --git a/core/modules/simpletest/src/Tests/WebTestBaseInstallTest.php b/core/modules/simpletest/src/Tests/WebTestBaseInstallTest.php
index 857e3a33b91422e833d4e6d161f3826593cad3cf..bfb1e0c9e6d3d99482f846c7197eb041bafaaabb 100644
--- a/core/modules/simpletest/src/Tests/WebTestBaseInstallTest.php
+++ b/core/modules/simpletest/src/Tests/WebTestBaseInstallTest.php
@@ -8,6 +8,7 @@
  * Tests the test-specifics customisations done in the installation.
  *
  * @group simpletest
+ * @group WebTestBase
  */
 class WebTestBaseInstallTest extends WebTestBase {
 
diff --git a/core/modules/simpletest/tests/src/Functional/SimpletestUiTest.php b/core/modules/simpletest/tests/src/Functional/SimpletestUiTest.php
new file mode 100644
index 0000000000000000000000000000000000000000..048ed2738949c46b4cabb04698ad66c585cf096a
--- /dev/null
+++ b/core/modules/simpletest/tests/src/Functional/SimpletestUiTest.php
@@ -0,0 +1,62 @@
+<?php
+
+namespace Drupal\Tests\simpletest\Functional;
+
+use Drupal\Core\Url;
+use Drupal\KernelTests\KernelTestBaseTest;
+use Drupal\Tests\action\Unit\Menu\ActionLocalTasksTest;
+use Drupal\Tests\BrowserTestBase;
+
+/**
+ * Test various aspects of testing through the UI form.
+ *
+ * @group simpletest
+ */
+class SimpletestUiTest extends BrowserTestBase {
+
+  /**
+   * {@inheritdoc}
+   */
+  public static $modules = ['simpletest'];
+
+  /**
+   * {@inheritdoc}
+   */
+  protected function setUp() {
+    parent::setUp();
+    $this->drupalLogin($this->createUser(['administer unit tests']));
+  }
+
+  /**
+   * Tests that unit, kernel, and functional tests work through the UI.
+   */
+  public function testTestingThroughUI() {
+    $url = Url::fromRoute('simpletest.test_form');
+    $assertion = $this->assertSession();
+
+    $this->drupalGet($url);
+    $settings = $this->getDrupalSettings();
+    $this->assertTrue(strpos($settings['simpleTest']['images'][0], 'core/misc/menu-collapsed.png') > 0, 'drupalSettings contains a link to core/misc/menu-collapsed.png.');
+
+    // We can not test WebTestBase tests here since they require a valid .htkey
+    // to be created. However this scenario is covered by the testception of
+    // \Drupal\simpletest\Tests\SimpleTestTest.
+    $tests = [
+      // A KernelTestBase test.
+      KernelTestBaseTest::class,
+      // A PHPUnit unit test.
+      ActionLocalTasksTest::class,
+      // A PHPUnit functional test.
+      ThroughUITest::class,
+    ];
+
+    foreach ($tests as $test) {
+      $edit = [
+        "tests[$test]" => TRUE,
+      ];
+      $this->drupalPostForm($url, $edit, t('Run tests'));
+      $assertion->pageTextContains('0 fails, 0 exceptions');
+    }
+  }
+
+}
diff --git a/core/modules/simpletest/tests/src/Unit/SimpletestUiPrinterTest.php b/core/modules/simpletest/tests/src/Unit/SimpletestUiPrinterTest.php
new file mode 100644
index 0000000000000000000000000000000000000000..d9c4730f296c1e1744e0aac178b02de61692753a
--- /dev/null
+++ b/core/modules/simpletest/tests/src/Unit/SimpletestUiPrinterTest.php
@@ -0,0 +1,45 @@
+<?php
+
+namespace Drupal\Tests\simpletest\Unit;
+
+use Drupal\Tests\Listeners\SimpletestUiPrinter;
+use Drupal\Tests\UnitTestCase;
+
+/**
+ * @coversDefaultClass \Drupal\Tests\Listeners\SimpletestUiPrinter
+ *
+ * @group simpletest
+ */
+class SimpletestUiPrinterTest extends UnitTestCase {
+
+  /**
+   * Data provider for testWrite().
+   *
+   * @return string[]
+   *   Array of data for testWrite().
+   *   - Expected output from SimpletestUiPrinter->write().
+   *   - Buffer to pass into SimpletestUiPrinter->write().
+   */
+  public function provideBuffer() {
+    return [
+      ['&amp;&quot;&#039;&lt;&gt;', '&"\'<>'],
+      ['<a href="http:////www.example.com" target="_blank" title="http:////www.example.com">http:////www.example.com</a>', 'http:////www.example.com'],
+      ['this is some text <a href="http://www.example.com/" target="_blank" title="http://www.example.com/">http://www.example.com/</a> with a link in it.', 'this is some text http://www.example.com/ with a link in it.'],
+      ["HTML output was generated<br />\n", "HTML output was generated\n"],
+    ];
+  }
+
+  /**
+   * @covers ::write
+   *
+   * @dataProvider provideBuffer
+   */
+  public function testWrite($expected, $buffer) {
+    $printer = new SimpletestUiPrinter();
+    // Set up our expectation.
+    $this->expectOutputString($expected);
+    // Write the buffer.
+    $printer->write($buffer);
+  }
+
+}
diff --git a/core/modules/simpletest/tests/src/Unit/TestBaseTest.php b/core/modules/simpletest/tests/src/Unit/TestBaseTest.php
index cdfe9869b59c873096c9466357d2630e1fae9a78..12deceb997e16869617be93204524092f1efeadc 100644
--- a/core/modules/simpletest/tests/src/Unit/TestBaseTest.php
+++ b/core/modules/simpletest/tests/src/Unit/TestBaseTest.php
@@ -8,6 +8,7 @@
  * @requires extension curl
  * @coversDefaultClass \Drupal\simpletest\TestBase
  * @group simpletest
+ * @group TestBase
  */
 class TestBaseTest extends UnitTestCase {
 
diff --git a/core/modules/simpletest/tests/src/Unit/TestDiscoveryTest.php b/core/modules/simpletest/tests/src/Unit/TestDiscoveryTest.php
index 74e86846e464ea47f2e227c6b1a53e9693aa8500..0d2843e97aa0d687f71b621d86ac573006f61558 100644
--- a/core/modules/simpletest/tests/src/Unit/TestDiscoveryTest.php
+++ b/core/modules/simpletest/tests/src/Unit/TestDiscoveryTest.php
@@ -3,6 +3,8 @@
 namespace Drupal\Tests\simpletest\Unit;
 
 use Composer\Autoload\ClassLoader;
+use Drupal\Core\DependencyInjection\Container;
+use Drupal\Core\DrupalKernel;
 use Drupal\Core\Extension\Extension;
 use Drupal\Core\Extension\ModuleHandlerInterface;
 use Drupal\simpletest\Exception\MissingGroupException;
@@ -272,6 +274,18 @@ protected function setupVfsWithTestClasses() {
  * @group example
  */
 class FunctionalExampleTest {}
+EOF;
+
+    $test_profile_info = <<<EOF
+name: Testing
+type: profile
+core: 8.x
+EOF;
+
+    $test_module_info = <<<EOF
+name: Testing
+type: module
+core: 8.x
 EOF;
 
     vfsStream::create([
@@ -293,6 +307,23 @@ class FunctionalExampleTest {}
           ],
         ],
       ],
+      'profiles' => [
+        'test_profile' => [
+          'test_profile.info.yml' => $test_profile_info,
+          'modules' => [
+            'test_profile_module' => [
+              'test_profile_module.info.yml' => $test_module_info,
+              'tests' => [
+                'src' => [
+                  'Kernel' => [
+                    'KernelExampleTest4.php' => str_replace(['FunctionalExampleTest', '@group example'], ['KernelExampleTest4', '@group example3'], $test_file),
+                  ],
+                ],
+              ],
+            ],
+          ],
+        ],
+      ],
     ]);
   }
 
@@ -350,10 +381,11 @@ public function testGetTestClassesWithSelectedTypes() {
 
     $extensions = [
       'test_module' => new Extension('vfs://drupal', 'module', 'modules/test_module/test_module.info.yml'),
+      'test_profile_module' => new Extension('vfs://drupal', 'profile', 'profiles/test_profile/modules/test_profile_module/test_profile_module.info.yml'),
     ];
     $test_discovery->setExtensions($extensions);
     $result = $test_discovery->getTestClasses(NULL, ['PHPUnit-Kernel']);
-    $this->assertCount(2, $result);
+    $this->assertCount(3, $result);
     $this->assertEquals([
       'example' => [],
       'example2' => [
@@ -364,9 +396,46 @@ public function testGetTestClassesWithSelectedTypes() {
           'type' => 'PHPUnit-Kernel',
         ],
       ],
+      'example3' => [
+        'Drupal\Tests\test_profile_module\Kernel\KernelExampleTest4' => [
+          'name' => 'Drupal\Tests\test_profile_module\Kernel\KernelExampleTest4',
+          'description' => 'Test description',
+          'group' => 'example3',
+          'type' => 'PHPUnit-Kernel',
+        ],
+      ],
     ], $result);
   }
 
+  /**
+   * @covers ::getTestClasses
+   */
+  public function testGetTestsInProfiles() {
+    $this->setupVfsWithTestClasses();
+    $class_loader = $this->prophesize(ClassLoader::class);
+    $module_handler = $this->prophesize(ModuleHandlerInterface::class);
+
+    $container = new Container();
+    $container->set('kernel', new DrupalKernel('prod', new ClassLoader()));
+    $container->set('site.path', 'sites/default');
+    \Drupal::setContainer($container);
+
+    $test_discovery = new TestDiscovery('vfs://drupal', $class_loader->reveal(), $module_handler->reveal());
+
+    $result = $test_discovery->getTestClasses(NULL, ['PHPUnit-Kernel']);
+    $expected = [
+      'example3' => [
+        'Drupal\Tests\test_profile_module\Kernel\KernelExampleTest4' => [
+          'name' => 'Drupal\Tests\test_profile_module\Kernel\KernelExampleTest4',
+          'description' => 'Test description',
+          'group' => 'example3',
+          'type' => 'PHPUnit-Kernel',
+        ],
+      ],
+    ];
+    $this->assertEquals($expected, $result);
+  }
+
   /**
    * @covers ::getPhpunitTestSuite
    * @dataProvider providerTestGetPhpunitTestSuite
diff --git a/core/modules/simpletest/tests/src/Unit/WebTestBaseTest.php b/core/modules/simpletest/tests/src/Unit/WebTestBaseTest.php
index df909560a117929ae5819529242939fc80bb36c4..c55c3e215fc65b46750c76045e3961c4ad83c133 100644
--- a/core/modules/simpletest/tests/src/Unit/WebTestBaseTest.php
+++ b/core/modules/simpletest/tests/src/Unit/WebTestBaseTest.php
@@ -8,6 +8,7 @@
  * @requires extension curl
  * @coversDefaultClass \Drupal\simpletest\WebTestBase
  * @group simpletest
+ * @group WebTestBase
  */
 class WebTestBaseTest extends UnitTestCase {
 
diff --git a/core/modules/simpletest/tests/modules/phpunit_test/phpunit_test.info.yml b/core/modules/system/tests/modules/phpunit_test/phpunit_test.info.yml
similarity index 100%
rename from core/modules/simpletest/tests/modules/phpunit_test/phpunit_test.info.yml
rename to core/modules/system/tests/modules/phpunit_test/phpunit_test.info.yml
diff --git a/core/modules/simpletest/tests/modules/phpunit_test/src/PhpUnitTestDummyClass.php b/core/modules/system/tests/modules/phpunit_test/src/PhpUnitTestDummyClass.php
similarity index 100%
rename from core/modules/simpletest/tests/modules/phpunit_test/src/PhpUnitTestDummyClass.php
rename to core/modules/system/tests/modules/phpunit_test/src/PhpUnitTestDummyClass.php
diff --git a/core/modules/simpletest/tests/modules/simpletest_test/simpletest_test.info.yml b/core/modules/system/tests/modules/test_batch_test/test_batch_test.info.yml
similarity index 52%
rename from core/modules/simpletest/tests/modules/simpletest_test/simpletest_test.info.yml
rename to core/modules/system/tests/modules/test_batch_test/test_batch_test.info.yml
index 3f62800d68b799e2707f3c49da77b39e6af5bf37..bc4a3eef2297512a566ace275966ffec00d6b1d5 100644
--- a/core/modules/simpletest/tests/modules/simpletest_test/simpletest_test.info.yml
+++ b/core/modules/system/tests/modules/test_batch_test/test_batch_test.info.yml
@@ -1,6 +1,6 @@
-name: 'Simpletest test'
+name: 'Test install batch test'
 type: module
-description: 'Support module for Simpletest tests.'
+description: 'Support module for functional tests.'
 package: Testing
 version: VERSION
 core: 8.x
diff --git a/core/modules/simpletest/tests/modules/simpletest_test/simpletest_test.install b/core/modules/system/tests/modules/test_batch_test/test_batch_test.install
similarity index 77%
rename from core/modules/simpletest/tests/modules/simpletest_test/simpletest_test.install
rename to core/modules/system/tests/modules/test_batch_test/test_batch_test.install
index aabe921f59095f35035bb1abd043cbc4da252c5a..d98049ebdbebb7105f0ab1967562eef1c5224006 100644
--- a/core/modules/simpletest/tests/modules/simpletest_test/simpletest_test.install
+++ b/core/modules/system/tests/modules/test_batch_test/test_batch_test.install
@@ -10,11 +10,11 @@
 /**
  * Implements hook_install().
  */
-function simpletest_test_install() {
+function test_batch_test_install() {
   $total = 2;
   $operations = [];
   for ($i = 1; $i <= $total; $i++) {
-    $operations[] = ['_simpletest_test_callback', [$i]];
+    $operations[] = ['_test_batch_test_callback', [$i]];
   }
   $batch = [
     'operations' => $operations,
@@ -28,7 +28,7 @@ function simpletest_test_install() {
 /**
  * Callback for batch operations.
  */
-function _simpletest_test_callback($id) {
+function _test_batch_test_callback($id) {
   $entity = EntityTest::create(['id' => $id]);
   $entity->save();
 }
diff --git a/core/modules/simpletest/tests/src/Traits/TestTrait.php b/core/modules/system/tests/src/Traits/TestTrait.php
similarity index 84%
rename from core/modules/simpletest/tests/src/Traits/TestTrait.php
rename to core/modules/system/tests/src/Traits/TestTrait.php
index eeac4963ecc55b7a403f33ea694ab85ba161ae73..02ef094bc1d2264022653909d3869071505282f1 100644
--- a/core/modules/simpletest/tests/src/Traits/TestTrait.php
+++ b/core/modules/system/tests/src/Traits/TestTrait.php
@@ -1,6 +1,6 @@
 <?php
 
-namespace Drupal\Tests\simpletest\Traits;
+namespace Drupal\Tests\system\Traits;
 
 /**
  * A nothing trait, but declared in the Drupal\Tests namespace.
@@ -8,7 +8,7 @@
  * We use this trait to test autoloading of traits outside of the normal test
  * suite namespaces.
  *
- * @see \Drupal\Tests\simpletest\Unit\TraitAccessTest
+ * @see \Drupal\Tests\system\Unit\TraitAccessTest
  */
 trait TestTrait {
 
diff --git a/core/modules/simpletest/tests/src/Unit/TraitAccessTest.php b/core/modules/system/tests/src/Unit/TraitAccessTest.php
similarity index 76%
rename from core/modules/simpletest/tests/src/Unit/TraitAccessTest.php
rename to core/modules/system/tests/src/Unit/TraitAccessTest.php
index dbaffbf9ab0101dbf0d2ede864d601296b69eb01..c9ac7ff668dad6cfb80b39c42bc745133719a468 100644
--- a/core/modules/simpletest/tests/src/Unit/TraitAccessTest.php
+++ b/core/modules/system/tests/src/Unit/TraitAccessTest.php
@@ -1,14 +1,15 @@
 <?php
 
-namespace Drupal\Tests\simpletest\Unit;
+namespace Drupal\Tests\system\Unit;
 
 use Drupal\Tests\UnitTestCase;
-use Drupal\Tests\simpletest\Traits\TestTrait;
+use Drupal\Tests\system\Traits\TestTrait;
 
 /**
  * Test whether traits are autoloaded during PHPUnit discovery time.
  *
- * @group simpletest
+ * @group system
+ * @group Test
  */
 class TraitAccessTest extends UnitTestCase {
 
diff --git a/core/tests/Drupal/FunctionalTests/BrowserTestBaseTest.php b/core/tests/Drupal/FunctionalTests/BrowserTestBaseTest.php
index 5cebed18068a14bd6e476c720e26d8bf090c370d..6c1bd8be50fcbe33e6a1b3cc45aeff34706461ad 100644
--- a/core/tests/Drupal/FunctionalTests/BrowserTestBaseTest.php
+++ b/core/tests/Drupal/FunctionalTests/BrowserTestBaseTest.php
@@ -641,14 +641,20 @@ public function testInstall() {
    * Tests the assumption that local time is in 'Australia/Sydney'.
    */
   public function testLocalTimeZone() {
+    $expected = 'Australia/Sydney';
     // The 'Australia/Sydney' time zone is set in core/tests/bootstrap.php
-    $this->assertEquals('Australia/Sydney', date_default_timezone_get());
+    $this->assertEquals($expected, date_default_timezone_get());
 
     // The 'Australia/Sydney' time zone is also set in
     // FunctionalTestSetupTrait::initConfig().
     $config_factory = $this->container->get('config.factory');
     $value = $config_factory->get('system.date')->get('timezone.default');
-    $this->assertEquals('Australia/Sydney', $value);
+    $this->assertEquals($expected, $value);
+
+    // Test that users have the correct time zone set.
+    $this->assertEquals($expected, $this->rootUser->getTimeZone());
+    $admin_user = $this->drupalCreateUser(['administer site configuration']);
+    $this->assertEquals($expected, $admin_user->getTimeZone());
   }
 
   /**
@@ -684,4 +690,21 @@ public function testProfileModules() {
     \Drupal::service('extension.list.module')->getPathname('demo_umami_content');
   }
 
+  /**
+   * Test the protections provided by .htkey.
+   */
+  public function testHtkey() {
+    // Remove the Simpletest private key file so we can test the protection
+    // against requests that forge a valid testing user agent to gain access
+    // to the installer.
+    // @see drupal_valid_test_ua()
+    // Not using File API; a potential error must trigger a PHP warning.
+    $install_url = Url::fromUri('base:core/install.php', ['external' => TRUE, 'absolute' => TRUE])->toString();
+    $this->drupalGet($install_url);
+    $this->assertSession()->statusCodeEquals(200);
+    unlink($this->siteDirectory . '/.htkey');
+    $this->drupalGet($install_url);
+    $this->assertSession()->statusCodeEquals(403);
+  }
+
 }
diff --git a/core/tests/Drupal/FunctionalTests/BrowserTestBaseUserAgentTest.php b/core/tests/Drupal/FunctionalTests/BrowserTestBaseUserAgentTest.php
new file mode 100644
index 0000000000000000000000000000000000000000..8468fd5af831be115894dcbfe91260dadbb86ea2
--- /dev/null
+++ b/core/tests/Drupal/FunctionalTests/BrowserTestBaseUserAgentTest.php
@@ -0,0 +1,68 @@
+<?php
+
+namespace Drupal\FunctionalTests;
+
+use Drupal\Tests\BrowserTestBase;
+
+/**
+ * Tests BrowserTestBase functionality.
+ *
+ * @group browsertestbase
+ */
+class BrowserTestBaseUserAgentTest extends BrowserTestBase {
+
+  /**
+   * The user agent string to use.
+   *
+   * @var string
+   */
+  protected $agent;
+
+  /**
+   * Test validation of the User-Agent header we use to perform test requests.
+   */
+  public function testUserAgentValidation() {
+    $assert_session = $this->assertSession();
+    $system_path = $this->buildUrl(drupal_get_path('module', 'system'));
+    $http_path = $system_path . '/tests/http.php/user/login';
+    $https_path = $system_path . '/tests/https.php/user/login';
+    // Generate a valid simpletest User-Agent to pass validation.
+    $this->assertTrue(preg_match('/test\d+/', $this->databasePrefix, $matches), 'Database prefix contains test prefix.');
+    $this->agent = drupal_generate_test_ua($matches[0]);
+
+    // Test pages only available for testing.
+    $this->drupalGet($http_path);
+    $assert_session->statusCodeEquals(200);
+    $this->drupalGet($https_path);
+    $assert_session->statusCodeEquals(200);
+
+    // Now slightly modify the HMAC on the header, which should not validate.
+    $this->agent = 'X';
+    $this->drupalGet($http_path);
+    $assert_session->statusCodeEquals(403);
+    $this->drupalGet($https_path);
+    $assert_session->statusCodeEquals(403);
+
+    // Use a real User-Agent and verify that the special files http.php and
+    // https.php can't be accessed.
+    $this->agent = 'Mozilla/5.0 (Macintosh; U; Intel Mac OS X 10.6; en-US; rv:1.9.2.12) Gecko/20101026 Firefox/3.6.12';
+    $this->drupalGet($http_path);
+    $assert_session->statusCodeEquals(403);
+    $this->drupalGet($https_path);
+    $assert_session->statusCodeEquals(403);
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  protected function prepareRequest() {
+    $session = $this->getSession();
+    if ($this->agent) {
+      $session->setCookie('SIMPLETEST_USER_AGENT', $this->agent);
+    }
+    else {
+      $session->setCookie('SIMPLETEST_USER_AGENT', drupal_generate_test_ua($this->databasePrefix));
+    }
+  }
+
+}
diff --git a/core/tests/Drupal/FunctionalTests/Core/Test/ModuleInstallBatchTest.php b/core/tests/Drupal/FunctionalTests/Core/Test/ModuleInstallBatchTest.php
new file mode 100644
index 0000000000000000000000000000000000000000..60c4356c391d918b84224fa2a8a021e88b43a3aa
--- /dev/null
+++ b/core/tests/Drupal/FunctionalTests/Core/Test/ModuleInstallBatchTest.php
@@ -0,0 +1,37 @@
+<?php
+
+namespace Drupal\FunctionalTests\Core\Test;
+
+use Drupal\entity_test\Entity\EntityTest;
+use Drupal\Tests\BrowserTestBase;
+
+/**
+ * Tests batch operations during tests execution.
+ *
+ * This demonstrates that a batch will be successfully executed during module
+ * installation when running tests.
+ *
+ * @group Test
+ * @group FunctionalTestSetupTrait
+ *
+ * @see \Drupal\simpletest\Tests\SimpleTestInstallBatchTest
+ */
+class ModuleInstallBatchTest extends BrowserTestBase {
+
+  /**
+   * Modules to enable.
+   *
+   * @var array
+   */
+  public static $modules = ['test_batch_test', 'entity_test'];
+
+  /**
+   * Tests loading entities created in a batch in test_batch_test_install().
+   */
+  public function testLoadingEntitiesCreatedInBatch() {
+    foreach ([1, 2] as $id) {
+      $this->assertNotNull(EntityTest::load($id), 'Successfully loaded entity ' . $id);
+    }
+  }
+
+}
diff --git a/core/modules/simpletest/tests/src/Unit/AssertContentTraitTest.php b/core/tests/Drupal/Tests/Core/Test/AssertContentTraitTest.php
similarity index 75%
rename from core/modules/simpletest/tests/src/Unit/AssertContentTraitTest.php
rename to core/tests/Drupal/Tests/Core/Test/AssertContentTraitTest.php
index 505a3b91ff42c781aff664175abbcfb91eab0184..70f62245b992321c0fc19b080a76f3b996740d0e 100644
--- a/core/modules/simpletest/tests/src/Unit/AssertContentTraitTest.php
+++ b/core/tests/Drupal/Tests/Core/Test/AssertContentTraitTest.php
@@ -1,18 +1,13 @@
 <?php
 
-/**
- * @file
- * Contains \Drupal\Tests\simpletest\Unit\AssertContentTraitTest.
- */
-
-namespace Drupal\Tests\simpletest\Unit;
+namespace Drupal\Tests\Core\Test;
 
-use Drupal\simpletest\AssertContentTrait;
+use Drupal\KernelTests\AssertContentTrait;
 use Drupal\Tests\UnitTestCase;
 
 /**
- * @coversDefaultClass \Drupal\simpletest\AssertContentTrait
- * @group simpletest
+ * @coversDefaultClass \Drupal\KernelTests\AssertContentTrait
+ * @group Test
  */
 class AssertContentTraitTest extends UnitTestCase {
 
diff --git a/core/modules/simpletest/tests/src/Unit/PhpUnitAutoloaderTest.php b/core/tests/Drupal/Tests/Core/Test/PhpUnitAutoloaderTest.php
similarity index 87%
rename from core/modules/simpletest/tests/src/Unit/PhpUnitAutoloaderTest.php
rename to core/tests/Drupal/Tests/Core/Test/PhpUnitAutoloaderTest.php
index ca8cac1e66394083610a3f3c94d7829db0f653e1..a6d30b23b8ed5a8cbe5678dc5ed8b7de14bb6b59 100644
--- a/core/modules/simpletest/tests/src/Unit/PhpUnitAutoloaderTest.php
+++ b/core/tests/Drupal/Tests/Core/Test/PhpUnitAutoloaderTest.php
@@ -1,13 +1,13 @@
 <?php
 
-namespace Drupal\Tests\simpletest\Unit;
+namespace Drupal\Tests\Core\Test;
 
 use Drupal\Tests\UnitTestCase;
 
 /**
  * Tests that classes are correctly loaded during PHPUnit initialization.
  *
- * @group simpletest
+ * @group Test
  */
 class PhpUnitAutoloaderTest extends UnitTestCase {
 
diff --git a/core/tests/Drupal/Tests/Listeners/Legacy/HtmlOutputPrinter.php b/core/tests/Drupal/Tests/Listeners/Legacy/HtmlOutputPrinter.php
index 7c1f45e38f905c718486c152dd6c0a0127add0be..7a332bc2de0b80b0ccea202256cccf4585ec48ef 100644
--- a/core/tests/Drupal/Tests/Listeners/Legacy/HtmlOutputPrinter.php
+++ b/core/tests/Drupal/Tests/Listeners/Legacy/HtmlOutputPrinter.php
@@ -15,7 +15,7 @@ class HtmlOutputPrinter extends \PHPUnit_TextUI_ResultPrinter {
   /**
    * {@inheritdoc}
    */
-  public function __construct($out, $verbose, $colors, $debug, $numberOfColumns) {
+  public function __construct($out = NULL, $verbose = FALSE, $colors = self::COLOR_DEFAULT, $debug = FALSE, $numberOfColumns = 80) {
     parent::__construct($out, $verbose, $colors, $debug, $numberOfColumns);
 
     $this->setUpHtmlOutput();