diff --git a/core/modules/locale/locale.module b/core/modules/locale/locale.module
index 2afc147..4231791 100644
--- a/core/modules/locale/locale.module
+++ b/core/modules/locale/locale.module
@@ -214,85 +214,6 @@ function locale_permission() {
 }
 
 /**
- * Form builder callback to display language selection widget.
- *
- * @ingroup forms
- * @see locale_form_alter()
- */
-function locale_language_selector_form($user) {
-  global $language_interface;
-  // Get list of enabled languages only.
-  $languages = language_list(TRUE);
-
-  // If the user is being created, we set the user language to the page language.
-  $user_preferred_language = $user->uid ? user_preferred_language($user) : $language_interface;
-
-  $names = array();
-  foreach ($languages as $langcode => $item) {
-    $names[$langcode] = $item->name;
-  }
-  // Get language negotiation settings.
-  $mode = language_negotiation_method_get_first(LANGUAGE_TYPE_INTERFACE) != LANGUAGE_NEGOTIATION_DEFAULT;
-  $form['locale'] = array(
-    '#type' => 'fieldset',
-    '#title' => t('Language settings'),
-    '#weight' => 1,
-  );
-  $form['locale']['preferred_langcode'] = array(
-    '#type' => (count($names) <= 5 ? 'radios' : 'select'),
-    '#title' => t('Language'),
-    '#default_value' => $user_preferred_language->langcode,
-    '#options' => $names,
-    '#description' => $mode ? t("This account's preferred language for e-mails and site presentation.") : t("This account's preferred language for e-mails."),
-  );
-  // User entities contain both a langcode property (for identifying the
-  // language of the entity data) and a preferred_langcode property (see above).
-  // Rather than provide a UI forcing the user to choose both separately,
-  // assume that the user profile data is in the user's preferred language. This
-  // element provides that synchronization. For use-cases where this
-  // synchronization is not desired, a module can alter or remove this element.
-  $form['locale']['langcode'] = array(
-    '#type' => 'value',
-    '#value_callback' => '_locale_language_selector_langcode_value',
-    // For the synchronization to work, this element must have a larger weight
-    // than the preferred_langcode element. Set a large weight here in case
-    // a module alters the weight of the other element.
-    '#weight' => 100,
-  );
-  return $form;
-}
-
-/**
- * Sets the value of the user register and profile forms' langcode element.
- *
- * @see locale_language_selector_form()
- */
-function _locale_language_selector_langcode_value($element, $input, &$form_state) {
-  $form_state['complete_form']['locale']['preferred_langcode']['#description'] .= ' ' . t("This is also assumed to be the primary language of this account's profile information.");
-  return $form_state['values']['preferred_langcode'];
-}
-
-/**
- * Implements hook_form_alter().
- *
- * Adds language fields to user forms.
- */
-function locale_form_alter(&$form, &$form_state, $form_id) {
-  // Only alter user forms if there is more than one language.
-  if (language_multilingual()) {
-    // Display language selector when either creating a user on the admin
-    // interface or editing a user account.
-    if ($form_id == 'user_register_form' || $form_id == 'user_profile_form') {
-      $selector = locale_language_selector_form($form['#user']);
-      if ($form_id == 'user_register_form') {
-        $selector['locale']['#access'] = user_access('administer users');
-      }
-      $form += $selector;
-    }
-  }
-}
-
-/**
  * Implements hook_form_BASE_FORM_ID_alter().
  */
 function locale_form_node_form_alter(&$form, &$form_state) {
diff --git a/core/modules/openid/openid.module b/core/modules/openid/openid.module
index a3df38f..5e7ccd9 100644
--- a/core/modules/openid/openid.module
+++ b/core/modules/openid/openid.module
@@ -255,21 +255,24 @@ function openid_form_user_register_form_alter(&$form, &$form_state) {
       // preferred langugage is "en-GB", we look for "en-gb" (Drupal's language
       // codes are lower-case) or fall back to "en".
       $parts = preg_split('/[_-]/', strtolower($language));
-      $candidate_languages[] = $parts[0];
+      $candidate_langcodes = array($parts[0]);
       if (count($parts) > 1) {
-        $candidate_languages[] = $parts[0] . '-' . $parts[1];
+        $candidate_langcodes[] = $parts[0] . '-' . $parts[1];
       }
       if (count($parts) > 2) {
-        $candidate_languages[] = $parts[0] . '-' . $parts[2];
-        $candidate_languages[] = $parts[0] . '-' . $parts[1] . '-' . $parts[2];
+        $candidate_langcodes[] = $parts[0] . '-' . $parts[2];
+        $candidate_langcodes[] = $parts[0] . '-' . $parts[1] . '-' . $parts[2];
       }
       $enabled_languages = language_list(TRUE);
       // Iterate over the generated permutations starting with the longest (most
       // specific) strings.
-      foreach (array_reverse($candidate_languages) as $candidate_language) {
-        if (isset($enabled_languages[$candidate_language])) {
-          $form['locale']['preferred_langcode']['#type'] = 'hidden';
-          $form['locale']['preferred_langcode']['#value'] = $candidate_language;
+      foreach (array_reverse($candidate_langcodes) as $candidate_langcode) {
+        if (isset($enabled_languages[$candidate_langcode])) {
+          $form['language']['preferred_langcode']['#type'] = 'hidden';
+          $form['language']['preferred_langcode']['#value'] = $candidate_langcode;
+          // Skip the rest of the foreach to not overwrite the specific
+          // language we found.
+          break;
         }
       }
     }
diff --git a/core/modules/openid/openid.test b/core/modules/openid/openid.test
index 7a4c9cf..6119d24 100644
--- a/core/modules/openid/openid.test
+++ b/core/modules/openid/openid.test
@@ -453,7 +453,7 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
   }
 
   function setUp() {
-    parent::setUp('openid', 'openid_test');
+    parent::setUp('openid', 'openid_test', 'language');
     variable_set('user_register', USER_REGISTER_VISITORS);
   }
 
@@ -469,10 +469,16 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
     variable_set('openid_test_response', array(
       'openid.sreg.nickname' => 'john',
       'openid.sreg.email' => 'john@example.com',
-      'openid.sreg.language' => 'en-GB',
+      'openid.sreg.language' => 'pt-BR',
       'openid.sreg.timezone' => 'Europe/London',
     ));
 
+    // Save Portuguese as an optional language so OpenID can pick that.
+    $language = (object) array(
+      'langcode' => 'pt',
+    );
+    language_save($language);
+
     // Use a User-supplied Identity that is the URL of an XRDS document.
     $identity = url('openid-test/yadis/xrds', array('absolute' => TRUE));
     $this->submitLoginForm($identity);
@@ -484,7 +490,7 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
     $this->assertTrue($user, t('User was registered with right username.'));
     $this->assertEqual($user->mail, 'john@example.com', t('User was registered with right email address.'));
     $this->assertEqual($user->timezone, 'Europe/London', t('User was registered with right timezone.'));
-    $this->assertEqual($user->preferred_langcode, 'en', t('User was registered with right language.'));
+    $this->assertEqual($user->preferred_langcode, 'pt', t('User was registered with right language.'));
     $this->assertFalse($user->data, t('No additional user info was saved.'));
 
     $this->submitLoginForm($identity);
@@ -513,10 +519,16 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
     variable_set('openid_test_response', array(
       'openid.sreg.nickname' => 'john',
       'openid.sreg.email' => 'john@example.com',
-      'openid.sreg.language' => 'en-GB',
+      'openid.sreg.language' => 'pt-BR',
       'openid.sreg.timezone' => 'Europe/London',
     ));
 
+    // Save Portuguese, Brazil as an optional language so OpenID can pick that.
+    $language = (object) array(
+      'langcode' => 'pt-br',
+    );
+    language_save($language);
+
     // Use a User-supplied Identity that is the URL of an XRDS document.
     $identity = url('openid-test/yadis/xrds', array('absolute' => TRUE));
     $this->submitLoginForm($identity);
@@ -526,7 +538,7 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
     $this->assertTrue($user, t('User was registered with right username.'));
     $this->assertEqual($user->mail, 'john@example.com', t('User was registered with right email address.'));
     $this->assertEqual($user->timezone, 'Europe/London', t('User was registered with right timezone.'));
-    $this->assertEqual($user->preferred_langcode, 'en', t('User was registered with right language.'));
+    $this->assertEqual($user->preferred_langcode, 'pt-br', t('User was registered with right language.'));
     $this->assertFalse($user->data, t('No additional user info was saved.'));
 
     $this->drupalLogout();
@@ -571,7 +583,7 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
 
     $user = user_load_by_name('john');
     $this->assertTrue($user, t('User was registered with right username.'));
-    $this->assertFalse($user->preferred_langcode, t('No user language was saved.'));
+    $this->assertEqual($user->preferred_langcode, language_default()->langcode, t('User language is site default.'));
     $this->assertFalse($user->data, t('No additional user info was saved.'));
 
     // Follow the one-time login that was sent in the welcome e-mail.
@@ -611,7 +623,7 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
 
     $user = user_load_by_name('john');
     $this->assertTrue($user, t('User was registered with right username.'));
-    $this->assertFalse($user->preferred_langcode, t('No user language was saved.'));
+    $this->assertEqual($user->preferred_langcode, language_default()->langcode, t('User language is site default.'));
     $this->assertFalse($user->data, t('No additional user info was saved.'));
 
     // Follow the one-time login that was sent in the welcome e-mail.
@@ -644,9 +656,20 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
       'openid.ext123.type.timezone' => 'http://axschema.org/pref/timezone',
       'openid.ext123.value.timezone' => 'Europe/London',
       'openid.ext123.type.language' => 'http://axschema.org/pref/language',
-      'openid.ext123.value.language' => 'en-GB',
+      'openid.ext123.value.language' => 'pt-PT',
     ));
 
+    // Save Portuguese and Portuguese, Portugal as an optional languages so
+    // OpenID can pick the right one.
+    $language = (object) array(
+      'langcode' => 'pt',
+    );
+    language_save($language);
+    $language = (object) array(
+      'langcode' => 'pt-pt',
+    );
+    language_save($language);
+
     // Use a User-supplied Identity that is the URL of an XRDS document.
     $identity = url('openid-test/yadis/xrds', array('absolute' => TRUE));
     $this->submitLoginForm($identity);
@@ -656,7 +679,7 @@ class OpenIDRegistrationTestCase extends OpenIDWebTestCase {
     $this->assertTrue($user, t('User was registered with right username.'));
     $this->assertEqual($user->mail, 'john@example.com', t('User was registered with right email address.'));
     $this->assertEqual($user->timezone, 'Europe/London', t('User was registered with right timezone.'));
-    $this->assertEqual($user->preferred_langcode, 'en', t('User was registered with right language.'));
+    $this->assertEqual($user->preferred_langcode, 'pt-pt', t('User was registered with right language.'));
   }
 }
 
diff --git a/core/modules/user/user.module b/core/modules/user/user.module
index 865f17b..1e3fd92 100644
--- a/core/modules/user/user.module
+++ b/core/modules/user/user.module
@@ -920,7 +920,7 @@ function user_user_view($account) {
  * @see user_validate_mail()
  */
 function user_account_form(&$form, &$form_state) {
-  global $user;
+  global $user, $language_interface;
 
   $account = $form['#user'];
   $register = ($form['#user']->uid > 0 ? FALSE : TRUE);
@@ -1088,6 +1088,72 @@ function user_account_form(&$form, &$form_state) {
     '#description' => t('Your virtual face or picture. Pictures larger than @dimensions pixels will be scaled down.', array('@dimensions' => variable_get('user_picture_dimensions', '85x85'))) . ' ' . filter_xss_admin(variable_get('user_picture_guidelines', '')),
   );
   $form['#validate'][] = 'user_validate_picture';
+
+  // @todo: modify to language after http://drupal.org/node/1468930 lands.
+  // this should be only committed after that.
+  if (module_exists('locale')) {
+    // Get list of enabled languages only.
+    $languages = language_list(TRUE);
+
+    // If the user is being created, we set the user language to the page language.
+    $user_preferred_language = $register ? $language_interface : user_preferred_language($account);
+
+    $names = array();
+    foreach ($languages as $langcode => $item) {
+      $names[$langcode] = $item->name;
+    }
+    // Get language negotiation settings.
+    $mode = language_negotiation_method_get_first(LANGUAGE_TYPE_INTERFACE) != LANGUAGE_NEGOTIATION_DEFAULT;
+    $form['language'] = array(
+      '#type' => 'fieldset',
+      '#title' => t('Language settings'),
+      // Display language selector when either creating a user on the admin
+      // interface or editing a user account.
+      '#access' => !$register || user_access('administer users'),
+    );
+    $form['language']['preferred_langcode'] = array(
+      '#type' => (count($names) <= 5 ? 'radios' : 'select'),
+      '#title' => t('Language'),
+      '#default_value' => $user_preferred_language->langcode,
+      '#options' => $names,
+      '#description' => $mode ? t("This account's preferred language for e-mails and site presentation.") : t("This account's preferred language for e-mails."),
+    );
+  }
+  else {
+    $form['language'] = array(
+      '#type' => 'container',
+    );
+    $form['language']['preferred_langcode'] = array(
+      '#type' => 'value',
+      '#value' => language_default()->langcode,
+    );
+  }
+
+  // User entities contain both a langcode property (for identifying the
+  // language of the entity data) and a preferred_langcode property (see above).
+  // Rather than provide a UI forcing the user to choose both separately,
+  // assume that the user profile data is in the user's preferred language. This
+  // element provides that synchronization. For use-cases where this
+  // synchronization is not desired, a module can alter or remove this element.
+  $form['language']['langcode'] = array(
+    '#type' => 'value',
+    '#value_callback' => '_user_language_selector_langcode_value',
+    // For the synchronization to work, this element must have a larger weight
+    // than the preferred_langcode element. Set a large weight here in case
+    // a module alters the weight of the other element.
+    '#weight' => 100,
+  );
+}
+
+/**
+ * Sets the value of the user register and profile forms' langcode element.
+ */
+function _user_language_selector_langcode_value($element, $input, &$form_state) {
+  // Only add to the description if the form element have a description.
+  if (isset($form_state['complete_form']['language']['preferred_langcode']['#description'])) {
+    $form_state['complete_form']['language']['preferred_langcode']['#description'] .= ' ' . t("This is also assumed to be the primary language of this account's profile information.");
+  }
+  return $form_state['values']['preferred_langcode'];
 }
 
 /**
diff --git a/core/modules/user/user.test b/core/modules/user/user.test
index 06fbc95..f93bd7f 100644
--- a/core/modules/user/user.test
+++ b/core/modules/user/user.test
@@ -166,8 +166,8 @@ class UserRegistrationTestCase extends DrupalWebTestCase {
     $this->assertTrue(($new_user->created > REQUEST_TIME - 20 ), t('Correct creation time.'));
     $this->assertEqual($new_user->status, variable_get('user_register', USER_REGISTER_VISITORS_ADMINISTRATIVE_APPROVAL) == USER_REGISTER_VISITORS ? 1 : 0, t('Correct status field.'));
     $this->assertEqual($new_user->timezone, variable_get('date_default_timezone'), t('Correct time zone field.'));
-    $this->assertEqual($new_user->langcode, '', t('Correct language field.'));
-    $this->assertEqual($new_user->preferred_langcode, '', t('Correct preferred language field.'));
+    $this->assertEqual($new_user->langcode, language_default()->langcode, t('Correct language field.'));
+    $this->assertEqual($new_user->preferred_langcode, language_default()->langcode, t('Correct preferred language field.'));
     $this->assertEqual($new_user->picture, '', t('Correct picture field.'));
     $this->assertEqual($new_user->init, $mail, t('Correct init field.'));
   }
