diff -Nur /tmp/ldap//ldap_authentication/LdapAuthenticationConf.class.php ldap//ldap_authentication/LdapAuthenticationConf.class.php
--- /tmp/ldap//ldap_authentication/LdapAuthenticationConf.class.php	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_authentication/LdapAuthenticationConf.class.php	2011-08-07 19:53:51.000000000 +0200
@@ -43,6 +43,8 @@
   public $allowTestPhp = NULL; // code that returns boolean TRUE || FALSE for allowing ldap authentication
   public $excludeIfNoAuthorizations = LDAP_AUTHENTICATION_EXCL_IF_NO_AUTHZ_DEFAULT;
 
+  public $syncPass = NULL;
+
   public $saveable = array(
     'sids',
     'authenticationMode',
@@ -60,6 +62,7 @@
     'seamlessLogin',
     'ldapImplementation',
     'cookieExpire',
+    'syncPass',
   );
 
   /** are any ldap servers that are enabled associated with ldap authentication **/
diff -Nur /tmp/ldap//ldap_authentication/LdapAuthenticationConfAdmin.class.php ldap//ldap_authentication/LdapAuthenticationConfAdmin.class.php
--- /tmp/ldap//ldap_authentication/LdapAuthenticationConfAdmin.class.php	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_authentication/LdapAuthenticationConfAdmin.class.php	2011-08-07 19:54:08.000000000 +0200
@@ -184,6 +184,13 @@
   public $hasError = FALSE;
   public $errorName = NULL;
 
+   /**
+   * 5. Password
+   */
+
+  public $syncPass = NULL;
+
+
   public function clearError() {
     $this->hasError = FALSE;
     $this->errorMsg = NULL;
@@ -413,6 +420,19 @@
       '#options' => $this->ldapImplementationOptions,
     );
 
+    $form['password'] = array(
+      '#type' => 'fieldset',
+      '#title' => t('Password Sychronisation'),
+      '#collapsible' => TRUE,
+      '#collapsed' => FALSE,
+    );
+    $form['password']['syncPass'] = array(
+      '#type' => 'checkbox',
+      '#title' => t('Enable password change'),
+      '#default_value' => $this->syncPass,
+      '#description' => t('Enable in order to allow LDAP password change by users.'),
+    );
+
     $form['submit'] = array(
       '#type' => 'submit',
       '#value' => 'Save',
@@ -477,6 +497,7 @@
     $this->seamlessLogin = ($values['seamlessLogin']) ? (int)$values['seamlessLogin'] : NULL;
     $this->cookieExpire = ($values['cookieExpire']) ? (int)$values['cookieExpire'] : NULL;
     $this->ldapImplementation = ($values['ldapImplementation']) ? (string)$values['ldapImplementation'] : NULL;
+    $this->syncPass = ($values['syncPass']) ? (int)$values['syncPass'] : NULL;
   }
 
   public function drupalFormSubmit($values) {
diff -Nur /tmp/ldap//ldap_authentication/ldap_authentication.inc ldap//ldap_authentication/ldap_authentication.inc
--- /tmp/ldap//ldap_authentication/ldap_authentication.inc	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_authentication/ldap_authentication.inc	2011-08-08 00:07:24.000000000 +0200
@@ -99,14 +99,26 @@
     }
 
     if (!ldap_authentication_show_reset_pwd($form['#user'])) {
-      $form['account']['current_pass']['#disabled'] = TRUE;
+      if($auth_conf->syncPass) {
+        $form['account']['current_pass']['#disabled'] = FALSE;
+      } else {
+        $form['account']['current_pass']['#disabled'] = TRUE;
+      }
       if ($auth_conf->ldapUserHelpLinkUrl) {
         $form['account']['current_pass']['#description'] = l(t($auth_conf->ldapUserHelpLinkText), $auth_conf->ldapUserHelpLinkUrl);
       }
       else {
-        $form['account']['current_pass']['#description'] = t('The password cannot be changed using this website');
+        if($auth_conf->syncPass) {
+          $form['account']['current_pass']['#description'] = t('Enter your current password.');
+        } else {
+          $form['account']['current_pass']['#description'] = t('The password cannot be changed using this website');
+        }
+      }
+      if($auth_conf->syncPass) {
+        $form['account']['pass']['#disabled'] = FALSE;
+      } else {
+        $form['account']['pass']['#disabled'] = TRUE;
       }
-      $form['account']['pass']['#disabled'] = TRUE;
     }
   }
 }
@@ -119,6 +131,7 @@
   * ldap authentication exclusively
   */
 function _ldap_authentication_user_login_authenticate_validate(&$form_state) {
+  watchdog('ldap_authentication', 'validate', array(), WATCHDOG_DEBUG);
 
   $detailed_watchdog_log = variable_get('ldap_help_watchdog_detail', 0);
   $name = $form_state['values']['name'];
diff -Nur /tmp/ldap//ldap_authorization/ldap_authorization.inc ldap//ldap_authorization/ldap_authorization.inc
--- /tmp/ldap//ldap_authorization/ldap_authorization.inc	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_authorization/ldap_authorization.inc	2011-08-07 19:43:50.000000000 +0200
@@ -387,7 +387,7 @@
   $derive_from_entry_authorizations = array();
   if ($consumer_conf->deriveFromEntry) {
     foreach ($consumer_conf->deriveFromEntryEntries as $branch) {
-      $filter = '(' . $consumer_conf->deriveFromEntryAttr . '="' . $user_ldap_entry['dn'] . '")';
+      $filter = '(' . $consumer_conf->deriveFromEntryAttr . '=' . $user_ldap_entry['dn'] . ')';
       $entries = $ldap_server->search($branch, $filter, array('cn'));
       if (empty($entries) || $entries['count'] == 0) {
         $filter = '(' . $consumer_conf->deriveFromEntryAttr . '=' . $user->name . ')';
diff -Nur /tmp/ldap//ldap_authorization/ldap_authorization_drupal_role/LdapAuthorizationConssumerRole.class.php ldap//ldap_authorization/ldap_authorization_drupal_role/LdapAuthorizationConssumerRole.class.php
--- /tmp/ldap//ldap_authorization/ldap_authorization_drupal_role/LdapAuthorizationConssumerRole.class.php	1970-01-01 01:00:00.000000000 +0100
+++ ldap//ldap_authorization/ldap_authorization_drupal_role/LdapAuthorizationConssumerRole.class.php	2011-08-04 18:45:44.000000000 +0200
@@ -0,0 +1,155 @@
+<?php
+// $Id:  $
+
+
+
+/**
+ * @file
+ * abstract class to represent an ldap_authorization consumer
+ * such as drupal_role, og_group, etc.
+ *
+ */
+require_once(drupal_get_path('module', 'ldap_authorization') . '/LdapAuthorizationConsumerAbstract.class.php');
+class LdapAuthorizationConsumerDrupalRole extends LdapAuthorizationConsumerAbstract {
+
+  public $consumerType = 'drupal_role';
+  public $allowSynchBothDirections = FALSE;
+  public $allowConsumerObjectCreation = TRUE;
+  public $onlyApplyToLdapAuthenticatedDefault = TRUE;
+  public $useMappingsAsFilterDefault = TRUE;
+  public $synchOnLogonDefault = TRUE;
+  public $synchManuallyDefault = TRUE;
+  public $revokeLdapProvisionedDefault = TRUE;
+  public $regrantLdapProvisionedDefault = TRUE;
+  public $createContainersDefault = TRUE;
+  public $drupalRolesByName = array();
+
+ /**
+   * Constructor Method
+   *
+   */
+  function __construct($consumer_type = NULL) {
+    $params = ldap_authorization_drupal_role_ldap_authorization_consumer();
+    $this->refreshConsumerIDs();
+    parent::__construct('drupal_role', $params['drupal_role']);
+  }
+
+  public function refreshConsumerIDs() {
+    $this->drupalRolesByName = array_flip(user_roles());
+    $this->_availableConsumerIDs = array_values(user_roles(TRUE));
+  }
+
+  public function availableConsumerIDs($reset = FALSE) {
+    if ($reset || ! is_array($this->_availableConsumerIDs)) {
+      $this->refreshConsumerIDs();
+    }
+    return $this->_availableConsumerIDs;
+  }
+
+  /**
+   * extends createConsumer method of base class
+   *
+   * creates of drupal roles may be mixed case.  drupal doesn't
+   * differentiate, so case is ignored in comparing, but preserved
+   * for the actual created role name saved.
+   *
+   * **/
+
+  public function createConsumers($creates_mixed_case) {
+
+    // 1. determins difference between existing drupal roles and ones that are requested to be created
+    $existing_roles_mixed_case = $this->availableConsumerIDs();
+    $creates_lower_case = array_map('drupal_strtolower', $creates_mixed_case);
+    $existing_roles_lower_case = array_map('drupal_strtolower', $existing_roles_mixed_case);
+    $roles_map_lc_to_mixed_case = array_combine($creates_lower_case, $creates_mixed_case);
+    $roles_to_create =  array_unique(array_diff($creates_lower_case, $existing_roles_lower_case));
+
+    // 2. create each role that is needed
+    foreach ($roles_to_create as $i => $role_name_lowercase) {
+      if (strlen($role_name_lowercase) > 63) {
+        watchdog('ldap_authorization_drupal_role', 'Tried to create drupal role with name of over 63 characters (%group_name).  Please correct your drupal ldap_authorization settings', array('%group_name' => $role_name_lowercase));
+        continue;
+      }
+      $role = new stdClass();
+      $role->name = $roles_map_lc_to_mixed_case[$role_name_lowercase];
+      if (! ($status = user_role_save($role))) {
+        // if role is not created, remove from array to user object doesn't have it stored as granted
+        watchdog('user', 'failed to create drupal role %role in ldap_authorizations module', array('%role' => $role->name));
+      }
+      else {
+        $created[] = $role->name;
+        watchdog('user', 'drupal role %role in ldap_authorizations module', array('%role' => $role->name));
+      }
+    }
+    // 3. return all existing user roles and flush cache of consumer ids.
+    $refreshed_available_consumer_ids = $this->availableConsumerIDs(TRUE);
+    if ($this->detailedWatchdogLog) {
+      $watchdog_tokens = array('%roles_to_create' => join(", ", $roles_to_create));
+      $watchdog_tokens = array('%existing_roles' => join(", ", $existing_roles_mixed_case));
+      $watchdog_tokens = array('%refreshed_available_consumer_ids' => join(", ", $refreshed_available_consumer_ids));
+      watchdog('ldap_authorization',
+        'LdapAuthorizationConsumerDrupalRole.createConsumers()
+        roles to create: %roles_to_create;
+        existing roles: %existing_roles;
+        available roles after createConsumers call: %refreshed_available_consumer_ids;',
+        $watchdog_tokens,
+        WATCHDOG_DEBUG);
+    }
+
+
+    return $refreshed_available_consumer_ids;  // return actual roles that exist, in case of failure
+
+  }
+
+  public function revokeSingleAuthorization(&$user, $role_name, &$user_auth_data) {
+
+    $user_edit = array('roles' => array_diff($user->roles, array($this->drupalRolesByName[$role_name] => $role_name)));
+    $user = user_save($user, $user_edit);
+    $result = ($user && !isset($user->roles[$this->drupalRolesByName[$role_name]]));
+
+    if ($this->detailedWatchdogLog) {
+      watchdog('ldap_authorization', 'LdapAuthorizationConsumerDrupalRole.revokeSingleAuthorization()
+        revoked:  rid=%rid, role_name=%role_name for username=%username, result=%result',
+        array('%rid' => $this->drupalRolesByName[$role_name], '%role_name' => $role_name, '%username' => $user->name,
+          '%result' => $result), WATCHDOG_DEBUG);
+    }
+
+    return $result;
+
+  }
+
+  /**
+   * extends grantSingleAuthorization()
+   */
+
+  public function grantSingleAuthorization(&$user, $role_name, &$user_auth_data) {
+    if (! isset($this->drupalRolesByName[$role_name])) {
+        watchdog('ldap_authorization', 'LdapAuthorizationConsumerDrupalRole.grantSingleAuthorization()
+        failed to grant %username the role %role_name because role does not exist',
+        array('%role_name' => $role_name, '%username' => $user->name),
+        WATCHDOG_ERROR);
+        return FALSE;
+    }
+
+    $user_edit = array('roles' => $user->roles + array($this->drupalRolesByName[$role_name] => $role_name));
+    $user = user_save($user, $user_edit);
+    $result = ($user && isset($user->roles[$this->drupalRolesByName[$role_name]]));
+
+
+    if ($this->detailedWatchdogLog) {
+      watchdog('ldap_authorization', 'LdapAuthorizationConsumerDrupalRole.grantSingleAuthorization()
+        granted: rid=%rid, role_name=%role_name for username=%username, result=%result',
+        array('%rid' => $this->drupalRolesByName[$role_name], '%role_name' => $role_name, '%username' => $user->name,
+          '%result' => $result), WATCHDOG_DEBUG);
+    }
+
+    return $result;
+
+  }
+
+  public function usersAuthorizations(&$user) {
+    return array_values($user->roles);
+  }
+
+
+}
diff -Nur /tmp/ldap//ldap_servers/LdapServer.class.php ldap//ldap_servers/LdapServer.class.php
--- /tmp/ldap//ldap_servers/LdapServer.class.php	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_servers/LdapServer.class.php	2011-08-07 19:43:50.000000000 +0200
@@ -40,6 +40,8 @@
   public $ldapToDrupalUserPhp;
   public $testingDrupalUsername;
   public $detailed_watchdog_log;
+  public $pass_attr;
+  public $hash_pass;
 
 
   public $inDatabase = FALSE;
@@ -61,7 +63,9 @@
     'user_attr'  => 'user_attr',
     'mail_attr'  => 'mail_attr',
     'ldap_to_drupal_user'  => 'ldapToDrupalUserPhp',
-    'testing_drupal_username'  => 'testingDrupalUsername'
+    'testing_drupal_username'  => 'testingDrupalUsername',
+    'pass_attr' => 'pass_attr',
+    'hash_pass' => 'hash_pass'
     );
 
   }
diff -Nur /tmp/ldap//ldap_servers/LdapServerAdmin.class.php ldap//ldap_servers/LdapServerAdmin.class.php
--- /tmp/ldap//ldap_servers/LdapServerAdmin.class.php	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_servers/LdapServerAdmin.class.php	2011-08-07 19:43:50.000000000 +0200
@@ -67,6 +67,8 @@
     $this->mail_attr = trim($values['mail_attr']);
     $this->ldapToDrupalUserPhp = $values['ldap_to_drupal_user'];
     $this->testingDrupalUsername = trim($values['testing_drupal_username']);
+    $this->pass_attr = trim($values['pass_attr']);
+    $this->hash_pass = trim($values['hash_pass']);
 
   }
 
@@ -375,6 +377,23 @@
     '#maxlength' => 255,
     '#description' => t('The attribute that holds the users\' email address. (eg. <code>mail</code>).'),
   );
+  $form['users']['hash_pass'] = array(
+    '#type' => 'radios',
+    '#title' => t('Password hash methode for LDAP. The password will be saved to the password attribute with prefixed hash. (eg. <code>userPassword: {SSHA}fjladsgeinfds13</code>)'),
+    '#default_value' => ($this->hash_pass) ? $this->hash_pass : LDAP_HASH_SSHA,
+    '#options' => array(
+      LDAP_HASH_SSHA => 'SSHA password hash. This is the OpenLDAP default.',
+    ),
+    '#required' => FALSE,
+  );
+  $form['users']['pass_attr'] = array(
+    '#type' => 'textfield',
+    '#title' => t('Password attribute'),
+    '#default_value' => $this->pass_attr,
+    '#size' => 30,
+    '#maxlength' => 255,
+    '#description' => t('The attribute that holds the users\' password. (eg. <code>userPassword</code>).'),
+  );
   $form['users']['ldap_to_drupal_user'] = array(
     '#type' => 'textarea',
     '#title' => t('PHP to transform Drupal login username to LDAP UserName attribute.'),
diff -Nur /tmp/ldap//ldap_servers/ldap_servers.functions.inc ldap//ldap_servers/ldap_servers.functions.inc
--- /tmp/ldap//ldap_servers/ldap_servers.functions.inc	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_servers/ldap_servers.functions.inc	2011-08-08 00:10:15.000000000 +0200
@@ -68,7 +68,7 @@
       $new_pass .= "{$new_password{$i}}\000";
     }
 
-    $status = ldap_mod_replace($ldap_server->connection, $userdn, array('unicodePwd' => $new_pass));
+    $status = ldap_mod_replace($ldap_server->connection, $userdn, array($ldap_server->pass_attr => $new_pass));
     if (!$status) {
       watchdog(
         'ldap_servers',
@@ -128,3 +128,4 @@
   }
   return $result;
 }
+
diff -Nur /tmp/ldap//ldap_servers/ldap_servers.inc ldap//ldap_servers/ldap_servers.inc
--- /tmp/ldap//ldap_servers/ldap_servers.inc	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_servers/ldap_servers.inc	2011-08-07 19:43:50.000000000 +0200
@@ -210,8 +210,24 @@
   'type' => 'int',
   'not null' => TRUE,
   'default' => 0,
+  )
+  ),
+
+  'pass_attr' => array(
+  'schema' => array(
+  'type' => 'varchar',
+  'length' => 255,
+  'not null' => FALSE,
+  )
   ),
+
+  'hash_pass' => array(
+  'schema' => array(
+  'type' => 'int',
+  'not null' => FALSE,
+  'default' => 0,
   )
+  ),
 
   );
 
diff -Nur /tmp/ldap//ldap_servers/ldap_servers.install ldap//ldap_servers/ldap_servers.install
--- /tmp/ldap//ldap_servers/ldap_servers.install	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_servers/ldap_servers.install	2011-08-07 19:43:50.000000000 +0200
@@ -173,6 +173,18 @@
         'not null' => TRUE,
         'default' => 0,
       ),
+
+      'pass_attr' => array(
+        'type' => 'varchar',
+        'length'=> 255,
+        'not null' => FALSE,
+      ),
+      
+      'hash_pass' => array(
+        'type' => 'int',
+        'not null' => FALSE,
+        'default' => 1,
+      ),
     ),
     'primary key' => array('numeric_sid'),
     'unique keys' => array('name' => array('name')),
diff -Nur /tmp/ldap//ldap_servers/ldap_servers.module ldap//ldap_servers/ldap_servers.module
--- /tmp/ldap//ldap_servers/ldap_servers.module	2011-08-07 08:31:31.000000000 +0200
+++ ldap//ldap_servers/ldap_servers.module	2011-08-07 19:47:20.000000000 +0200
@@ -105,6 +105,9 @@
 define('LDAP_CLIENT_LOOP', 0x60);
 define('LDAP_REFERRAL_LIMIT_EXCEEDED', 0x61);
 
+//PasswordHashingForPasswordChange);
+define('LDAP_HASH_SSHA', 1);
+
 function ldap_servers_menu() {
   $menu_offset = 4;
 
