diff --git a/core/config/schema/core.data_types.schema.yml b/core/config/schema/core.data_types.schema.yml
index 41332e3..c8c69af 100644
--- a/core/config/schema/core.data_types.schema.yml
+++ b/core/config/schema/core.data_types.schema.yml
@@ -566,7 +566,7 @@ field.field_settings.entity_reference:
       type: string
       label: 'Reference method'
     handler_settings:
-      type: entity_reference.[%parent.handler].handler_settings
+      type: entity_reference.handler_settings.[plugin_id]
       label: 'Reference method settings'
 
 field.value.entity_reference:
diff --git a/core/lib/Drupal/Core/Entity/Plugin/EntityReferenceSelection/SelectionBase.php b/core/lib/Drupal/Core/Entity/Plugin/EntityReferenceSelection/SelectionBase.php
index 07ec8cd..614f4af 100644
--- a/core/lib/Drupal/Core/Entity/Plugin/EntityReferenceSelection/SelectionBase.php
+++ b/core/lib/Drupal/Core/Entity/Plugin/EntityReferenceSelection/SelectionBase.php
@@ -7,6 +7,8 @@
 
 namespace Drupal\Core\Entity\Plugin\EntityReferenceSelection;
 
+use Drupal\Component\Plugin\ConfigurablePluginInterface;
+use Drupal\Component\Utility\NestedArray;
 use Drupal\Component\Utility\String;
 use Drupal\Core\Database\Query\AlterableInterface;
 use Drupal\Core\Database\Query\SelectInterface;
@@ -39,7 +41,7 @@
  *   deriver = "Drupal\Core\Entity\Plugin\Derivative\SelectionBase"
  * )
  */
-class SelectionBase extends PluginBase implements SelectionInterface, ContainerFactoryPluginInterface {
+class SelectionBase extends PluginBase implements SelectionInterface, ContainerFactoryPluginInterface, ConfigurablePluginInterface {
 
   /**
    * The entity manager.
@@ -80,7 +82,7 @@ class SelectionBase extends PluginBase implements SelectionInterface, ContainerF
    */
   public function __construct(array $configuration, $plugin_id, $plugin_definition, EntityManagerInterface $entity_manager, ModuleHandlerInterface $module_handler, AccountInterface $current_user) {
     parent::__construct($configuration, $plugin_id, $plugin_definition);
-
+    $this->setConfiguration($configuration);
     $this->entityManager = $entity_manager;
     $this->moduleHandler = $module_handler;
     $this->currentUser = $current_user;
@@ -109,15 +111,6 @@ public function buildConfigurationForm(array $form, FormStateInterface $form_sta
     $entity_type = $this->entityManager->getDefinition($entity_type_id);
     $bundles = $this->entityManager->getBundleInfo($entity_type_id);
 
-    // Merge-in default values.
-    $selection_handler_settings += array(
-      'target_bundles' => array(),
-      'sort' => array(
-        'field' => '_none',
-      ),
-      'auto_create' => FALSE,
-    );
-
     if ($entity_type->hasKey('bundle')) {
       $bundle_options = array();
       foreach ($bundles as $bundle_name => $bundle_info) {
@@ -388,4 +381,47 @@ protected function reAlterQuery(AlterableInterface $query, $tag, $base_table) {
     $query->alterMetaData = $old_metadata;
   }
 
+  /**
+   * {@inheritdoc}
+   */
+  public function setConfiguration(array $configuration) {
+    $this->configuration = NestedArray::mergeDeep(
+      $this->defaultConfiguration(),
+      $configuration
+    );
+  }
+  /**
+   * Returns default configuration for this plugin.
+   *
+   * @return array
+   *   An associative array with the default configuration.
+   */
+  public function defaultConfiguration() {
+    return [
+      'handler_settings' => [
+        'plugin_id' => $this->getPluginId(),
+        'target_bundles' => [],
+        'sort' => [
+          'field' => '_none',
+        ],
+        'auto_create' => FALSE,
+      ]
+    ];
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getConfiguration() {
+    return $this->configuration;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function calculateDependencies() {
+    // @todo add dependency on target bundles.
+    return [];
+  }
+
 }
diff --git a/core/lib/Drupal/Core/Field/BaseFieldDefinition.php b/core/lib/Drupal/Core/Field/BaseFieldDefinition.php
index 1d2bf6d..78c41f2 100644
--- a/core/lib/Drupal/Core/Field/BaseFieldDefinition.php
+++ b/core/lib/Drupal/Core/Field/BaseFieldDefinition.php
@@ -63,7 +63,7 @@ public static function create($type) {
     // settings for the field type.
     // @todo Cleanup in https://drupal.org/node/2116341.
     $field_type_manager = \Drupal::service('plugin.manager.field.field_type');
-    $default_settings = $field_type_manager->getDefaultStorageSettings($type) + $field_type_manager->getDefaultFieldSettings($type);
+    $default_settings = $field_type_manager->getDefaultStorageSettings($type) + $field_type_manager->getDefaultFieldSettings($type, $field_definition);
     $field_definition->itemDefinition->setSettings($default_settings);
     return $field_definition;
   }
diff --git a/core/lib/Drupal/Core/Field/Entity/BaseFieldOverride.php b/core/lib/Drupal/Core/Field/Entity/BaseFieldOverride.php
index b6b2a3c..7f4a18d 100644
--- a/core/lib/Drupal/Core/Field/Entity/BaseFieldOverride.php
+++ b/core/lib/Drupal/Core/Field/Entity/BaseFieldOverride.php
@@ -158,7 +158,7 @@ public function preSave(EntityStorageInterface $storage) {
     // that a complete field definition is passed to the various hooks and
     // written to config.
     $field_type_manager = \Drupal::service('plugin.manager.field.field_type');
-    $default_settings = $field_type_manager->getDefaultFieldSettings($this->getType());
+    $default_settings = $field_type_manager->getDefaultFieldSettings($this->getType(), $this);
     $this->settings = array_intersect_key($this->settings, $default_settings) + $default_settings;
 
     // Call the parent's presave method to perform validate and calculate
diff --git a/core/lib/Drupal/Core/Field/FieldTypePluginManager.php b/core/lib/Drupal/Core/Field/FieldTypePluginManager.php
index e355985..1e5283e 100644
--- a/core/lib/Drupal/Core/Field/FieldTypePluginManager.php
+++ b/core/lib/Drupal/Core/Field/FieldTypePluginManager.php
@@ -61,11 +61,11 @@ public function getDefaultStorageSettings($type) {
   /**
    * {@inheritdoc}
    */
-  public function getDefaultFieldSettings($type) {
+  public function getDefaultFieldSettings($type, FieldDefinitionInterface $field = NULL) {
     $plugin_definition = $this->getDefinition($type, FALSE);
     if (!empty($plugin_definition['class'])) {
       $plugin_class = DefaultFactory::getPluginClass($type, $plugin_definition);
-      return $plugin_class::defaultFieldSettings();
+      return $plugin_class::defaultFieldSettings($field);
     }
     return array();
   }
diff --git a/core/modules/entity_reference/config/schema/entity_reference.schema.yml b/core/modules/entity_reference/config/schema/entity_reference.schema.yml
index ec291fa..9648db9 100644
--- a/core/modules/entity_reference/config/schema/entity_reference.schema.yml
+++ b/core/modules/entity_reference/config/schema/entity_reference.schema.yml
@@ -1,9 +1,12 @@
 # Schema for the configuration files of the Entity Reference module.
 
-entity_reference.default.handler_settings:
+entity_reference.handler_settings:
   type: mapping
   label: 'View handler settings'
   mapping:
+    plugin_id:
+      type: string
+      label: 'Entity reference selection plugin ID'
     target_bundles:
       type: sequence
       label: 'types'
@@ -20,19 +23,9 @@ entity_reference.default.handler_settings:
         direction:
           type: string
           label: 'Sort direction'
-    filter:
-      type: mapping
-      label: 'Filter settings'
-      mapping:
-        type:
-          type: string
-          label: 'Filter by'
-        role:
-          type: sequence
-          label: 'Restrict to the selected roles'
-          sequence:
-            - type: string
-              label: 'Role'
     auto_create:
       type: boolean
       label: 'Create referenced entities if they don''t already exist'
+
+entity_reference.handler_settings.*:
+  type: entity_reference.handler_settings
diff --git a/core/modules/entity_reference/src/ConfigurableEntityReferenceItem.php b/core/modules/entity_reference/src/ConfigurableEntityReferenceItem.php
index 5f0f75d..fd106cd 100644
--- a/core/modules/entity_reference/src/ConfigurableEntityReferenceItem.php
+++ b/core/modules/entity_reference/src/ConfigurableEntityReferenceItem.php
@@ -7,8 +7,10 @@
 
 namespace Drupal\entity_reference;
 
+use Drupal\Component\Utility\NestedArray;
 use Drupal\Component\Utility\String;
-use Drupal\Core\Field\FieldStorageDefinitionInterface;
+use Drupal\Core\Field\BaseFieldDefinition;
+use Drupal\Core\Field\FieldDefinitionInterface;
 use Drupal\Core\Field\Plugin\Field\FieldType\EntityReferenceItem;
 use Drupal\Core\Form\FormStateInterface;
 use Drupal\Core\Form\OptGroup;
@@ -45,10 +47,25 @@ public static function defaultStorageSettings() {
   /**
    * {@inheritdoc}
    */
-  public static function defaultFieldSettings() {
-    return array(
-      'handler_settings' => array(),
-    ) + parent::defaultFieldSettings();
+  public static function defaultFieldSettings(FieldDefinitionInterface $field = NULL) {
+    $defaults = ['handler_settings' => []];
+    $defaults = NestedArray::mergeDeep($defaults, parent::defaultFieldSettings(), $field->getSettings());
+    if ($field instanceof BaseFieldDefinition) {
+      $field->setSettings($defaults);
+    }
+    else {
+      $field->settings = $defaults;
+    }
+    // Get the default settings from the entity reference selection plugin if
+    // possible.
+    if ($field->getFieldStorageDefinition()->getSetting('target_type')) {
+      $handler = \Drupal::service('plugin.manager.entity_reference_selection')->getSelectionHandler($field);
+      $defaults = NestedArray::mergeDeep($defaults, $handler->defaultConfiguration());
+    }
+    // The target type is handled by the 'target_type' property in the field
+    // storage settings.
+    unset($defaults['target_type']);
+    return $defaults;
   }
 
   /**
@@ -194,7 +211,10 @@ public function fieldSettingsForm(array $form, FormStateInterface $form_state) {
 
     $handler = \Drupal::service('plugin.manager.entity_reference_selection')->getSelectionHandler($field);
     $form['handler']['handler_settings'] += $handler->buildConfigurationForm(array(), $form_state);
-
+    $form['handler']['handler_settings']['plugin_id'] = array(
+      '#type' => 'value',
+      '#value' => $handler->getPluginId(),
+    );
     return $form;
   }
 
diff --git a/core/modules/field/src/Entity/FieldConfig.php b/core/modules/field/src/Entity/FieldConfig.php
index 802bc1b..e6c5df1 100644
--- a/core/modules/field/src/Entity/FieldConfig.php
+++ b/core/modules/field/src/Entity/FieldConfig.php
@@ -7,6 +7,7 @@
 
 namespace Drupal\field\Entity;
 
+use Drupal\Component\Utility\NestedArray;
 use Drupal\Component\Utility\String;
 use Drupal\Core\Entity\EntityStorageInterface;
 use Drupal\Core\Field\FieldConfigBase;
@@ -141,8 +142,8 @@ public function preSave(EntityStorageInterface $storage) {
     // Filter out unknown settings and make sure all settings are present, so
     // that a complete field definition is passed to the various hooks and
     // written to config.
-    $default_settings = $field_type_manager->getDefaultFieldSettings($storage_definition->getType());
-    $this->settings = array_intersect_key($this->settings, $default_settings) + $default_settings;
+    $default_settings = $field_type_manager->getDefaultFieldSettings($storage_definition->getType(), $this);
+    $this->settings = NestedArray::mergeDeep($default_settings, array_intersect_key($this->settings, $default_settings));
 
     if ($this->isNew()) {
       // Notify the entity storage.
diff --git a/core/modules/field/src/Tests/FieldCrudTest.php b/core/modules/field/src/Tests/FieldCrudTest.php
index 33ace63..4dbf87a 100644
--- a/core/modules/field/src/Tests/FieldCrudTest.php
+++ b/core/modules/field/src/Tests/FieldCrudTest.php
@@ -87,7 +87,7 @@ function testCreateField() {
     $this->assertIdentical($config['description'], '', 'Description defaults to empty string.');
 
     // Check that default settings are set.
-    $this->assertEqual($config['settings'], $field_type_manager->getDefaultFieldSettings($this->fieldStorageDefinition['type']) , 'Default field settings have been written.');
+    $this->assertEqual($config['settings'], $field_type_manager->getDefaultFieldSettings($this->fieldStorageDefinition['type'], $field) , 'Default field settings have been written.');
 
     // Check that the denormalized 'field_type' was properly written.
     $this->assertEqual($config['field_type'], $this->fieldStorageDefinition['type']);
diff --git a/core/modules/user/config/schema/user.schema.yml b/core/modules/user/config/schema/user.schema.yml
index 772deea..279521c 100644
--- a/core/modules/user/config/schema/user.schema.yml
+++ b/core/modules/user/config/schema/user.schema.yml
@@ -174,3 +174,20 @@ condition.plugin.user_role:
       type: sequence
       sequence:
         - type: string
+
+entity_reference.handler_settings.default:user:
+  type: entity_reference.handler_settings
+  mapping:
+    filter:
+      type: mapping
+      label: 'Filter settings'
+      mapping:
+        type:
+          type: string
+          label: 'Filter by'
+        role:
+          type: sequence
+          label: 'Restrict to the selected roles'
+          sequence:
+            - type: string
+              label: 'Role'
diff --git a/core/modules/user/src/Plugin/EntityReferenceSelection/UserSelection.php b/core/modules/user/src/Plugin/EntityReferenceSelection/UserSelection.php
index 8d2e701..e7dab16 100644
--- a/core/modules/user/src/Plugin/EntityReferenceSelection/UserSelection.php
+++ b/core/modules/user/src/Plugin/EntityReferenceSelection/UserSelection.php
@@ -189,4 +189,12 @@ public function entityQueryAlter(SelectInterface $query) {
     }
   }
 
+  /**
+   * {@inheritdoc}
+   */
+  public function calculateDependencies() {
+    // @todo add dependency on roles.
+    return parent::calculateDependencies();
+  }
+
 }
diff --git a/core/modules/views/config/schema/views.entity_reference.schema.yml b/core/modules/views/config/schema/views.entity_reference.schema.yml
index 3067041..51704a1 100644
--- a/core/modules/views/config/schema/views.entity_reference.schema.yml
+++ b/core/modules/views/config/schema/views.entity_reference.schema.yml
@@ -1,9 +1,12 @@
 # Schema for the views entity reference selection plugins.
 
-entity_reference.views.handler_settings:
+entity_reference.handler_settings.views:
   type: mapping
   label: 'View handler settings'
   mapping:
+    plugin_id:
+      type: string
+      label: 'Entity reference selection plugin ID'
     view:
       type: mapping
       label: 'View used to select the entities'
diff --git a/core/modules/views/src/Plugin/EntityReferenceSelection/ViewsSelection.php b/core/modules/views/src/Plugin/EntityReferenceSelection/ViewsSelection.php
index 4c0d889..7c4036d 100644
--- a/core/modules/views/src/Plugin/EntityReferenceSelection/ViewsSelection.php
+++ b/core/modules/views/src/Plugin/EntityReferenceSelection/ViewsSelection.php
@@ -7,6 +7,8 @@
 
 namespace Drupal\views\Plugin\EntityReferenceSelection;
 
+use Drupal\Component\Plugin\ConfigurablePluginInterface;
+use Drupal\Component\Utility\NestedArray;
 use Drupal\Core\Database\Query\SelectInterface;
 use Drupal\Core\Entity\EntityManagerInterface;
 use Drupal\Core\Form\FormStateInterface;
@@ -27,7 +29,7 @@
  *   weight = 0
  * )
  */
-class ViewsSelection extends PluginBase implements SelectionInterface, ContainerFactoryPluginInterface {
+class ViewsSelection extends PluginBase implements SelectionInterface, ContainerFactoryPluginInterface, ConfigurablePluginInterface {
 
   /**
    * The entity manager.
@@ -57,7 +59,7 @@ class ViewsSelection extends PluginBase implements SelectionInterface, Container
    */
   public function __construct(array $configuration, $plugin_id, $plugin_definition, EntityManagerInterface $entity_manager) {
     parent::__construct($configuration, $plugin_id, $plugin_definition);
-
+    $this->setConfiguration($configuration);
     $this->entityManager = $entity_manager;
   }
 
@@ -269,4 +271,41 @@ public function settingsFormValidate($element, FormStateInterface $form_state, $
     $form_state->setValueForElement($element, $value);
   }
 
+  /**
+   * {@inheritdoc}
+   */
+  public function setConfiguration(array $configuration) {
+    $this->configuration = NestedArray::mergeDeep(
+      $this->defaultConfiguration(),
+      $configuration
+    );
+  }
+  /**
+   * Returns default configuration for this plugin.
+   *
+   * @return array
+   *   An associative array with the default configuration.
+   */
+  public function defaultConfiguration() {
+    return [
+      'handler_settings' => [
+        'plugin_id' => $this->getPluginId(),
+      ]
+    ];
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function getConfiguration() {
+    return $this->configuration;
+  }
+
+  /**
+   * {@inheritdoc}
+   */
+  public function calculateDependencies() {
+    return [];
+  }
+
 }
