diff --git a/core/includes/ajax.inc b/core/includes/ajax.inc
index 3f2389f..a5d2174 100644
--- a/core/includes/ajax.inc
+++ b/core/includes/ajax.inc
@@ -241,7 +241,7 @@ function ajax_render($commands = array()) {
     // since the base page ought to have at least one JS file and one CSS file
     // loaded. It probably indicates an error, and rather than making the page
     // reload all of the files, instead we return no new files.
-    if (empty($_POST['ajax_page_state'][$type])) {
+    if (!\Drupal::request()->request->get("ajax_page_state[$type]", NULL, TRUE)) {
       $items[$type] = array();
     }
     else {
@@ -323,9 +323,10 @@ function ajax_render($commands = array()) {
  * @see file_menu()
  */
 function ajax_base_page_theme() {
-  if (!empty($_POST['ajax_page_state']['theme']) && !empty($_POST['ajax_page_state']['theme_token'])) {
-    $theme = $_POST['ajax_page_state']['theme'];
-    $token = $_POST['ajax_page_state']['theme_token'];
+  $ajax_page_state = \Drupal::Request()->request->get('ajax_page_state', array());
+  if (!empty($ajax_page_state['theme']) && !empty($ajax_page_state['theme_token'])) {
+    $theme = $ajax_page_state['theme'];
+    $token = $ajax_page_state['theme_token'];
 
     // Prevent a request forgery from giving a person access to a theme they
     // shouldn't be otherwise allowed to see. However, since everyone is allowed
diff --git a/core/includes/bootstrap.inc b/core/includes/bootstrap.inc
index 399c9fb..90c9aa2 100644
--- a/core/includes/bootstrap.inc
+++ b/core/includes/bootstrap.inc
@@ -457,25 +457,28 @@ function config_get_config_directory($type = CONFIG_ACTIVE_DIRECTORY) {
  * 'REMOTE_ADDR' key.
  *
  * @param $variables
- *   (optional) An associative array of variables within $_SERVER that should
- *   be replaced. If the special element 'url' is provided in this array, it
- *   will be used to populate some of the server defaults; it should be set to
- *   the URL of the current page request, excluding any $_GET request but
- *   including the script name (e.g., http://www.example.com/mysite/index.php).
+ *   (optional) An associative array of variables within
+ *   \Drupal::request()->server that should be replaced. If the special element
+ *   'url' is provided in this array, it will be used to populate some of the
+ *   server defaults; it should be set to the URL of the current page request,
+ *   excluding any GET request but including the script name
+ *   (e.g., http://www.example.com/mysite/index.php).
  *
  * @see conf_path()
  * @see request_uri()
  * @see \Symfony\Component\HttpFoundation\Request::getClientIP()
  */
 function drupal_override_server_variables($variables = array()) {
+  $request = \Drupal::request();
+  $server_vars = $request->server->all();
   // Allow the provided URL to override any existing values in $_SERVER.
   if (isset($variables['url'])) {
     $url = parse_url($variables['url']);
     if (isset($url['host'])) {
-      $_SERVER['HTTP_HOST'] = $url['host'];
+      $server_vars['HTTP_HOST'] = $request->getHttpHost();
     }
     if (isset($url['path'])) {
-      $_SERVER['SCRIPT_NAME'] = $url['path'];
+      $server_vars['SCRIPT_NAME'] = $request->getScriptName();
     }
     unset($variables['url']);
   }
@@ -492,7 +495,7 @@ function drupal_override_server_variables($variables = array()) {
     'HTTP_USER_AGENT' => NULL,
   );
   // Replace elements of the $_SERVER array, as appropriate.
-  $_SERVER = $variables + $_SERVER + $defaults;
+  $request->server->replace($variables + $server_vars + $defaults);
 }
 
 /**
diff --git a/core/includes/common.inc b/core/includes/common.inc
index 8f60fe4..153763a 100644
--- a/core/includes/common.inc
+++ b/core/includes/common.inc
@@ -432,7 +432,8 @@ function drupal_get_feeds($delimiter = "\n") {
  * Processes a URL query parameter array to remove unwanted elements.
  *
  * @param $query
- *   (optional) An array to be processed. Defaults to $_GET.
+ *   (optional) An array to be processed. Defaults to \Drupal::request()->query
+ *   parameters.
  * @param $exclude
  *   (optional) A list of $query array keys to remove. Use "parent[child]" to
  *   exclude nested items.
@@ -511,7 +512,7 @@ function drupal_get_destination() {
  * The returned array contains a 'path' that may be passed separately to url().
  * For example:
  * @code
- *   $options = drupal_parse_url($_GET['destination']);
+ *   $options = drupal_parse_url(\Drupal::request()->query->get('destination'));
  *   $my_url = url($options['path'], $options);
  *   $my_link = l('Example link', $options['path'], $options);
  * @endcode
@@ -522,7 +523,7 @@ function drupal_get_destination() {
  * $options['query'] and the fragment into $options['fragment'].
  *
  * @param $url
- *   The URL string to parse, f.e. $_GET['destination'].
+ *   The URL string to parse.
  *
  * @return
  *   An associative array containing the keys:
@@ -1955,6 +1956,7 @@ function drupal_html_id($id) {
   // take into account IDs that are already in use on the base page.
   $seen_ids_init = &drupal_static(__FUNCTION__ . ':init');
   if (!isset($seen_ids_init)) {
+    $ajax_html_ids = \Drupal::request()->request->get('ajax_html_ids');
     // Ideally, Drupal would provide an API to persist state information about
     // prior page requests in the database, and we'd be able to add this
     // function's $seen_ids static variable to that state information in order
@@ -1964,7 +1966,7 @@ function drupal_html_id($id) {
     // normally not recommended as it could open up security risks, but because
     // the raw POST data is cast to a number before being returned by this
     // function, this usage is safe.
-    if (empty($_POST['ajax_html_ids'])) {
+    if (empty($ajax_html_ids)) {
       $seen_ids_init = array();
     }
     else {
@@ -1973,7 +1975,7 @@ function drupal_html_id($id) {
       // requested id. $_POST['ajax_html_ids'] contains the ids as they were
       // returned by this function, potentially with the appended counter, so
       // we parse that to reconstruct the $seen_ids array.
-      $ajax_html_ids = explode(' ', $_POST['ajax_html_ids']);
+      $ajax_html_ids = explode(' ', $ajax_html_ids);
       foreach ($ajax_html_ids as $seen_id) {
         // We rely on '--' being used solely for separating a base id from the
         // counter, which this function ensures when returning an id.
diff --git a/core/includes/form.inc b/core/includes/form.inc
index 5867a36..5dfa29a 100644
--- a/core/includes/form.inc
+++ b/core/includes/form.inc
@@ -495,7 +495,8 @@ function form_type_checkboxes_value($element, $input = FALSE) {
     // NULL elements from the array before constructing the return value, to
     // simulate the behavior of web browsers (which do not send unchecked
     // checkboxes to the server at all). This will not affect non-programmatic
-    // form submissions, since all values in $_POST are strings.
+    // form submissions, since all values in \Drupal::request()->request are
+    // strings.
     foreach ($input as $key => $value) {
       if (!isset($value)) {
         unset($input[$key]);
diff --git a/core/includes/install.core.inc b/core/includes/install.core.inc
index 9159f71..c923c8d 100644
--- a/core/includes/install.core.inc
+++ b/core/includes/install.core.inc
@@ -253,9 +253,19 @@ function install_state_defaults() {
  *   modified with information gleaned from the beginning of the page request.
  */
 function install_begin_request(&$install_state) {
+  // A request object from the HTTPFoundation to tell us about the request.
+  $request = Request::createFromGlobals();
+
+  // Create a minimal container so that t() and $request will work. This
+  // container will be overriden but it's needed for the very early installation
+  // process when database tasks run.
+  $container = new ContainerBuilder();
+  $container->set('request', $request);
+  \Drupal::setContainer($container);
+
   // Add any installation parameters passed in via the URL.
   if ($install_state['interactive']) {
-    $install_state['parameters'] += $_GET;
+    $install_state['parameters'] += $request->query->all();
   }
 
   // Validate certain core settings that are used throughout the installation.
@@ -288,13 +298,10 @@ function install_begin_request(&$install_state) {
   // _drupal_load_test_overrides() sets the simpletest_conf_path in-memory
   // setting in this case.
   if ($install_state['interactive'] && drupal_valid_test_ua() && !settings()->get('simpletest_conf_path')) {
-    header($_SERVER['SERVER_PROTOCOL'] . ' 403 Forbidden');
+    header($request->server->get('SERVER_PROTOCOL') . ' 403 Forbidden');
     exit;
   }
 
-  // A request object from the HTTPFoundation to tell us about the request.
-  $request = Request::createFromGlobals();
-
   // If we have a language selected and it is not yet saved in the system
   // (eg. pre-database data screens we are unable to persistently store
   // the default language), we should set language_default so the proper
@@ -324,10 +331,6 @@ function install_begin_request(&$install_state) {
   // Determine whether the configuration system is ready to operate.
   $install_state['config_verified'] = install_verify_config_directory(CONFIG_ACTIVE_DIRECTORY) && install_verify_config_directory(CONFIG_STAGING_DIRECTORY);
 
-  // Create a minimal container for t() to work.
-  // This container will be overriden but it needed for the very early
-  // installation process when database tasks run.
-  $container = new ContainerBuilder();
   // Register the translation services.
   install_register_translation_service($container);
   \Drupal::setContainer($container);
@@ -1343,7 +1346,7 @@ function install_select_profile(&$install_state) {
  *
  * A profile will be selected if:
  * - Only one profile is available,
- * - A profile was submitted through $_POST,
+ * - A profile was submitted through \Drupal::request()->request,
  * - Exactly one of the profiles is marked as "exclusive".
  * If multiple profiles are marked as "exclusive" then no profile will be
  * selected.
@@ -1357,12 +1360,13 @@ function install_select_profile(&$install_state) {
  */
 function _install_select_profile($profiles) {
   // Don't need to choose profile if only one available.
+  $request_params = \Drupal::request()->request;
   if (count($profiles) == 1) {
     $profile = array_pop($profiles);
     return $profile->name;
   }
-  elseif (!empty($_POST['profile']) && isset($profiles[$_POST['profile']])) {
-    return $profiles[$_POST['profile']]->name;
+  elseif ($request_params->has('profile') && ($profile = $request_params->get('profile')) && isset($profiles[$profile])) {
+    return $profiles[$profile]->name;
   }
   // Check for a profile marked as "exclusive" and ensure that only one
   // profile is marked as such.
@@ -1543,6 +1547,7 @@ function install_select_language(&$install_state) {
   // Find all available translation files.
   $files = install_find_translations();
   $install_state['translations'] += $files;
+  $request_params = \Drupal::request()->request;
 
   // If a valid language code is set, continue with the next installation step.
   // When translations from the localization server are used, any language code
@@ -1550,9 +1555,9 @@ function install_select_language(&$install_state) {
   // langauges available at http://localize.drupal.org.
   // When files from the translation directory are used, we only accept
   // languages for which a file is available.
-  if (!empty($_POST['langcode'])) {
+  if ($request_params->has('langcode')) {
     $standard_languages = LanguageManager::getStandardLanguageList();
-    $langcode = $_POST['langcode'];
+    $langcode = $request_params->get('langcode');
     if ($langcode == 'en' || isset($files[$langcode]) || isset($standard_languages[$langcode])) {
       $install_state['parameters']['langcode'] = $langcode;
       return;
@@ -2096,7 +2101,8 @@ function install_configure_form($form, &$form_state, &$install_state) {
   // especially out of place on the last page of the installer, where it would
   // distract from the message that the Drupal installation has completed
   // successfully.)
-  if (empty($_POST) && (!drupal_verify_install_file(DRUPAL_ROOT . '/' . $settings_file, FILE_EXIST|FILE_READABLE|FILE_NOT_WRITABLE) || !drupal_verify_install_file(DRUPAL_ROOT . '/' . $settings_dir, FILE_NOT_WRITABLE, 'dir'))) {
+  $post_params = \Drupal::request()->request->all();
+  if (empty($post_params) && (!drupal_verify_install_file(DRUPAL_ROOT . '/' . $settings_file, FILE_EXIST|FILE_READABLE|FILE_NOT_WRITABLE) || !drupal_verify_install_file(DRUPAL_ROOT . '/' . $settings_dir, FILE_NOT_WRITABLE, 'dir'))) {
     drupal_set_message(t('All necessary changes to %dir and %file have been made, so you should remove write permissions to them now in order to avoid security risks. If you are unsure how to do so, consult the <a href="@handbook_url">online handbook</a>.', array('%dir' => $settings_dir, '%file' => $settings_file, '@handbook_url' => 'http://drupal.org/server-permissions')), 'warning');
   }
 
diff --git a/core/includes/language.inc b/core/includes/language.inc
index 07cc383..618e3a7 100644
--- a/core/includes/language.inc
+++ b/core/includes/language.inc
@@ -100,7 +100,8 @@
  *   $langcode = language_from_url($languages);
  *
  *   // If we are on an administrative path, override with the default language.
- *   if (isset($_GET['q']) && strtok($_GET['q'], '/') == 'admin') {
+ *   $query = \Drupal::request()->query;
+ *   if ($query->has('q') && strtok($query->get('q'), '/') == 'admin') {
  *     return language_default()->id;
  *   }
  *   return $langcode;
diff --git a/core/includes/pager.inc b/core/includes/pager.inc
index ba7f65b..9874689 100644
--- a/core/includes/pager.inc
+++ b/core/includes/pager.inc
@@ -16,13 +16,13 @@
  *
  * @return
  *  The number of the current requested page, within the pager represented by
- *  $element. This is determined from the URL query parameter $_GET['page'], or
- *  0 by default. Note that this number may differ from the actual page being
- *  displayed. For example, if a search for "example text" brings up three
- *  pages of results, but a users visits search/node/example+text?page=10, this
- *  function will return 10, even though the default pager implementation
- *  adjusts for this and still displays the third page of search results at
- *  that URL.
+ *  $element. This is determined from the URL query parameter
+ *  \Drupal::request()->query->get('page'), or 0 by default. Note that this
+ *  number may differ from the actual page being displayed. For example, if a
+ *  search for "example text" brings up three pages of results, but a users
+ *  visits search/node/example+text?page=10, this function will return 10, even
+ *  though the default pager implementation adjusts for this and still displays
+ * the third page of search results at that URL.
  *
  * @see pager_default_initialize()
  */
@@ -109,10 +109,11 @@ function pager_find_page($element = 0) {
  *
  * @return
  *   The number of the current page, within the pager represented by $element.
- *   This is determined from the URL query parameter $_GET['page'], or 0 by
- *   default. However, if a page that does not correspond to the actual range
- *   of the result set was requested, this function will return the closest
- *   page actually within the result set.
+ *   This is determined from the URL query parameter
+ *   \Drupal::request()->query->get('page), or 0 by default. However, if a page
+ *   that does not correspond to the actual range of the result set was
+ *   requested, this function will return the closest page actually within the
+ *   result set.
  */
 function pager_default_initialize($total, $limit, $element = 0) {
   global $pager_page_array, $pager_total, $pager_total_items, $pager_limits;
diff --git a/core/includes/session.inc b/core/includes/session.inc
index 4cc8139..002d8dc 100644
--- a/core/includes/session.inc
+++ b/core/includes/session.inc
@@ -83,7 +83,8 @@ function _drupal_session_read($sid) {
   // Handle the case of first time visitors and clients that don't store
   // cookies (eg. web crawlers).
   $insecure_session_name = substr(session_name(), 1);
-  if (!isset($_COOKIE[session_name()]) && !isset($_COOKIE[$insecure_session_name])) {
+  $cookies = \Drupal::request()->cookies;
+  if (!$cookies->has(session_name()) && !$cookies->has($insecure_session_name)) {
     $user = new UserSession();
     return '';
   }
@@ -95,9 +96,9 @@ function _drupal_session_read($sid) {
   if (\Drupal::request()->isSecure()) {
     $values = db_query("SELECT u.*, s.* FROM {users} u INNER JOIN {sessions} s ON u.uid = s.uid WHERE s.ssid = :ssid", array(':ssid' => $sid))->fetchAssoc();
     if (!$values) {
-      if (isset($_COOKIE[$insecure_session_name])) {
+      if ($cookies->has($insecure_session_name)) {
         $values = db_query("SELECT u.*, s.* FROM {users} u INNER JOIN {sessions} s ON u.uid = s.uid WHERE s.sid = :sid AND s.uid = 0", array(
-        ':sid' => $_COOKIE[$insecure_session_name]))
+        ':sid' => $cookies->get($insecure_session_name)))
         ->fetchAssoc();
       }
     }
@@ -188,13 +189,14 @@ function _drupal_session_write($sid, $value) {
       // On HTTPS connections, use the session ID as both 'sid' and 'ssid'.
       if (\Drupal::request()->isSecure()) {
         $key['ssid'] = $sid;
+        $cookies = \Drupal::request()->cookies;
         // The "secure pages" setting allows a site to simultaneously use both
         // secure and insecure session cookies. If enabled and both cookies are
         // presented then use both keys.
         if (settings()->get('mixed_mode_sessions', FALSE)) {
           $insecure_session_name = substr(session_name(), 1);
-          if (isset($_COOKIE[$insecure_session_name])) {
-            $key['sid'] = $_COOKIE[$insecure_session_name];
+          if ($cookies->has($insecure_session_name)) {
+            $key['sid'] = $cookies->get($insecure_session_name);
           }
         }
       }
@@ -241,9 +243,8 @@ function drupal_session_initialize() {
   session_set_save_handler('_drupal_session_open', '_drupal_session_close', '_drupal_session_read', '_drupal_session_write', '_drupal_session_destroy', '_drupal_session_garbage_collection');
 
   $is_https = \Drupal::request()->isSecure();
-  // We use !empty() in the following check to ensure that blank session IDs
-  // are not valid.
-  if (!empty($_COOKIE[session_name()]) || ($is_https && settings()->get('mixed_mode_sessions', FALSE) && !empty($_COOKIE[substr(session_name(), 1)]))) {
+  $cookies = \Drupal::request()->cookies;
+  if ($cookies->has(session_name()) || ($is_https && settings()->get('mixed_mode_sessions', FALSE) && $cookies->has(substr(session_name(), 1)))) {
     // If a session cookie exists, initialize the session. Otherwise the
     // session is only started on demand in drupal_session_commit(), making
     // anonymous users not use a session cookie unless something is stored in
@@ -267,7 +268,7 @@ function drupal_session_initialize() {
     if ($is_https && settings()->get('mixed_mode_sessions', FALSE)) {
       $insecure_session_name = substr(session_name(), 1);
       $session_id = Crypt::hashBase64(uniqid(mt_rand(), TRUE));
-      $_COOKIE[$insecure_session_name] = $session_id;
+      $cookies->set($insecure_session_name, $session_id);
     }
   }
   date_default_timezone_set(drupal_get_user_timezone());
@@ -323,7 +324,8 @@ function drupal_session_commit() {
         $insecure_session_name = substr(session_name(), 1);
         $params = session_get_cookie_params();
         $expire = $params['lifetime'] ? REQUEST_TIME + $params['lifetime'] : 0;
-        setcookie($insecure_session_name, $_COOKIE[$insecure_session_name], $expire, $params['path'], $params['domain'], FALSE, $params['httponly']);
+        $cookie_params = \Drupal::request()->cookies;
+        setcookie($insecure_session_name, $cookie_params->get($insecure_session_name), $expire, $params['path'], $params['domain'], FALSE, $params['httponly']);
       }
     }
     // Write the session data.
@@ -356,11 +358,12 @@ function drupal_session_regenerate() {
   }
 
   $is_https = \Drupal::request()->isSecure();
+  $cookies = \Drupal::request()->cookies;
 
   if ($is_https && settings()->get('mixed_mode_sessions', FALSE)) {
     $insecure_session_name = substr(session_name(), 1);
-    if (!isset($GLOBALS['lazy_session']) && isset($_COOKIE[$insecure_session_name])) {
-      $old_insecure_session_id = $_COOKIE[$insecure_session_name];
+    if (!isset($GLOBALS['lazy_session']) && $cookies->has($insecure_session_name)) {
+      $old_insecure_session_id = $cookies->get($insecure_session_name);
     }
     $params = session_get_cookie_params();
     $session_id = Crypt::hashBase64(uniqid(mt_rand(), TRUE) . Crypt::randomBytes(55));
@@ -369,7 +372,7 @@ function drupal_session_regenerate() {
     // it will expire when the browser is closed.
     $expire = $params['lifetime'] ? REQUEST_TIME + $params['lifetime'] : 0;
     setcookie($insecure_session_name, $session_id, $expire, $params['path'], $params['domain'], FALSE, $params['httponly']);
-    $_COOKIE[$insecure_session_name] = $session_id;
+    $cookies->set($insecure_session_name, $session_id);
   }
 
   if (drupal_session_started()) {
@@ -461,13 +464,14 @@ function _drupal_session_destroy($sid) {
  *   Force the secure value of the cookie.
  */
 function _drupal_session_delete_cookie($name, $secure = NULL) {
-  if (isset($_COOKIE[$name]) || (!\Drupal::request()->isSecure() && $secure === TRUE)) {
+  $cookies = \Drupal::request()->cookies;
+  if ($cookies->has($name) || (!\Drupal::request()->isSecure() && $secure === TRUE)) {
     $params = session_get_cookie_params();
     if ($secure !== NULL) {
       $params['secure'] = $secure;
     }
     setcookie($name, '', REQUEST_TIME - 3600, $params['path'], $params['domain'], $params['secure'], $params['httponly']);
-    unset($_COOKIE[$name]);
+    $cookies->remove($name);
   }
 }
 
diff --git a/core/lib/Drupal/Component/Utility/Url.php b/core/lib/Drupal/Component/Utility/Url.php
index cdc01c8..4f61a92 100644
--- a/core/lib/Drupal/Component/Utility/Url.php
+++ b/core/lib/Drupal/Component/Utility/Url.php
@@ -34,7 +34,8 @@ class Url {
    *   http_build_query() directly.
    *
    * @param array $query
-   *   The query parameter array to be processed, e.g. $_GET.
+   *   The query parameter array to be processed,
+   *   e.g. \Drupal::request()->query->all().
    * @param string $parent
    *   Internal use only. Used to build the $query array key for nested items.
    *
@@ -118,13 +119,14 @@ public static function filterQueryParameters(array $query, array $exclude = arra
    * The returned array contains a 'path' that may be passed separately to url().
    * For example:
    * @code
-   *   $options = Url::parse($_GET['destination']);
+   *   $options = Url::parse(\Drupal::request()->query->get('destination'));
    *   $my_url = url($options['path'], $options);
    *   $my_link = l('Example link', $options['path'], $options);
    * @endcode
    *
    * @param string $url
-   *   The URL string to parse, f.e. $_GET['destination'].
+   *   The URL string to parse, i.e.
+   *     \Drupal::request()->query->get('destination').
    *
    * @return
    *   An associative array containing the keys:
diff --git a/core/lib/Drupal/Core/Ajax/AjaxResponse.php b/core/lib/Drupal/Core/Ajax/AjaxResponse.php
index 44d146a..7bd7c38 100644
--- a/core/lib/Drupal/Core/Ajax/AjaxResponse.php
+++ b/core/lib/Drupal/Core/Ajax/AjaxResponse.php
@@ -76,10 +76,11 @@ protected function ajaxRender(Request $request) {
     // diffing logic using array_diff_key().
     $ajax_page_state = $request->request->get('ajax_page_state');
     foreach (array('css', 'js') as $type) {
-      // It is highly suspicious if $_POST['ajax_page_state'][$type] is empty,
-      // since the base page ought to have at least one JS file and one CSS file
-      // loaded. It probably indicates an error, and rather than making the page
-      // reload all of the files, instead we return no new files.
+      // It is highly suspicious if
+      // $request->request->get("ajax_page_state[$type]") is empty, since the
+      // base page ought to have at least one JS file and one CSS file loaded.
+      // It probably indicates an error, and rather than making the page reload
+      // all of the files, instead we return no new files.
       if (empty($ajax_page_state[$type])) {
         $items[$type] = array();
       }
diff --git a/core/lib/Drupal/Core/EventSubscriber/RedirectResponseSubscriber.php b/core/lib/Drupal/Core/EventSubscriber/RedirectResponseSubscriber.php
index 609e909..6cc7916 100644
--- a/core/lib/Drupal/Core/EventSubscriber/RedirectResponseSubscriber.php
+++ b/core/lib/Drupal/Core/EventSubscriber/RedirectResponseSubscriber.php
@@ -48,9 +48,10 @@ public function checkRedirectUrl(FilterResponseEvent $event) {
       $options = array();
 
       $destination = $event->getRequest()->query->get('destination');
-      // A destination in $_GET always overrides the current RedirectResponse.
-      // We do not allow absolute URLs to be passed via $_GET, as this can be an
-      // attack vector, with the following exception:
+      // A destination from \Drupal::request()->query always overrides the
+      // current RedirectResponse. We do not allow absolute URLs to be passed
+      // via \Drupal::request()->query, as this can be an attack vector, with
+      // the following exception:
       // - Absolute URLs that point to this site (i.e. same base URL and
       //   base path) are allowed.
       if ($destination && (!url_is_external($destination) || _external_url_is_local($destination))) {
diff --git a/core/lib/Drupal/Core/Form/FormBuilder.php b/core/lib/Drupal/Core/Form/FormBuilder.php
index 38bfab7..883b5cb 100644
--- a/core/lib/Drupal/Core/Form/FormBuilder.php
+++ b/core/lib/Drupal/Core/Form/FormBuilder.php
@@ -202,7 +202,8 @@ public function buildForm($form_id, &$form_state) {
     $form_state += $this->getFormStateDefaults();
 
     if (!isset($form_state['input'])) {
-      $form_state['input'] = $form_state['method'] == 'get' ? $_GET : $_POST;
+      $request = \Drupal::request();
+      $form_state['input'] = $form_state['method'] == 'get' ? $request->query->all() : $request->request->all();
     }
 
     if (isset($_SESSION['batch_form_state'])) {
@@ -586,7 +587,7 @@ public function retrieveForm($form_id, &$form_state) {
   public function processForm($form_id, &$form, &$form_state) {
     $form_state['values'] = array();
 
-    // With $_GET, these forms are always submitted if requested.
+    // With GET, these forms are always submitted if requested.
     if ($form_state['method'] == 'get' && !empty($form_state['always_process'])) {
       if (!isset($form_state['input']['form_build_id'])) {
         $form_state['input']['form_build_id'] = $form['#build_id'];
@@ -1465,9 +1466,10 @@ protected function handleInputElement($form_id, &$element, &$form_state) {
       $name = array_shift($element['#parents']);
       $element['#name'] = $name;
       if ($element['#type'] == 'file') {
-        // To make it easier to handle $_FILES in file.inc, we place all
+        // To make it easier to handle files in file.inc, we place all
         // file fields in the 'files' array. Also, we do not support
         // nested file names.
+        // @todo Remove this files prefix now?
         $element['#name'] = 'files[' . $element['#name'] . ']';
       }
       elseif (count($element['#parents'])) {
@@ -1583,7 +1585,8 @@ protected function handleInputElement($form_id, &$element, &$form_state) {
       if (!empty($element['#is_button'])) {
         // All buttons in the form need to be tracked for
         // form_state_values_clean() and for the self::doBuildForm() code that
-        // handles a form submission containing no button information in $_POST.
+        // handles a form submission containing no button information in
+        // \Drupal::request()->request.
         $form_state['buttons'][] = $element;
         if ($this->buttonWasClicked($element, $form_state)) {
           $form_state['triggering_element'] = $element;
@@ -1643,15 +1646,15 @@ protected function buttonWasClicked($element, &$form_state) {
     // buttons on a form share the same name (usually 'op'), and the specific
     // return value is used to determine which was clicked. This ONLY works as
     // long as $form['#name'] puts the value at the top level of the tree of
-    // $_POST data.
+    // \Drupal::request()->request data.
     if (isset($form_state['input'][$element['#name']]) && $form_state['input'][$element['#name']] == $element['#value']) {
       return TRUE;
     }
     // When image buttons are clicked, browsers do NOT pass the form element
-    // value in $_POST. Instead they pass an integer representing the
-    // coordinates of the click on the button image. This means that image
-    // buttons MUST have unique $form['#name'] values, but the details of their
-    // $_POST data should be ignored.
+    // value in \Drupal::request()->Request. Instead they pass an integer
+    // representing the coordinates of the click on the button image. This means
+    // that image buttons MUST have unique $form['#name'] values, but the
+    // details of their \Drupal::request()->request data should be ignored.
     elseif (!empty($element['#has_garbage_value']) && isset($element['#value']) && $element['#value'] !== '') {
       return TRUE;
     }
diff --git a/core/lib/Drupal/Core/Form/FormBuilderInterface.php b/core/lib/Drupal/Core/Form/FormBuilderInterface.php
index aa09c41..c6657bd 100644
--- a/core/lib/Drupal/Core/Form/FormBuilderInterface.php
+++ b/core/lib/Drupal/Core/Form/FormBuilderInterface.php
@@ -154,8 +154,9 @@ public function getForm($form_arg);
    *     understanding of security implications. In almost all cases, code
    *     should use the data in the 'values' array exclusively. The most common
    *     use of this key is for multi-step forms that need to clear some of the
-   *     user input when setting 'rebuild'. The values correspond to $_POST or
-   *     $_GET, depending on the 'method' chosen.
+   *     user input when setting 'rebuild'. The values correspond to
+   *     \Drupal::request()->request or \Drupal::request()->query, depending on
+   *     the 'method' chosen.
    *   - always_process: If TRUE and the method is GET, a form_id is not
    *     necessary. This should only be used on RESTful GET forms that do NOT
    *     write data, as this could lead to security issues. It is useful so that
@@ -169,8 +170,8 @@ public function getForm($form_arg);
    *     invoked via self::submitForm(). Defaults to FALSE.
    *   - process_input: Boolean flag. TRUE signifies correct form submission.
    *     This is always TRUE for programmed forms coming from self::submitForm()
-   *     (see 'programmed' key), or if the form_id coming from the $_POST data
-   *     is set and matches the current form_id.
+   *     (see 'programmed' key), or if the form_id coming from the
+   *     \Drupal::request()->request data is set and matches the current form_id.
    *   - submitted: If TRUE, the form has been submitted. Defaults to FALSE.
    *   - executed: If TRUE, the form was submitted and has been processed and
    *     executed. Defaults to FALSE.
@@ -309,11 +310,12 @@ public function setCache($form_build_id, $form, $form_state);
    * @param $form_state
    *   A keyed array containing the current state of the form. Most important is
    *   the $form_state['values'] collection, a tree of data used to simulate the
-   *   incoming $_POST information from a user's form submission. If a key is
-   *   not filled in $form_state['values'], then the default value of the
-   *   respective element is used. To submit an unchecked checkbox or other
-   *   control that browsers submit by not having a $_POST entry, include the
-   *   key, but set the value to NULL.
+   *   incoming \Drupal::request()->request information from a user's form
+   *   submission. If a key is not filled in $form_state['values'], then the
+   *   default value of the respective element is used. To submit an unchecked
+   *   checkbox or other control that browsers submit by not having a
+   *   \Drupal::request()->request entry, include the key, but set the value to
+   *   NULL.
    * @param ...
    *   Any additional arguments are passed on to the functions called by
    *   self::submitForm(), including the unique form constructor function.
@@ -378,8 +380,8 @@ public function retrieveForm($form_id, &$form_state);
    *   A keyed array containing the current state of the form. This
    *   includes the current persistent storage data for the form, and
    *   any data passed along by earlier steps when displaying a
-   *   multi-step form. Additional information, like the sanitized $_POST
-   *   data, is also accumulated here.
+   *   multi-step form. Additional information, like the sanitized
+   *   \Drupal::request()->request data, is also accumulated here.
    *
    * @return \Symfony\Component\HttpFoundation\RedirectResponse|null
    */
@@ -477,8 +479,9 @@ public function validateForm($form_id, &$form, &$form_state);
    *   redirect is accomplished by returning a RedirectResponse, passing in the
    *   value of $form_state['redirect'] if it is set, or the current path if it
    *   is not. RedirectResponse preferentially uses the value of
-   *   $_GET['destination'] (the 'destination' URL query string) if it is
-   *   present, so this will override any values set by $form_state['redirect'].
+   *   \Drupal::request->query->get('destination') (the 'destination' URL query
+   *   string) if it is present, so this will override any values set by
+   *   $form_state['redirect'].
    *
    * @param $form_state
    *   An associative array containing the current state of the form.
@@ -721,7 +724,7 @@ public function setError(&$element, $message = '');
    *   A keyed array containing the current state of the form. In this
    *   context, it is used to accumulate information about which button
    *   was clicked when the form was submitted, as well as the sanitized
-   *   $_POST data.
+   *   \Drupal::request()->request data.
    *
    * @return array
    */
diff --git a/core/modules/aggregator/lib/Drupal/aggregator/Form/OpmlFeedAdd.php b/core/modules/aggregator/lib/Drupal/aggregator/Form/OpmlFeedAdd.php
index abf1cad..e2a1ce7 100644
--- a/core/modules/aggregator/lib/Drupal/aggregator/Form/OpmlFeedAdd.php
+++ b/core/modules/aggregator/lib/Drupal/aggregator/Form/OpmlFeedAdd.php
@@ -138,7 +138,8 @@ public function buildForm(array $form, array &$form_state) {
    */
   public function validateForm(array &$form, array &$form_state) {
     // If both fields are empty or filled, cancel.
-    if (empty($form_state['values']['remote']) == empty($_FILES['files']['name']['upload'])) {
+    $file_upload = $this->getRequest()->files->get('files[upload]', NULL, TRUE);
+    if (empty($form_state['values']['remote']) == empty($file_upload)) {
       form_set_error('remote', $this->t('You must <em>either</em> upload a file or enter a URL.'));
     }
   }
diff --git a/core/modules/config/lib/Drupal/config/Form/ConfigImportForm.php b/core/modules/config/lib/Drupal/config/Form/ConfigImportForm.php
index 2d5c4a8..d34350a 100644
--- a/core/modules/config/lib/Drupal/config/Form/ConfigImportForm.php
+++ b/core/modules/config/lib/Drupal/config/Form/ConfigImportForm.php
@@ -74,11 +74,12 @@ public function buildForm(array $form, array &$form_state) {
    * {@inheritdoc}
    */
   public function validateForm(array &$form, array &$form_state) {
-    if (!empty($_FILES['files']['error']['import_tarball'])) {
-      form_set_error('import_tarball', $this->t('The import tarball could not be uploaded.'));
+    $file_upload = $this->getRequest()->files->get('files[import_tarball]', NULL, TRUE);
+    if ($file_upload && $file_upload->isValid()) {
+      $form_state['values']['import_tarball'] = $file_upload->getRealPath();
     }
     else {
-      $form_state['values']['import_tarball'] = $_FILES['files']['tmp_name']['import_tarball'];
+      form_set_error('import_tarball', $this->t('The import tarball could not be uploaded.'));
     }
   }
 
diff --git a/core/modules/editor/lib/Drupal/editor/Form/EditorImageDialog.php b/core/modules/editor/lib/Drupal/editor/Form/EditorImageDialog.php
index 1811bcd..4f5ffc4 100644
--- a/core/modules/editor/lib/Drupal/editor/Form/EditorImageDialog.php
+++ b/core/modules/editor/lib/Drupal/editor/Form/EditorImageDialog.php
@@ -33,8 +33,8 @@ public function getFormId() {
    *   The filter format for which this dialog corresponds.
    */
   public function buildForm(array $form, array &$form_state, FilterFormat $filter_format = NULL) {
-    // The default values are set directly from $_POST, provided by the
-    // editor plugin opening the dialog.
+    // The default values are set directly from \Drupal::request()->request,
+    // provided by the editor plugin opening the dialog.
     if (!isset($form_state['image_element'])) {
       $form_state['image_element'] = isset($form_state['input']['editor_object']) ? $form_state['input']['editor_object'] : array();
     }
diff --git a/core/modules/editor/lib/Drupal/editor/Form/EditorLinkDialog.php b/core/modules/editor/lib/Drupal/editor/Form/EditorLinkDialog.php
index 42f47cb..71af79d 100644
--- a/core/modules/editor/lib/Drupal/editor/Form/EditorLinkDialog.php
+++ b/core/modules/editor/lib/Drupal/editor/Form/EditorLinkDialog.php
@@ -33,8 +33,8 @@ public function getFormId() {
    *   The filter format for which this dialog corresponds.
    */
   public function buildForm(array $form, array &$form_state, FilterFormat $filter_format = NULL) {
-    // The default values are set directly from $_POST, provided by the
-    // editor plugin opening the dialog.
+    // The default values are set directly from \Drupal::request()->request,
+    // provided by the editor plugin opening the dialog.
     $input = isset($form_state['input']['editor_object']) ? $form_state['input']['editor_object'] : array();
 
     $form['#tree'] = TRUE;
diff --git a/core/modules/file/file.module b/core/modules/file/file.module
index bf67993..46f0558 100644
--- a/core/modules/file/file.module
+++ b/core/modules/file/file.module
@@ -768,8 +768,9 @@ function file_save_upload($form_field_name, $validators = array(), $destination
   $user = \Drupal::currentUser();
   static $upload_cache;
 
+  $file_upload = \Drupal::request()->files->get("files[$form_field_name]", NULL, TRUE);
   // Make sure there's an upload to process.
-  if (empty($_FILES['files']['name'][$form_field_name])) {
+  if (empty($file_upload)) {
     return NULL;
   }
 
@@ -784,40 +785,39 @@ function file_save_upload($form_field_name, $validators = array(), $destination
 
   // Prepare uploaded files info. Representation is slightly different
   // for multiple uploads and we fix that here.
-  $uploaded_files = $_FILES;
-  if (!is_array($uploaded_files['files']['name'][$form_field_name])) {
-    foreach (array('name', 'type', 'tmp_name', 'error', 'size') as $value)
-    $uploaded_files['files'][$value][$form_field_name] = array($uploaded_files['files'][$value][$form_field_name]);
+  $uploaded_files = $file_upload;
+  if (!is_array($file_upload)) {
+    $uploaded_files = array($file_upload);
   }
 
   $files = array();
-  foreach ($uploaded_files['files']['name'][$form_field_name] as $i => $name) {
+  foreach ($uploaded_files as $i => $file_info) {
     // Check for file upload errors and return FALSE for this file if a lower
     // level system error occurred. For a complete list of errors:
     // See http://php.net/manual/features.file-upload.errors.php.
-    switch ($uploaded_files['files']['error'][$form_field_name][$i]) {
+    switch ($file_info->getError()) {
       case UPLOAD_ERR_INI_SIZE:
       case UPLOAD_ERR_FORM_SIZE:
-        drupal_set_message(t('The file %file could not be saved because it exceeds %maxsize, the maximum allowed size for uploads.', array('%file' => $name, '%maxsize' => format_size(file_upload_max_size()))), 'error');
+        drupal_set_message(t('The file %file could not be saved because it exceeds %maxsize, the maximum allowed size for uploads.', array('%file' => $file_info->getFilename(), '%maxsize' => format_size(file_upload_max_size()))), 'error');
         $files[$i] = FALSE;
         continue;
 
       case UPLOAD_ERR_PARTIAL:
       case UPLOAD_ERR_NO_FILE:
-        drupal_set_message(t('The file %file could not be saved because the upload did not complete.', array('%file' => $name)), 'error');
+        drupal_set_message(t('The file %file could not be saved because the upload did not complete.', array('%file' => $file_info->getFilename())), 'error');
         $files[$i] = FALSE;
         continue;
 
       case UPLOAD_ERR_OK:
         // Final check that this is a valid upload, if it isn't, use the
         // default error handler.
-        if (is_uploaded_file($uploaded_files['files']['tmp_name'][$form_field_name][$i])) {
+        if (is_uploaded_file($file_info->getRealPath())) {
           break;
         }
 
         // Unknown error
       default:
-        drupal_set_message(t('The file %file could not be saved. An unknown error has occurred.', array('%file' => $name)), 'error');
+        drupal_set_message(t('The file %file could not be saved. An unknown error has occurred.', array('%file' => $file_info->getFilename())), 'error');
         $files[$i] = FALSE;
         continue;
 
@@ -826,9 +826,9 @@ function file_save_upload($form_field_name, $validators = array(), $destination
     $values = array(
       'uid' => $user->id(),
       'status' => 0,
-      'filename' => trim(drupal_basename($name, '.')),
-      'uri' => $uploaded_files['files']['tmp_name'][$form_field_name][$i],
-      'filesize' => $uploaded_files['files']['size'][$form_field_name][$i],
+      'filename' => $file_info->getClientOriginalName(),
+      'uri' => $file_info->getRealPath(),
+      'filesize' => $file_info->getSize(),
     );
     $values['filemime'] = file_get_mimetype($values['filename']);
     $file = entity_create('file', $values);
@@ -931,7 +931,7 @@ function file_save_upload($form_field_name, $validators = array(), $destination
     // directory. This overcomes open_basedir restrictions for future file
     // operations.
     $file->uri = $file->destination;
-    if (!drupal_move_uploaded_file($uploaded_files['files']['tmp_name'][$form_field_name][$i], $file->getFileUri())) {
+    if (!drupal_move_uploaded_file($file_info->getRealPath(), $file->getFileUri())) {
       form_set_error($form_field_name, t('File upload error. Could not move uploaded file.'));
       watchdog('file', 'Upload error. Could not move uploaded file %file to destination %destination.', array('%file' => $file->filename, '%destination' => $file->uri));
       $files[$i] = FALSE;
@@ -1459,7 +1459,8 @@ function file_managed_file_submit($form, &$form_state) {
  */
 function file_managed_file_save_upload($element) {
   $upload_name = implode('_', $element['#parents']);
-  if (empty($_FILES['files']['name'][$upload_name])) {
+  $file_upload = \Drupal::request()->files->get("files[$upload_name]", NULL, TRUE);
+  if (empty($file_upload)) {
     return FALSE;
   }
 
@@ -1471,8 +1472,8 @@ function file_managed_file_save_upload($element) {
   }
 
   // Save attached files to the database.
-  $files_uploaded = $element['#multiple'] && count(array_filter($_FILES['files']['name'][$upload_name])) > 0;
-  $files_uploaded |= !$element['#multiple'] && !empty($_FILES['files']['name'][$upload_name]);
+  $files_uploaded = $element['#multiple'] && count(array_filter($file_upload)) > 0;
+  $files_uploaded |= !$element['#multiple'] && !empty($file_upload);
   if ($files_uploaded) {
     if (!$files = file_save_upload($upload_name, $element['#upload_validators'], $destination)) {
       watchdog('file', 'The file upload failed. %upload', array('%upload' => $upload_name));
diff --git a/core/modules/node/lib/Drupal/node/Plugin/Search/NodeSearch.php b/core/modules/node/lib/Drupal/node/Plugin/Search/NodeSearch.php
index 0dbd1ac..242f580 100644
--- a/core/modules/node/lib/Drupal/node/Plugin/Search/NodeSearch.php
+++ b/core/modules/node/lib/Drupal/node/Plugin/Search/NodeSearch.php
@@ -176,8 +176,8 @@ public function execute() {
       ->searchExpression($keys, $this->getPluginId());
 
     // Handle advanced search filters in the f query string.
-    // $_GET['f'] is an array that looks like this in the URL:
-    // ?f[]=type:page&f[]=term:27&f[]=term:13&f[]=langcode:en
+    // \Drupal::request()->query->get('f') is an array that looks like this in
+    // the URL: ?f[]=type:page&f[]=term:27&f[]=term:13&f[]=langcode:en
     // So $parameters['f'] looks like:
     // array('type:page', 'term:27', 'term:13', 'langcode:en');
     // We need to parse this out into query conditions.
diff --git a/core/modules/search/lib/Drupal/search/Controller/SearchController.php b/core/modules/search/lib/Drupal/search/Controller/SearchController.php
index 18f38e3..df11240 100644
--- a/core/modules/search/lib/Drupal/search/Controller/SearchController.php
+++ b/core/modules/search/lib/Drupal/search/Controller/SearchController.php
@@ -72,8 +72,8 @@ public static function create(ContainerInterface $container) {
   public function view(Request $request, $plugin_id = NULL, $keys = NULL) {
     $info = FALSE;
     $keys = trim($keys);
-    // Also try to pull search keywords out of the $_REQUEST variable to
-    // support old GET format of searches for existing links.
+    // Also try to pull search keywords from the request to support old GET
+    // format of searches for existing links.
     if (!$keys && $request->query->has('keys')) {
       $keys = trim($request->query->get('keys'));
     }
@@ -104,11 +104,11 @@ public function view(Request $request, $plugin_id = NULL, $keys = NULL) {
     // Default results output is an empty string.
     $results = array('#markup' => '');
 
-    // Process the search form. Note that if there is $_POST data,
-    // search_form_submit() will cause a redirect to search/[path]/[keys],
-    // which will get us back to this page callback. In other words, the search
-    // form submits with POST but redirects to GET. This way we can keep
-    // the search query URL clean as a whistle.
+    // Process the search form. Note that if there is
+    // \Drupal::request()->request data, search_form_submit() will cause a
+    // redirect to search/[path]/[keys], which will get us back to this page
+    // callback. In other words, the search form submits with POST but redirects
+    // to GET. This way we can keep the search query URL clean as a whistle.
     if ($request->request->has('form_id') || $request->request->get('form_id') != 'search_form') {
       // Only search if there are keywords or non-empty conditions.
       if ($plugin->isSearchExecutable()) {
diff --git a/core/modules/search/search.module b/core/modules/search/search.module
index 3fc2953..bf431cd 100644
--- a/core/modules/search/search.module
+++ b/core/modules/search/search.module
@@ -672,8 +672,9 @@ function search_box_form_submit($form, &$form_state) {
   // The search form relies on control of the redirect destination for its
   // functionality, so we override any static destination set in the request.
   // See http://drupal.org/node/292565.
-  if (isset($_GET['destination'])) {
-    unset($_GET['destination']);
+  $query = \Drupal::request()->query;
+  if ($query->has('destination')) {
+    $query->remove('destination');
   }
 
   // Check to see if the form was submitted empty.
diff --git a/core/modules/simpletest/lib/Drupal/simpletest/WebTestBase.php b/core/modules/simpletest/lib/Drupal/simpletest/WebTestBase.php
index a4c7b27..813019e 100644
--- a/core/modules/simpletest/lib/Drupal/simpletest/WebTestBase.php
+++ b/core/modules/simpletest/lib/Drupal/simpletest/WebTestBase.php
@@ -1138,8 +1138,9 @@ protected function curlExec($curl_options, $redirect = FALSE) {
     // so you can't debug actual running code. In order to make debuggers work
     // this bit of information is forwarded. Make sure that the debugger listens
     // to at least three external connections.
-    if (isset($_COOKIE['XDEBUG_SESSION'])) {
-      $cookies[] = 'XDEBUG_SESSION=' . $_COOKIE['XDEBUG_SESSION'];
+    $cookie_params = \Drupal::request()->cookies;
+    if ($cookie_params->has('XDEBUG_SESSION')) {
+      $cookies[] = 'XDEBUG_SESSION=' . $cookie_params->get('XDEBUG_SESSION');
     }
 
     // Merge additional cookies in.
diff --git a/core/modules/system/lib/Drupal/system/Tests/Common/TableSortExtenderUnitTest.php b/core/modules/system/lib/Drupal/system/Tests/Common/TableSortExtenderUnitTest.php
index 241949f..59eca4a 100644
--- a/core/modules/system/lib/Drupal/system/Tests/Common/TableSortExtenderUnitTest.php
+++ b/core/modules/system/lib/Drupal/system/Tests/Common/TableSortExtenderUnitTest.php
@@ -15,13 +15,6 @@
  */
 class TableSortExtenderUnitTest extends UnitTestBase {
 
-  /**
-   * Storage for initial value of $_GET.
-   *
-   * @var array
-   */
-  protected $GET = array();
-
   public static function getInfo() {
     return array(
       'name' => 'Tablesort',
@@ -30,20 +23,6 @@ public static function getInfo() {
     );
   }
 
-  function setUp() {
-    // Save the original $_GET to be restored later.
-    $this->GET = $_GET;
-
-    parent::setUp();
-  }
-
-  function tearDown() {
-    // Revert $_GET.
-    $_GET = $this->GET;
-
-    parent::tearDown();
-  }
-
   /**
    * Tests tablesort_init().
    */
@@ -52,8 +31,8 @@ function testTableSortInit() {
     // Test simple table headers.
 
     $headers = array('foo', 'bar', 'baz');
-    // Reset $_GET to prevent parameters from Simpletest and Batch API ending
-    // up in $ts['query'].
+    // Reset $requesr->query to prevent parameters from Simpletest and Batch API
+    // ending up in $ts['query'].
     $expected_ts = array(
       'name' => 'foo',
       'sql' => '',
diff --git a/core/modules/system/lib/Drupal/system/Tests/Form/TriggeringElementTest.php b/core/modules/system/lib/Drupal/system/Tests/Form/TriggeringElementTest.php
index 2ca12a1..1c4f1df 100644
--- a/core/modules/system/lib/Drupal/system/Tests/Form/TriggeringElementTest.php
+++ b/core/modules/system/lib/Drupal/system/Tests/Form/TriggeringElementTest.php
@@ -95,7 +95,7 @@ function testAttemptAccessControlBypass() {
     // trying to get around security safeguards could easily do. We have to do
     // a little trickery here, to work around the safeguards in drupalPostForm(): by
     // renaming the text field that is in the form to 'button1', we can get the
-    // data we want into $_POST.
+    // data we want into \Drupal::request()->request.
     $elements = $this->xpath('//form[@id="' . $form_html_id . '"]//input[@name="text"]');
     $elements[0]['name'] = 'button1';
     $this->drupalPostForm(NULL, array('button1' => 'button1'), NULL, array(), array(), $form_html_id);
diff --git a/core/modules/system/system.module b/core/modules/system/system.module
index 66e5a6f..fbe459e 100644
--- a/core/modules/system/system.module
+++ b/core/modules/system/system.module
@@ -899,8 +899,9 @@ function system_theme_suggestions_region(array $variables) {
 function _system_batch_theme() {
   // Retrieve the current state of the batch.
   $batch = &batch_get();
-  if (!$batch && isset($_REQUEST['id'])) {
-    $batch = \Drupal::service('batch.storage')->load($_REQUEST['id']);
+  $request_params = \Drupal::request()->request;
+  if (!$batch && $request_params->has('id')) {
+    $batch = \Drupal::service('batch.storage')->load($request_params->get('id'));
   }
   // Use the same theme as the page that started the batch.
   if (!empty($batch['theme'])) {
@@ -2743,7 +2744,8 @@ function system_default_region($theme) {
  *
  * If the submit handler for a form that implements confirm_form() is invoked,
  * the user successfully confirmed the action. You should never directly
- * inspect $_POST to see if an action was confirmed.
+ * inspect $_POST or \Drupal::request()->request to see if an action was
+ * confirmed.
  *
  * Note - if the parameters $question, $description, $yes, or $no could contain
  * any user input (such as node titles or taxonomy terms), it is the
@@ -2838,7 +2840,7 @@ function confirm_form($form, $question, $path, $description = NULL, $yes = NULL,
 function system_admin_compact_mode() {
   // PHP converts dots into underscores in cookie names to avoid problems with
   // its parser, so we use a converted cookie name.
-  return isset($_COOKIE['Drupal_visitor_admin_compact_mode']) ? $_COOKIE['Drupal_visitor_admin_compact_mode'] : \Drupal::config('system.site')->get('admin_compact_mode');
+  return \Drupal::request()->cookies->get('Drupal_visitor_admin_compact_mode', \Drupal::config('system.site')->get('admin_compact_mode'));
 }
 
 /**
diff --git a/core/modules/system/tests/modules/ajax_test/ajax_test.module b/core/modules/system/tests/modules/ajax_test/ajax_test.module
index 802b34e..4f30edd 100644
--- a/core/modules/system/tests/modules/ajax_test/ajax_test.module
+++ b/core/modules/system/tests/modules/ajax_test/ajax_test.module
@@ -78,8 +78,9 @@ function ajax_test_order() {
  */
 function ajax_test_error() {
   $message = '';
-  if (!empty($_GET['message'])) {
-    $message = $_GET['message'];
+  $query = \Drupal::request()->query;
+  if ($query->has('message')) {
+    $message = $query->get('message');
   }
   $response = new AjaxResponse();
   $response->addCommand(new AlertCommand($message));
diff --git a/core/modules/system/tests/modules/form_test/form_test.module b/core/modules/system/tests/modules/form_test/form_test.module
index a3d1cd0..526033d 100644
--- a/core/modules/system/tests/modules/form_test/form_test.module
+++ b/core/modules/system/tests/modules/form_test/form_test.module
@@ -605,7 +605,7 @@ function form_test_storage_form($form, &$form_state) {
     '#value' => 'Save',
   );
 
-  if (isset($_REQUEST['cache'])) {
+  if (\Drupal::request()->request->has('cache')) {
     // Manually activate caching, so we can test that the storage keeps working
     // when it's enabled.
     $form_state['cache'] = TRUE;
@@ -624,7 +624,7 @@ function form_test_storage_element_validate_value_cached($element, &$form_state)
   // This presumes that another submitted form value triggers a validation error
   // elsewhere in the form. Form API should still update the cached form storage
   // though.
-  if (isset($_REQUEST['cache']) && $form_state['values']['value'] == 'change_title') {
+  if (\Drupal::request()->request->has('cache') && $form_state['values']['value'] == 'change_title') {
     $form_state['storage']['thing']['changed'] = TRUE;
   }
 }
@@ -1760,7 +1760,7 @@ function form_test_state_persist_submit($form, &$form_state) {
 function form_test_form_form_test_state_persist_alter(&$form, &$form_state) {
   // Simulate a form alter implementation inserting form elements that enable
   // caching of the form, e.g. elements having #ajax.
-  if (!empty($_REQUEST['cache'])) {
+  if (\Drupal::request()->request->has('cache')) {
     $form_state['cache'] = TRUE;
   }
 }
@@ -1973,7 +1973,7 @@ function form_test_form_user_register_form_alter(&$form, &$form_state) {
     '#submit' => array('form_test_user_register_form_rebuild'),
   );
   // If requested, add the test field by attaching the node page form.
-  if (!empty($_REQUEST['field'])) {
+  if (\Drupal::request()->request->has('field')) {
     $node = entity_create('node', array(
       'type' => 'page',
     ));
diff --git a/core/modules/system/tests/modules/menu_test/menu_test.module b/core/modules/system/tests/modules/menu_test/menu_test.module
index 566a620..629fae4 100644
--- a/core/modules/system/tests/modules/menu_test/menu_test.module
+++ b/core/modules/system/tests/modules/menu_test/menu_test.module
@@ -11,7 +11,7 @@
  * Implements hook_menu().
  */
 function menu_test_menu() {
-  // The name of the menu changes during the course of the test. Using a $_GET.
+  // The name of the menu changes during the course of the test. Using a GET.
   $items['menu_name_test'] = array(
     'title' => 'Test menu_name router item',
     'route_name' => 'menu_test.menu_name_test',
diff --git a/core/modules/system/tests/modules/system_test/system_test.module b/core/modules/system/tests/modules/system_test/system_test.module
index 56ae206..aa93e6d 100644
--- a/core/modules/system/tests/modules/system_test/system_test.module
+++ b/core/modules/system/tests/modules/system_test/system_test.module
@@ -8,8 +8,9 @@
  * @deprecated \Drupal\system_test\Controller\SystemTestController::setHeader()
  */
 function system_test_set_header() {
-  drupal_add_http_header($_GET['name'], $_GET['value']);
-  return t('The following header was set: %name: %value', array('%name' => $_GET['name'], '%value' => $_GET['value']));
+  $query = \Drupal::request()->query->all();
+  drupal_add_http_header($query['name'], $query['value']);
+  return t('The following header was set: %name: %value', array('%name' => $query['name'], '%value' => $query['value']));
 }
 
 /**
diff --git a/core/modules/taxonomy/lib/Drupal/taxonomy/Form/OverviewTerms.php b/core/modules/taxonomy/lib/Drupal/taxonomy/Form/OverviewTerms.php
index 3852ea8..1cd031f 100644
--- a/core/modules/taxonomy/lib/Drupal/taxonomy/Form/OverviewTerms.php
+++ b/core/modules/taxonomy/lib/Drupal/taxonomy/Form/OverviewTerms.php
@@ -170,7 +170,7 @@ public function buildForm(array $form, array &$form_state, VocabularyInterface $
     // error. Ensure the form is rebuilt in the same order as the user
     // submitted.
     if (!empty($form_state['input'])) {
-      // Get the $_POST order.
+      // Get the POST order.
       $order = array_flip(array_keys($form_state['input']['terms']));
       // Update our form with the new order.
       $current_page = array_merge($order, $current_page);
diff --git a/core/modules/update/update.manager.inc b/core/modules/update/update.manager.inc
index 6063dfc..0796679 100644
--- a/core/modules/update/update.manager.inc
+++ b/core/modules/update/update.manager.inc
@@ -632,7 +632,8 @@ function _update_manager_check_backends(&$form, $operation) {
  * @see update_manager_install_form_submit()
  */
 function update_manager_install_form_validate($form, &$form_state) {
-  if (!($form_state['values']['project_url'] XOR !empty($_FILES['files']['name']['project_upload']))) {
+  $uploaded_file = \Drupal::request()->files->get('files[project_upload]', NULL, TRUE);
+  if (!($form_state['values']['project_url'] XOR !empty($uploaded_file))) {
     form_set_error('project_url', t('You must either provide a URL or upload an archive file to install.'));
   }
 }
diff --git a/core/modules/views/lib/Drupal/views/Controller/ViewAjaxController.php b/core/modules/views/lib/Drupal/views/Controller/ViewAjaxController.php
index e1aae78..307d63f 100644
--- a/core/modules/views/lib/Drupal/views/Controller/ViewAjaxController.php
+++ b/core/modules/views/lib/Drupal/views/Controller/ViewAjaxController.php
@@ -106,8 +106,8 @@ public function ajaxView(Request $request) {
           $request->attributes->set('_system_path', $path);
         }
 
-        // Add all $_POST data, because AJAX is always a post and many things,
-        // such as tablesorts, exposed filters and paging assume $_GET.
+        // Add all POST data, because AJAX is always a post and many things,
+        // such as tablesorts, exposed filters and paging assume GET.
         $request_all = $request->request->all();
         $query_all = $request->query->all();
         $request->query->replace($request_all + $query_all);
diff --git a/core/modules/views/lib/Drupal/views/Plugin/views/HandlerBase.php b/core/modules/views/lib/Drupal/views/Plugin/views/HandlerBase.php
index 763622f..d226f40 100644
--- a/core/modules/views/lib/Drupal/views/Plugin/views/HandlerBase.php
+++ b/core/modules/views/lib/Drupal/views/Plugin/views/HandlerBase.php
@@ -448,7 +448,7 @@ public function showExposeForm(&$form, &$form_state) {
     $this->buildExposeForm($form, $form_state);
 
     // When we click the expose button, we add new gadgets to the form but they
-    // have no data in $_POST so their defaults get wiped out. This prevents
+    // have no data in POST so their defaults get wiped out. This prevents
     // these defaults from getting wiped out. This setting will only be TRUE
     // during a 2nd pass rerender.
     if (!empty($form_state['force_expose_options'])) {
diff --git a/core/modules/views/lib/Drupal/views/Plugin/views/field/FieldPluginBase.php b/core/modules/views/lib/Drupal/views/Plugin/views/field/FieldPluginBase.php
index 1f8264e..287f1e3 100644
--- a/core/modules/views/lib/Drupal/views/Plugin/views/field/FieldPluginBase.php
+++ b/core/modules/views/lib/Drupal/views/Plugin/views/field/FieldPluginBase.php
@@ -1482,7 +1482,7 @@ public function getRenderTokens($item) {
       $tokens['!' . $count] = isset($this->view->args[$count - 1]) ? strip_tags(decode_entities($this->view->args[$count - 1])) : '';
     }
 
-    // Get flattened set of tokens for any array depth in $_GET parameters.
+    // Get flattened set of tokens for any array depth in query parameters.
     $tokens += $this->getTokenValuesRecursive(\Drupal::request()->query->all());
 
     // Now add replacements for our fields.
diff --git a/core/modules/views/lib/Drupal/views/Plugin/views/filter/FilterPluginBase.php b/core/modules/views/lib/Drupal/views/Plugin/views/filter/FilterPluginBase.php
index ba2adde..905fa94 100644
--- a/core/modules/views/lib/Drupal/views/Plugin/views/filter/FilterPluginBase.php
+++ b/core/modules/views/lib/Drupal/views/Plugin/views/filter/FilterPluginBase.php
@@ -352,7 +352,7 @@ public function showBuildGroupForm(&$form, &$form_state) {
     $this->buildExposedFiltersGroupForm($form, $form_state);
 
     // When we click the expose button, we add new gadgets to the form but they
-    // have no data in $_POST so their defaults get wiped out. This prevents
+    // have no data in POST so their defaults get wiped out. This prevents
     // these defaults from getting wiped out. This setting will only be TRUE
     // during a 2nd pass rerender.
     if (!empty($form_state['force_build_group_options'])) {
diff --git a/core/modules/views/lib/Drupal/views/ViewExecutable.php b/core/modules/views/lib/Drupal/views/ViewExecutable.php
index 41050d6..76c12bd 100644
--- a/core/modules/views/lib/Drupal/views/ViewExecutable.php
+++ b/core/modules/views/lib/Drupal/views/ViewExecutable.php
@@ -556,7 +556,7 @@ public function ajaxEnabled() {
 
   /**
    * Set the exposed filters input to an array. If unset they will be taken
-   * from $_GET when the time comes.
+   * from \Drupal::request()->query when the time comes.
    */
   public function setExposedInput($filters) {
     $this->exposed_input = $filters;
@@ -566,8 +566,8 @@ public function setExposedInput($filters) {
    * Figure out what the exposed input for this view is.
    */
   public function getExposedInput() {
-    // Fill our input either from $_GET or from something previously set on the
-    // view.
+    // Fill our input either from \Drupal::request()->query or from something
+    // previously set on the view.
     if (empty($this->exposed_input)) {
       $this->exposed_input = \Drupal::request()->query->all();
       // unset items that are definitely not our input:
diff --git a/core/modules/views/views.module b/core/modules/views/views.module
index 279f14c..0cd5aa6 100644
--- a/core/modules/views/views.module
+++ b/core/modules/views/views.module
@@ -1296,7 +1296,7 @@ function views_exposed_form($form, &$form_state) {
 
   $form['actions'] = array('#type' => 'actions');
   $form['actions']['submit'] = array(
-    // Prevent from showing up in $_GET.
+    // Prevent from showing up in \Drupal::request()->query.
     '#name' => '',
     '#type' => 'submit',
     '#value' => t('Apply'),
diff --git a/core/modules/views_ui/admin.inc b/core/modules/views_ui/admin.inc
index 8631f25..851e589 100644
--- a/core/modules/views_ui/admin.inc
+++ b/core/modules/views_ui/admin.inc
@@ -422,10 +422,10 @@ function views_ui_build_form_path($form_state) {
  * #process callback for a button; determines if a button is the form's triggering element.
  *
  * The Form API has logic to determine the form's triggering element based on
- * the data in $_POST. However, it only checks buttons based on a single #value
+ * the data in POST. However, it only checks buttons based on a single #value
  * per button. This function may be added to a button's #process callbacks to
  * extend button click detection to support multiple #values per button. If the
- * data in $_POST matches any value in the button's #values array, then the
+ * data in POST matches any value in the button's #values array, then the
  * button is detected as having been clicked. This can be used when the value
  * (label) of the same logical button may be different based on context (e.g.,
  * "Apply" vs. "Apply and continue").
diff --git a/core/modules/views_ui/lib/Drupal/views_ui/ViewEditFormController.php b/core/modules/views_ui/lib/Drupal/views_ui/ViewEditFormController.php
index 5f81565..e2f6876 100644
--- a/core/modules/views_ui/lib/Drupal/views_ui/ViewEditFormController.php
+++ b/core/modules/views_ui/lib/Drupal/views_ui/ViewEditFormController.php
@@ -289,9 +289,6 @@ public function submit(array $form, array &$form_state) {
         if (($display->getPluginId() == 'page') && ($old_path == $destination) && ($old_path != $view->getExecutable()->displayHandlers->get($id)->getOption('path'))) {
           $destination = $view->getExecutable()->displayHandlers->get($id)->getOption('path');
           $query->remove('destination');
-          // @todo For whatever reason drupal_goto is still using $_GET.
-          // @see http://drupal.org/node/1668866
-          unset($_GET['destination']);
         }
       }
       $form_state['redirect'] = $destination;
diff --git a/core/profiles/standard/standard.profile b/core/profiles/standard/standard.profile
index d554c93..209107d 100644
--- a/core/profiles/standard/standard.profile
+++ b/core/profiles/standard/standard.profile
@@ -11,5 +11,5 @@
  */
 function standard_form_install_configure_form_alter(&$form, $form_state) {
   // Pre-populate the site name with the server name.
-  $form['site_information']['site_name']['#default_value'] = $_SERVER['SERVER_NAME'];
+  $form['site_information']['site_name']['#default_value'] = \Drupal::request()->server->get('SERVER_NAME');
 }
