diff --git a/core/includes/form.inc b/core/includes/form.inc
index 2e7436f..1f8dba4 100644
--- a/core/includes/form.inc
+++ b/core/includes/form.inc
@@ -743,9 +743,13 @@ function drupal_retrieve_form($form_id, &$form_state) {
   // the constructor function itself.
   $args = $form_state['build_info']['args'];
 
-  // We first check to see if there's a function named after the $form_id.
+  // If an explicit form builder callback is defined we just use it, otherwise
+  // we look for a function named after the $form_id.
+  $callback = !empty($form_state['build_info']['callback']) ? $form_state['build_info']['callback'] : $form_id;
+
+  // We first check to see if there is a valid form builder callback defined.
   // If there is, we simply pass the arguments on to it to get the form.
-  if (!function_exists($form_id)) {
+  if (!is_callable($callback)) {
     // In cases where many form_ids need to share a central constructor function,
     // such as the node editing form, modules can implement hook_forms(). It
     // maps one or more form_ids to the correct constructor functions.
@@ -766,14 +770,7 @@ function drupal_retrieve_form($form_id, &$form_state) {
     }
     if (isset($form_definition['callback'])) {
       $callback = $form_definition['callback'];
-      if (empty($form_definition['base_form_ids'])) {
-        $form_definition['base_form_ids'] = array($callback);
-      }
-      // The most specific base form id will be used as the main one.
-      $form_state['build_info']['base_form_id'] = end($form_definition['base_form_ids']);
-      // Store the additional base form ids to allow for more generic or
-      // granular form altering.
-      $form_state['build_info']['base_form_ids'] = $form_definition['base_form_ids'];
+      $form_state['build_info']['base_form_id'] = $callback;
     }
     // In case $form_state['wrapper_callback'] is not defined already, we also
     // allow hook_forms() to define one.
@@ -811,7 +808,7 @@ function drupal_retrieve_form($form_id, &$form_state) {
 
   // If $callback was returned by a hook_forms() implementation, call it.
   // Otherwise, call the function named after the form id.
-  $form = call_user_func_array(isset($callback) ? $callback : $form_id, $args);
+  $form = call_user_func_array($callback, $args);
   $form['#form_id'] = $form_id;
 
   return $form;
@@ -1092,10 +1089,8 @@ function drupal_prepare_form($form_id, &$form, &$form_state) {
   // Invoke hook_form_alter(), hook_form_BASE_FORM_ID_alter(), and
   // hook_form_FORM_ID_alter() implementations.
   $hooks = array('form');
-  if (isset($form_state['build_info']['base_form_ids'])) {
-    foreach ($form_state['build_info']['base_form_ids'] as $base_form_id) {
-      $hooks[] = 'form_' . $base_form_id;
-    }
+  if (isset($form_state['build_info']['base_form_id'])) {
+    $hooks[] = 'form_' . $form_state['build_info']['base_form_id'];
   }
   $hooks[] = 'form_' . $form_id;
   drupal_alter($hooks, $form, $form_state, $form_id);
diff --git a/core/modules/entity/entity.module b/core/modules/entity/entity.module
index 37819e4..b1230c4 100644
--- a/core/modules/entity/entity.module
+++ b/core/modules/entity/entity.module
@@ -5,8 +5,8 @@
  * Entity API for handling entities like nodes or users.
  */
 
-use Drupal\entity\EntityInterface;
 use Drupal\entity\EntityMalformedException;
+use Drupal\entity\EntityInterface;
 
 /**
  * Implements hook_help().
@@ -485,8 +485,7 @@ function entity_get_form_controller($entity_type, $bundle = NULL, $context = 'de
   }
   // If a non-existing context has been specified stop.
   else {
-    // @todo Here we should throw an exception.
-    return FALSE;
+    throw new EntityMalformedException("Missing form controller for '$entity_type' bundle '$bundle' in context '$context'");
   }
 
   return new $class($context);
@@ -523,44 +522,15 @@ function entity_get_form($entity, $context = 'default') {
   if (is_string($entity)) {
     $entity = entity_create($entity, array());
   }
-  $form_id = _entity_form_id($entity, $context);
-  return drupal_get_form($form_id, $entity, $context);
-}
 
-/**
- * Implements hook_forms().
- *
- * Returns the generic 'entity_form' callback and defines the additional
- * ENTITY_TYPE_form base id to allow for both generic and entity-specific form
- * alterations. This we have three levels of granularity: bundle, entity type,
- * all.
- */
-function entity_forms($form_id, $args) {
-  $forms = array();
-
-  if (!empty($args) && $args[0] instanceof EntityInterface) {
-    try {
-      list($entity, $context) = $args;
-      if ($form_id == _entity_form_id($entity, $context)) {
-        $callback = 'entity_form';
-        $forms[$form_id]['callback'] = $callback;
-        $forms[$form_id]['base_form_ids'] = array($callback, $entity->entityType() . '_form');
-      }
-    }
-    catch (EntityMalformedException $e) {
-      // Not an entity form, exit silently.
-    }
-  }
+  $controller = entity_get_form_controller($entity->entityType(), $entity->bundle(), $context);
 
-  return $forms;
-}
+  $form_state['build_info']['callback'] = array($controller, 'build');
+  $form_state['build_info']['base_form_id'] = $entity->entityType() . '_form';
+  $form_state['build_info']['args'] = array($entity, $context);
 
-/**
- * Form builder for any entity form.
- */
-function entity_form($form, &$form_state, EntityInterface $entity, $context) {
-  $controller = entity_get_form_controller($entity->entityType(), $entity->bundle(), $context);
-  return $controller->build($form, $form_state, $entity);
+  $form_id = _entity_form_id($entity, $context);
+  return drupal_build_form($form_id, $form_state);
 }
 
 /**
