diff --git a/core/modules/action/src/Tests/ConfigurationTest.php b/core/modules/action/src/Tests/ConfigurationTest.php
index 97448ae..866318a 100644
--- a/core/modules/action/src/Tests/ConfigurationTest.php
+++ b/core/modules/action/src/Tests/ConfigurationTest.php
@@ -11,7 +11,10 @@
 use Drupal\simpletest\WebTestBase;
 
 /**
- * Actions configuration.
+ * Tests UI CRUD configuration for complex actions.
+ *
+ * @group Action
+ * @requires module action
  */
 class ConfigurationTest extends WebTestBase {
 
@@ -22,14 +25,6 @@ class ConfigurationTest extends WebTestBase {
    */
   public static $modules = array('action');
 
-  public static function getInfo() {
-    return array(
-      'name' => 'Actions configuration',
-      'description' => 'Tests complex actions configuration by adding, editing, and deleting a complex action.',
-      'group' => 'Action',
-    );
-  }
-
   /**
    * Tests configuration of advanced actions through administration interface.
    */
diff --git a/core/modules/serialization/tests/src/EntityResolver/UuidResolverTest.php b/core/modules/serialization/tests/src/EntityResolver/UuidResolverTest.php
index c41eea8..9d49dce 100644
--- a/core/modules/serialization/tests/src/EntityResolver/UuidResolverTest.php
+++ b/core/modules/serialization/tests/src/EntityResolver/UuidResolverTest.php
@@ -2,10 +2,10 @@
 
 /**
  * @file
- * Contains \Drupal\serialization\Tests\Normalizer\ListNormalizerTest.
+ * Contains \Drupal\serialization\Tests\EntityResolver\UuidResolverTest.
  */
 
-namespace Drupal\serialization\Tests\Normalizer;
+namespace Drupal\serialization\Tests\EntityResolver;
 
 use Drupal\Tests\UnitTestCase;
 use Drupal\serialization\EntityResolver\UuidResolver;
diff --git a/core/modules/simpletest/css/simpletest.module.css b/core/modules/simpletest/css/simpletest.module.css
index 611cc4a..71f7eea 100644
--- a/core/modules/simpletest/css/simpletest.module.css
+++ b/core/modules/simpletest/css/simpletest.module.css
@@ -4,7 +4,7 @@
   width: 1em;
 }
 th.simpletest-test-label {
-  width: 16em;
+  width: 40%;
 }
 
 .simpletest-image {
diff --git a/core/modules/simpletest/simpletest.module b/core/modules/simpletest/simpletest.module
index bec96c4..1d70f35 100644
--- a/core/modules/simpletest/simpletest.module
+++ b/core/modules/simpletest/simpletest.module
@@ -435,159 +435,14 @@ function simpletest_log_read($test_id, $database_prefix, $test_class) {
  *   @endcode
  */
 function simpletest_test_get_all($module = NULL) {
-  static $all_groups = array();
-  $cid = "simpletest:$module";
-
-  if (!isset($all_groups[$cid])) {
-    $all_groups[$cid] = array();
-    $groups = &$all_groups[$cid];
-    // Register namespaces (extensions are not necessarily enabled).
-    simpletest_classloader_register();
-
-    // Load test information from cache if available, otherwise retrieve the
-    // information from each tests getInfo() method.
-    if ($cache = \Drupal::cache()->get($cid)) {
-      $groups = $cache->data;
-    }
-    else {
-      // Select all PSR-0 classes in the Tests namespace of all modules.
-      $listing = new ExtensionDiscovery();
-      // Ensure that tests in all profiles are discovered.
-      $listing->setProfileDirectories(array());
-      $all_data = $listing->scan('module', TRUE);
-      // If module is set then we keep only that one module.
-      if (isset($module)) {
-        $all_data = array(
-          $module => $all_data[$module],
-        );
-      }
-      else {
-        $all_data += $listing->scan('profile', TRUE);
-        $all_data += $listing->scan('theme', TRUE);
-      }
-
-      // Scan all extension folders for class files.
-      $classes = array();
-      foreach ($all_data as $name => $data) {
-
-        // Build the directory in which simpletest test classes would reside.
-        $tests_dir = DRUPAL_ROOT . '/' . $data->getPath() . '/src/Tests';
-
-        // Check if the directory exists.
-        if (!is_dir($tests_dir)) {
-          // This extension has no directory for simpletest cases.
-          continue;
-        }
-
-        // Scan the directory for class files.
-        $files = file_scan_directory($tests_dir, '/\.php$/');
-        if (empty($files)) {
-          // No class files found.
-          continue;
-        }
-
-        // Convert the file names into the namespaced class names.
-        $strlen = strlen($tests_dir) + 1;
-        $namespace = 'Drupal\\' . $name . '\Tests\\';
-        foreach ($files as $file) {
-          $classes[] = $namespace . str_replace('/', '\\', substr($file->uri, $strlen, -4));
-        }
-      }
-
-      // Check that each class has a getInfo() method and store the information
-      // in an array keyed with the group specified in the test information.
-      $groups = array();
-      foreach ($classes as $class) {
-        // Test classes need to implement getInfo() to be valid.
-        if (class_exists($class) && method_exists($class, 'getInfo')) {
-          $reflectionClass = new ReflectionClass($class);
-          // Skip abstract classes and interfaces.
-          if ($reflectionClass->isInstantiable()) {
-            $reflectionMethod = new ReflectionMethod($class, 'getInfo');
-            $declaringClass = $reflectionMethod->getDeclaringClass()->getName();
-            // Avoid testing intermediate classes which do not implement the
-            // method.
-            if ($class == $declaringClass) {
-              $info = call_user_func(array($class, 'getInfo'));
-            }
-            else {
-              continue;
-            }
-          }
-          else {
-            continue;
-          }
-          // If this test class requires a non-existing module, skip it.
-          if (!empty($info['dependencies'])) {
-            foreach ($info['dependencies'] as $dependency) {
-              if (!isset($dependency_data[$dependency])) {
-                continue 2;
-              }
-            }
-          }
-
-          $groups[$info['group']][$class] = $info;
-        }
-      }
-
-      // Sort the groups and tests within the groups by name.
-      uksort($groups, 'strnatcasecmp');
-      foreach ($groups as &$tests) {
-        uksort($tests, 'strnatcasecmp');
-      }
-
-      // Allow modules extending core tests to disable originals.
-      \Drupal::moduleHandler()->alter('simpletest', $groups);
-      \Drupal::cache()->set($cid, $groups);
-    }
-  }
-  return $all_groups[$cid];
+  return \Drupal::service('test_discovery')->getTestClasses();
 }
 
 /**
  * Registers namespaces for disabled modules.
  */
 function simpletest_classloader_register() {
-  // Use the same cache prefix as simpletest_test_get_all().
-  $cid = "simpletest::all";
-  $types = array(
-    'theme_engine',
-    'module',
-    'theme',
-    'profile',
-  );
-
-  if ($cache = \Drupal::cache()->get($cid)) {
-    $extensions = $cache->data;
-  }
-  else {
-    $listing = new ExtensionDiscovery();
-    // Ensure that tests in all profiles are discovered.
-    $listing->setProfileDirectories(array());
-    $extensions = array();
-    foreach ($types as $type) {
-      foreach ($listing->scan($type, TRUE) as $name => $file) {
-        $extensions[$type][$name] = $file->getPathname();
-      }
-    }
-    \Drupal::cache()->set($cid, $extensions);
-  }
-
-  $classloader = drupal_classloader();
-  foreach ($types as $type) {
-    foreach ($extensions[$type] as $name => $uri) {
-      drupal_classloader_register($name, dirname($uri));
-      $classloader->addPsr4('Drupal\\' . $name . '\\Tests\\', array(
-        DRUPAL_ROOT . '/' . dirname($uri) . '/tests/Drupal/' . $name . '/Tests',
-        DRUPAL_ROOT . '/' . dirname($uri) . '/tests/src',
-      ));
-      // While being there, prime drupal_get_filename().
-      drupal_get_filename($type, $name, $uri);
-    }
-  }
-
-  // Register the core test directory so we can find \Drupal\UnitTestCase.
-  $classloader->add('Drupal\\Tests', DRUPAL_ROOT . '/core/tests');
+  \Drupal::service('test_discovery')->registerTestNamespaces();
 }
 
 /**
diff --git a/core/modules/simpletest/simpletest.services.yml b/core/modules/simpletest/simpletest.services.yml
new file mode 100644
index 0000000..b6c75e2
--- /dev/null
+++ b/core/modules/simpletest/simpletest.services.yml
@@ -0,0 +1,3 @@
+services:
+  test_discovery:
+    class: Drupal\simpletest\TestDiscovery
diff --git a/core/modules/simpletest/src/Form/SimpletestTestForm.php b/core/modules/simpletest/src/Form/SimpletestTestForm.php
index e3876a5..ca84a43 100644
--- a/core/modules/simpletest/src/Form/SimpletestTestForm.php
+++ b/core/modules/simpletest/src/Form/SimpletestTestForm.php
@@ -96,7 +96,6 @@ public function buildForm(array $form, array &$form_state) {
 
     // Generate the list of tests arranged by group.
     $groups = simpletest_test_get_all();
-    $groups['PHPUnit'] = simpletest_phpunit_get_available_tests();
     $form_state['storage']['PHPUnit'] = $groups['PHPUnit'];
 
     foreach ($groups as $group => $tests) {
@@ -150,10 +149,7 @@ public function buildForm(array $form, array &$form_state) {
         );
         $form['tests'][$class]['description'] = array(
           '#prefix' => '<div class="description">',
-          '#markup' => String::format('@description (@class)', array(
-            '@description' => $info['description'],
-            '@class' => $class,
-          )),
+          '#markup' => String::checkPlain($info['description']),
           '#suffix' => '</div>',
           '#wrapper_attributes' => array(
             'class' => array('simpletest-test-description', 'table-filter-text-source'),
@@ -192,14 +188,14 @@ public function buildForm(array $form, array &$form_state) {
   public function submitForm(array &$form, array &$form_state) {
     simpletest_classloader_register();
 
-    $phpunit_all = array_keys($form_state['storage']['PHPUnit']);
+    $phpunit_all = $form_state['storage']['PHPUnit'];
 
     $tests_list = array();
     foreach ($form_state['values']['tests'] as $class_name => $value) {
       // Since class_exists() will likely trigger an autoload lookup,
       // we do the fast check first.
       if ($value === $class_name && class_exists($class_name)) {
-        $test_type = in_array($class_name, $phpunit_all) ? 'UnitTest' : 'WebTest';
+        $test_type = isset($phpunit_all[$class_name]) ? 'UnitTest' : 'WebTest';
         $tests_list[$test_type][] = $class_name;
       }
     }
diff --git a/core/modules/simpletest/src/TestBase.php b/core/modules/simpletest/src/TestBase.php
index 023cf8e..133e931 100644
--- a/core/modules/simpletest/src/TestBase.php
+++ b/core/modules/simpletest/src/TestBase.php
@@ -200,27 +200,6 @@ public function __construct($test_id = NULL) {
   }
 
   /**
-   * Provides meta information about this test case, such as test name.
-   *
-   * @return array
-   *   An array of untranslated strings with the following keys:
-   *   - name: An overview of what is tested by the class; for example, "User
-   *     access rules".
-   *   - description: One sentence describing the test, starting with a verb.
-   *   - group: The human-readable name of the module ("Node", "Statistics"), or
-   *     the human-readable name of the Drupal facility tested (e.g. "Form API"
-   *     or "XML-RPC").
-   */
-  public static function getInfo() {
-    // PHP does not allow us to declare this method as abstract public static,
-    // so we simply throw an exception here if this has not been implemented by
-    // a child class.
-    throw new \RuntimeException(String::format('@class must implement \Drupal\simpletest\TestBase::getInfo().', array(
-      '@class' => get_called_class(),
-    )));
-  }
-
-  /**
    * Performs setup tasks before each individual test method is run.
    */
   abstract protected function setUp();
diff --git a/core/modules/simpletest/src/TestDiscovery.php b/core/modules/simpletest/src/TestDiscovery.php
new file mode 100644
index 0000000..f3f7fa9
--- /dev/null
+++ b/core/modules/simpletest/src/TestDiscovery.php
@@ -0,0 +1,367 @@
+<?php
+
+/**
+ * @file
+ * Contains \Drupal\simpletest\TestDiscovery.
+ */
+
+namespace Drupal\simpletest;
+
+use Drupal\Core\Extension\Extension;
+use Drupal\Core\Extension\ExtensionDiscovery;
+use PHPUnit_Util_Test;
+
+/**
+ * Discovers available tests.
+ */
+class TestDiscovery {
+
+  /**
+   * Cached map of all test namespaces to respective directories.
+   *
+   * @var array
+   */
+  protected $testNamespaces;
+
+  /**
+   * Cached list of all discovered test classes.
+   *
+   * @var array
+   */
+  protected $testClasses;
+
+  /**
+   * Cached list of available extension names, keyed by extension type.
+   *
+   * @var array
+   */
+  protected $availableExtensions;
+
+  /**
+   * Registers test namespaces of all available extensions.
+   *
+   * @return array
+   *   An associative array whose keys are PSR-4 namespace prefixes and whose
+   *   values are directory names.
+   *
+   * @todo Inject class loader.
+   */
+  public function registerTestNamespaces() {
+    if (isset($this->testNamespaces)) {
+      return $this->testNamespaces;
+    }
+    $this->testNamespaces = array();
+
+    $loader = drupal_classloader();
+    $existing = $loader->getPrefixes();
+    $old = array();
+    $new = array();
+
+    // Add PHPUnit test namespace of Drupal core.
+    $new['Drupal\\Tests\\'] = DRUPAL_ROOT . '/core/tests/Drupal/Tests';
+
+    $this->availableExtensions = array();
+    foreach ($this->getExtensions() as $name => $extension) {
+      $this->availableExtensions[$extension->getType()][$name] = $name;
+
+      $base_namespace = "Drupal\\$name\\";
+      $base_path = DRUPAL_ROOT . '/' . $extension->getPath();
+
+      // Add namespace of disabled/uninstalled extensions.
+      if (!isset($existing[$base_namespace])) {
+        $new[$base_namespace] = "$base_path/src";
+      }
+      else {
+        $old[$base_namespace] = reset($existing[$base_namespace]);
+      }
+      // Add PHPUnit test namespace.
+      // @todo Move PHPUnit namespace of extensions into Drupal\Tests\$name.
+      // @see https://drupal.org/node/2260121
+      $new[$base_namespace . 'Tests\\'] = "$base_path/tests/src";
+
+      // While being there, prime drupal_get_filename().
+      // @todo Remove this.
+      drupal_get_filename($extension->getType(), $name, $extension->getPathname());
+    }
+
+    foreach ($new as $prefix => $path) {
+      $loader->addPsr4($prefix, $path);
+    }
+
+    $this->testNamespaces = $new + $old;
+    return $this->testNamespaces;
+  }
+
+  /**
+   * Discovers all available tests in all extensions.
+   *
+   * @return array
+   *   An array of tests keyed by the @group specified in each of test's
+   *   phpDoc comment block, and then keyed by class names. For example:
+   *   @code
+   *     $groups['Block'] => array(
+   *       'Drupal\block\Tests\BlockTest' => array(
+   *         'name' => 'Drupal\block\Tests\BlockTest',
+   *         'description' => 'Tests block UI CRUD functionality.',
+   *         'group' => 'Block',
+   *       ),
+   *     );
+   *   @endcode
+   */
+  public function getTestClasses() {
+    if (isset($this->testClasses)) {
+      return $this->testClasses;
+    }
+    $this->testClasses = array();
+    foreach ($this->findTestClasses() as $classname => $pathname) {
+      try {
+        $class = new \ReflectionClass($classname);
+      }
+      catch (\ReflectionException $e) {
+        // Re-throw with expected pathname.
+        $message = $e->getMessage() . " in expected $pathname";
+        throw new \ReflectionException($message, $e->getCode(), $e);
+      }
+      // Skip abstract classes and interfaces.
+      if (!$class->isInstantiable()) {
+        continue;
+      }
+      // Skip non-test classes.
+      if (!$class->isSubclassOf('Drupal\simpletest\TestBase') && !$class->isSubclassOf('PHPUnit_Framework_TestCase')) {
+        continue;
+      }
+      $info = static::getTestInfo($class);
+
+      // Skip this test class if it requires unavailable modules.
+      if (!empty($info['requires']['module'])) {
+        if (array_diff($info['requires']['module'], $this->availableExtensions['module'])) {
+          continue;
+        }
+      }
+      // @todo If this is a PHPUnit test class, construct a new
+      //   PHPUnit_Framework_TestSuite($class) and ignore/hide/remove it if that
+      //   throws a PHPUnit_Framework_Warning exception.
+      // @see simpletest_phpunit_get_available_tests()
+
+      $this->testClasses[$info['group']][$classname] = $info;
+    }
+
+    // Sort the groups and tests within the groups by name.
+    uksort($this->testClasses, 'strnatcasecmp');
+    foreach ($this->testClasses as &$tests) {
+      uksort($tests, 'strnatcasecmp');
+    }
+
+    // Allow modules extending core tests to disable originals.
+    \Drupal::moduleHandler()->alter('simpletest', $this->testClasses);
+
+    return $this->testClasses;
+  }
+
+  /**
+   * Discovers all test classes in all available extensions.
+   *
+   * @return array
+   *   A classmap containing all discovered test classes.
+   */
+  protected function findTestClasses() {
+    $classmap = array();
+    foreach ($this->registerTestNamespaces() as $namespace => $path) {
+      if (!is_dir($path)) {
+        continue;
+      }
+      $classmap += static::scanDirectory($namespace, $path);
+    }
+    return $classmap;
+  }
+
+  /**
+   * Scans a given directory for class files.
+   *
+   * @param string $namespace_prefix
+   *   The namespace prefix to use for discovered classes. Must contain a
+   *   trailing namespace separator (backslash).
+   *   For example: 'Drupal\\node\\Tests\\'
+   * @param string $path
+   *   The directory path to scan.
+   *   For example: '/path/to/drupal/core/modules/node/tests/src'
+   *
+   * @return array
+   *   An associative array whose keys are fully-qualified class names and whose
+   *   values are corresponding filesystem pathnames.
+   */
+  public static function scanDirectory($namespace_prefix, $path) {
+    if (substr($namespace_prefix, -1) !== '\\') {
+      throw new \InvalidArgumentException("Namespace prefix for $path must contain a trailing namespace separator.");
+    }
+    $flags = \FilesystemIterator::UNIX_PATHS;
+    $flags |= \FilesystemIterator::SKIP_DOTS;
+    $flags |= \FilesystemIterator::FOLLOW_SYMLINKS;
+    $flags |= \FilesystemIterator::CURRENT_AS_SELF;
+
+    $iterator = new \RecursiveDirectoryIterator($path, $flags);
+    $filter = new \RecursiveCallbackFilterIterator($iterator, function ($current, $key, $iterator) {
+      if ($iterator->hasChildren()) {
+        return TRUE;
+      }
+      return $current->isFile() && $current->getExtension() === 'php';
+    });
+    $files = new \RecursiveIteratorIterator($filter);
+    $classes = array();
+    foreach ($files as $fileinfo) {
+      $class = $namespace_prefix;
+      if ('' !== $subpath = $fileinfo->getSubPath()) {
+        $class .= strtr($subpath, '/', '\\') . '\\';
+      }
+      $class .= $fileinfo->getBasename('.php');
+      $classes[$class] = $fileinfo->getPathname();
+    }
+    return $classes;
+  }
+
+  /**
+   * Retrieves information about a test class for UI purposes.
+   *
+   * @param \ReflectionClass $class
+   *   The reflected test class.
+   *
+   * @return array
+   *   An associative array containing:
+   *   - name: The test class name.
+   *   - description: The test (phpDoc) summary.
+   *   - group: A human-readable group name parsed from a @group class phpDoc
+   *     annotation. (Only one at this point.)
+   *   - requires: An associative array containing requirements:
+   *     - module: A list of Drupal module extension names that the test depends
+   *       on.
+   */
+  public static function getTestInfo(\ReflectionClass $class) {
+    $classname = $class->getName();
+    $info = array(
+      'name' => $classname,
+      'description' => static::parseTestClassSummary($class),
+    );
+    // For now, only @group and @requires are supported.
+    $annotations = static::parseTestClassAnnotations($class);
+    $info += array_intersect_key($annotations, array('group' => 1, 'requires' => 1));
+
+    // Automatically convert @coversDefaultClass into description.
+    if (isset($annotations['coversDefaultClass'][0])) {
+      $info['description'] = 'Tests ' . $annotations['coversDefaultClass'][0] . '.';
+    }
+
+    // @todo Remove support for legacy getInfo() methods.
+    if ($class->hasMethod('getInfo')) {
+      $legacy_info = $classname::getInfo();
+      if (isset($legacy_info['group'])) {
+        $info['group'][] = $legacy_info['group'];
+      }
+      if (isset($legacy_info['dependencies'])) {
+        $info += array('requires' => array());
+        $info['requires'] += array('module' => array());
+        $info['requires']['module'] = array_merge($info['requires']['module'], $legacy_info['dependencies']);
+      }
+    }
+
+    // For now, all PHPUnit tests are forced into a single PHPUnit group.
+    if ($class->isSubclassOf('PHPUnit_Framework_TestCase')) {
+      $info['group'] = 'PHPUnit';
+    }
+    // For now, only one @group is supported.
+    // @todo Support multiple @groups + change UI to expose a group select
+    //   dropdown to filter tests by group instead of collapsible table groups.
+    elseif (empty($info['group'])) {
+      throw new \LogicException("Missing @group for $classname.");
+    }
+    else {
+      $info['group'] = reset($info['group']);
+    }
+
+    return $info;
+  }
+
+  /**
+   * Parses the phpDoc summary line of a test class.
+   *
+   * @param \ReflectionClass $class
+   *   The reflected test class.
+   *
+   * @return string
+   *   The parsed phpDoc summary line.
+   *
+   * @todo Rethink this implementation; a single preg_match_all() may be faster.
+   */
+  public static function parseTestClassSummary(\ReflectionClass $class) {
+    $phpDoc = $class->getDocComment();
+    // Normalize line endings.
+    $phpDoc = preg_replace('/\r\n|\r/', '\n', $phpDoc);
+    // Strip leading and trailing doc block lines.
+    //$phpDoc = trim($phpDoc, "* /\n");
+    $phpDoc = substr($phpDoc, 4, -4);
+
+    // Extract actual phpDoc content.
+    $phpDoc = explode("\n", $phpDoc);
+    array_walk($phpDoc, function (&$value) {
+      $value = trim($value, "* /\n");
+    });
+
+    // Extract summary; allowed to it wrap and continue on next line.
+    list($summary) = explode("\n\n", implode("\n", $phpDoc));
+    if ($summary === '') {
+      throw new \LogicException(sprintf('Missing phpDoc on %s.', $class->getName()));
+    }
+    return $summary;
+  }
+
+  /**
+   * Parses annotations in the phpDoc of a test class.
+   *
+   * @param \ReflectionClass $class
+   *   The reflected test class.
+   *
+   * @return array
+   *   An associative array that contains all annotations on the test class;
+   *   typically including:
+   *   - group: A list of @group values.
+   *   - requires: An associative array of @requires values; e.g.:
+   *     - module: A list of Drupal module dependencies that are required to
+   *       exist.
+   *
+   * @see PHPUnit_Util_Test::parseTestMethodAnnotations()
+   * @see http://phpunit.de/manual/current/en/incomplete-and-skipped-tests.html#incomplete-and-skipped-tests.skipping-tests-using-requires
+   */
+  public static function parseTestClassAnnotations(\ReflectionClass $class) {
+    $annotations = PHPUnit_Util_Test::parseTestMethodAnnotations($class->getName());
+
+    // @todo Enhance PHPUnit upstream to allow for custom @requires identifiers.
+    // @see PHPUnit_Util_Test::getRequirements()
+    // @todo Add support for 'PHP', 'OS', 'function', 'extension'.
+    if (isset($annotations['class']['requires'])) {
+      foreach ($annotations['class']['requires'] as $i => $value) {
+        list($type, $value) = explode(' ', $value, 2);
+        if ($type == 'module') {
+          $annotations['class']['requires']['module'][$value] = $value;
+        }
+        unset($annotations['class']['requires'][$i]);
+      }
+    }
+    return $annotations['class'];
+  }
+
+  /**
+   * Returns all available extensions.
+   *
+   * @return \Drupal\Core\Extension\Extension[]
+   *   An array of Extension objects, keyed by extension name.
+   */
+  protected function getExtensions() {
+    $listing = new ExtensionDiscovery();
+    // Ensure that tests in all profiles are discovered.
+    $listing->setProfileDirectories(array());
+    $extensions = $listing->scan('module', TRUE);
+    $extensions += $listing->scan('profile', TRUE);
+    $extensions += $listing->scan('theme', TRUE);
+    return $extensions;
+  }
+
+}
diff --git a/core/modules/system/src/Tests/Page/DefaultMetatagsTest.php b/core/modules/system/src/Tests/Page/DefaultMetatagsTest.php
index baae991..3b2afdf 100644
--- a/core/modules/system/src/Tests/Page/DefaultMetatagsTest.php
+++ b/core/modules/system/src/Tests/Page/DefaultMetatagsTest.php
@@ -9,6 +9,9 @@
 
 use Drupal\simpletest\WebTestBase;
 
+/**
+ * Tests default HTML metatags on a page.
+ */
 class DefaultMetatagsTest extends WebTestBase {
 
   /**
diff --git a/core/scripts/run-tests.sh b/core/scripts/run-tests.sh
index 8eff2a2..b99ef44 100755
--- a/core/scripts/run-tests.sh
+++ b/core/scripts/run-tests.sh
@@ -58,7 +58,7 @@
   foreach ($groups as $group => $tests) {
     echo $group . "\n";
     foreach ($tests as $class => $info) {
-      echo " - " . $info['name'] . ' (' . $class . ')' . "\n";
+      echo " - $class\n";
     }
   }
   exit;
@@ -561,7 +561,6 @@ function simpletest_script_setup_database($new = FALSE) {
  */
 function simpletest_script_get_all_tests($module = NULL) {
   $tests = simpletest_test_get_all($module);
-  $tests['PHPUnit'] = simpletest_phpunit_get_available_tests($module);
   return $tests;
 }
 
diff --git a/core/tests/Drupal/Tests/Component/PhpStorage/FileStorageReadOnlyTest.php b/core/tests/Drupal/Tests/Component/PhpStorage/FileStorageReadOnlyTest.php
index 4d4bc0f..a907a07 100644
--- a/core/tests/Drupal/Tests/Component/PhpStorage/FileStorageReadOnlyTest.php
+++ b/core/tests/Drupal/Tests/Component/PhpStorage/FileStorageReadOnlyTest.php
@@ -2,7 +2,7 @@
 
 /**
  * @file
- * Contains \Drupal\Tests\Component\PhpStorage\FileStorageTest.
+ * Contains \Drupal\Tests\Component\PhpStorage\FileStorageReadOnlyTest.
  */
 
 namespace Drupal\Tests\Component\PhpStorage;
@@ -18,7 +18,7 @@
  *
  * @coversDefaultClass \Drupal\Component\PhpStorage\FileReadOnlyStorage
  */
-class FileStorageReadyOnlyTest extends PhpStorageTestBase {
+class FileStorageReadOnlyTest extends PhpStorageTestBase {
 
   /**
    * Standard test settings to pass to storage instances.
diff --git a/core/tests/Drupal/Tests/Core/Logger/LogMessageParserTest.php b/core/tests/Drupal/Tests/Core/Logger/LogMessageParserTest.php
index e30f551..2fa198e 100644
--- a/core/tests/Drupal/Tests/Core/Logger/LogMessageParserTest.php
+++ b/core/tests/Drupal/Tests/Core/Logger/LogMessageParserTest.php
@@ -2,7 +2,7 @@
 
 /**
  * @file
- * Contains \Drupal\Tests\Core\Logger\LogMessageParserTraitTest
+ * Contains \Drupal\Tests\Core\Logger\LogMessageParserTest.
  */
 
 namespace Drupal\Tests\Core\Logger;
diff --git a/core/tests/Drupal/Tests/Core/Logger/LoggerChannelFactoryTest.php b/core/tests/Drupal/Tests/Core/Logger/LoggerChannelFactoryTest.php
index 82e20b2..8bbe4ab 100644
--- a/core/tests/Drupal/Tests/Core/Logger/LoggerChannelFactoryTest.php
+++ b/core/tests/Drupal/Tests/Core/Logger/LoggerChannelFactoryTest.php
@@ -2,10 +2,10 @@
 
 /**
  * @file
- * Contains \Drupal\Tests\Core\Logger\LoggerChannelFactoryTest
+ * Contains \Drupal\Tests\Core\Logger\LoggerChannelFactoryTest.
  */
 
-namespace Drupal\Tests\Logger;
+namespace Drupal\Tests\Core\Logger;
 
 use Drupal\Core\Logger\LoggerChannelFactory;
 use Drupal\Core\Session\AccountInterface;
diff --git a/core/tests/Drupal/Tests/Core/Logger/LoggerChannelTest.php b/core/tests/Drupal/Tests/Core/Logger/LoggerChannelTest.php
index 2cc0a50..51c7e86 100644
--- a/core/tests/Drupal/Tests/Core/Logger/LoggerChannelTest.php
+++ b/core/tests/Drupal/Tests/Core/Logger/LoggerChannelTest.php
@@ -2,10 +2,10 @@
 
 /**
  * @file
- * Contains \Drupal\Tests\Core\Logger\LoggerChannelTest
+ * Contains \Drupal\Tests\Core\Logger\LoggerChannelTest.
  */
 
-namespace Drupal\Tests\Logger;
+namespace Drupal\Tests\Core\Logger;
 
 use Drupal\Core\Logger\LoggerChannel;
 use Drupal\Core\Session\AccountInterface;
diff --git a/core/tests/Drupal/Tests/Core/Path/AliasManagerTest.php b/core/tests/Drupal/Tests/Core/Path/AliasManagerTest.php
index f8d5c0e..bffc88d 100644
--- a/core/tests/Drupal/Tests/Core/Path/AliasManagerTest.php
+++ b/core/tests/Drupal/Tests/Core/Path/AliasManagerTest.php
@@ -2,10 +2,10 @@
 
 /**
  * @file
- * Contains \Drupal\Tests\Core\ExternalUrlTest.
+ * Contains \Drupal\Tests\Core\Path\AliasManagerTest.
  */
 
-namespace Drupal\Tests\Core;
+namespace Drupal\Tests\Core\Path;
 
 use Drupal\Core\DependencyInjection\ContainerBuilder;
 use Drupal\Core\Language\Language;
