original_string: function ldap_get_ad_pwdexpire($pwdlastset, $ldapconn, $user_dn){
          global $CFG;
  
          if (!function_exists('bcsub')) {
              error_log($this->errorlogtag.get_string ('needbcmath', 'auth_ldap'));
              return 0;
          }
  
          // If UF_DONT_EXPIRE_PASSWD flag is set in user's
          // userAccountControl attribute, the password doesn't expire.
          $sr = ldap_read($ldapconn, $user_dn, '(objectClass=*)',
                          array('userAccountControl'));
          if (!$sr) {
              error_log($this->errorlogtag.get_string ('useracctctrlerror', 'auth_ldap', $user_dn));
              // Don't expire password, as we are not sure if it has to be
              // expired or not.
              return 0;
          }
  
          $entry = ldap_get_entries_moodle($ldapconn, $sr);
          $info = $entry[0];
          $useraccountcontrol = $info['useraccountcontrol'][0];
          if ($useraccountcontrol & UF_DONT_EXPIRE_PASSWD) {
              // Password doesn't expire.
              return 0;
          }
  
          // If pwdLastSet is zero, the user must change his/her password now
          // (unless UF_DONT_EXPIRE_PASSWD flag is set, but we already
          // tested this above)
          if ($pwdlastset === '0') {
              // Password has expired
              return -1;
          }
  
          // ----------------------------------------------------------------
          // Password expiration time in Active Directory is the composition of
          // two values:
          //
          //   - User's pwdLastSet attribute, that stores the last time
          //     the password was changed.
          //
          //   - Domain's maxPwdAge attribute, that sets how long
          //     passwords last in this domain.
          //
          // We already have the first value (passed in as a parameter). We
          // need to get the second one. As we don't know the domain DN, we
          // have to query rootDSE's defaultNamingContext attribute to get
          // it. Then we have to query that DN's maxPwdAge attribute to get
          // the real value.
          //
          // Once we have both values, we just need to combine them. But MS
          // chose to use a different base and unit for time measurements.
          // So we need to convert the values to Unix timestamps (see
          // details below).
          // ----------------------------------------------------------------
  
          $sr = ldap_read($ldapconn, ROOTDSE, '(objectClass=*)',
                          array('defaultNamingContext'));
          if (!$sr) {
              error_log($this->errorlogtag.get_string ('rootdseerror', 'auth_ldap'));
              return 0;
          }
  
          $entry = ldap_get_entries_moodle($ldapconn, $sr);
          $info = $entry[0];
          $domaindn = $info['defaultnamingcontext'][0];
  
          $sr = ldap_read ($ldapconn, $domaindn, '(objectClass=*)',
                           array('maxPwdAge'));
          $entry = ldap_get_entries_moodle($ldapconn, $sr);
          $info = $entry[0];
          $maxpwdage = $info['maxpwdage'][0];
          if ($sr = ldap_read($ldapconn, $user_dn, '(objectClass=*)', array('msDS-ResultantPSO'))) {
              if ($entry = ldap_get_entries_moodle($ldapconn, $sr)) {
                  $info = $entry[0];
                  $userpso = $info['msds-resultantpso'][0];
  
                  // If a PSO exists, FGPP is being utilized.
                  // Grab the new maxpwdage from the msDS-MaximumPasswordAge attribute of the PSO.
                  if (!empty($userpso)) {
                      $sr = ldap_read($ldapconn, $userpso, '(objectClass=*)', array('msDS-MaximumPasswordAge'));
                      if ($entry = ldap_get_entries_moodle($ldapconn, $sr)) {
                          $info = $entry[0];
                          // Default value of msds-maximumpasswordage is 42 and is always set.
                          $maxpwdage = $info['msds-maximumpasswordage'][0];
                      }
                  }
              }
          }
          // ----------------------------------------------------------------
          // MSDN says that "pwdLastSet contains the number of 100 nanosecond
          // intervals since January 1, 1601 (UTC), stored in a 64 bit integer".
          //
          // According to Perl's Date::Manip, the number of seconds between
          // this date and Unix epoch is 11644473600. So we have to
          // substract this value to calculate a Unix time, once we have
          // scaled pwdLastSet to seconds. This is the script used to
          // calculate the value shown above:
          //
          //    #!/usr/bin/perl -w
          //
          //    use Date::Manip;
          //
          //    $date1 = ParseDate ("160101010000 UTC");
          //    $date2 = ParseDate ("197001010000 UTC");
          //    $delta = DateCalc($date1, $date2, \$err);
          //    $secs = Delta_Format($delta, 0, "%st");
          //    print "$secs \n";
          //
          // MSDN also says that "maxPwdAge is stored as a large integer that
          // represents the number of 100 nanosecond intervals from the time
          // the password was set before the password expires." We also need
          // to scale this to seconds. Bear in mind that this value is stored
          // as a _negative_ quantity (at least in my AD domain).
          //
          // As a last remark, if the low 32 bits of maxPwdAge are equal to 0,
          // the maximum password age in the domain is set to 0, which means
          // passwords do not expire (see
          // http://msdn2.microsoft.com/en-us/library/ms974598.aspx)
          //
          // As the quantities involved are too big for PHP integers, we
          // need to use BCMath functions to work with arbitrary precision
          // numbers.
          // ----------------------------------------------------------------
  
          // If the low order 32 bits are 0, then passwords do not expire in
          // the domain. Just do '$maxpwdage mod 2^32' and check the result
          // (2^32 = 4294967296)
          if (bcmod ($maxpwdage, 4294967296) === '0') {
              return 0;
          }
  
          // Add up pwdLastSet and maxPwdAge to get password expiration
          // time, in MS time units. Remember maxPwdAge is stored as a
          // _negative_ quantity, so we need to substract it in fact.
          $pwdexpire = bcsub ($pwdlastset, $maxpwdage);
  
          // Scale the result to convert it to Unix time units and return
          // that value.
          return bcsub( bcdiv($pwdexpire, '10000000'), '11644473600');
      }
code: function ldap_get_ad_pwdexpire($pwdlastset, $ldapconn, $user_dn){
          global $CFG;
  
          if (!function_exists('bcsub')) {
              error_log($this->errorlogtag.get_string ('needbcmath', 'auth_ldap'));
              return 0;
          }
  
          // If UF_DONT_EXPIRE_PASSWD flag is set in user's
          // userAccountControl attribute, the password doesn't expire.
          $sr = ldap_read($ldapconn, $user_dn, '(objectClass=*)',
                          array('userAccountControl'));
          if (!$sr) {
              error_log($this->errorlogtag.get_string ('useracctctrlerror', 'auth_ldap', $user_dn));
              // Don't expire password, as we are not sure if it has to be
              // expired or not.
              return 0;
          }
  
          $entry = ldap_get_entries_moodle($ldapconn, $sr);
          $info = $entry[0];
          $useraccountcontrol = $info['useraccountcontrol'][0];
          if ($useraccountcontrol & UF_DONT_EXPIRE_PASSWD) {
              // Password doesn't expire.
              return 0;
          }
  
          // If pwdLastSet is zero, the user must change his/her password now
          // (unless UF_DONT_EXPIRE_PASSWD flag is set, but we already
          // tested this above)
          if ($pwdlastset === '0') {
              // Password has expired
              return -1;
          }
  
          // ----------------------------------------------------------------
          // Password expiration time in Active Directory is the composition of
          // two values:
          //
          //   - User's pwdLastSet attribute, that stores the last time
          //     the password was changed.
          //
          //   - Domain's maxPwdAge attribute, that sets how long
          //     passwords last in this domain.
          //
          // We already have the first value (passed in as a parameter). We
          // need to get the second one. As we don't know the domain DN, we
          // have to query rootDSE's defaultNamingContext attribute to get
          // it. Then we have to query that DN's maxPwdAge attribute to get
          // the real value.
          //
          // Once we have both values, we just need to combine them. But MS
          // chose to use a different base and unit for time measurements.
          // So we need to convert the values to Unix timestamps (see
          // details below).
          // ----------------------------------------------------------------
  
          $sr = ldap_read($ldapconn, ROOTDSE, '(objectClass=*)',
                          array('defaultNamingContext'));
          if (!$sr) {
              error_log($this->errorlogtag.get_string ('rootdseerror', 'auth_ldap'));
              return 0;
          }
  
          $entry = ldap_get_entries_moodle($ldapconn, $sr);
          $info = $entry[0];
          $domaindn = $info['defaultnamingcontext'][0];
  
          $sr = ldap_read ($ldapconn, $domaindn, '(objectClass=*)',
                           array('maxPwdAge'));
          $entry = ldap_get_entries_moodle($ldapconn, $sr);
          $info = $entry[0];
          $maxpwdage = $info['maxpwdage'][0];
          if ($sr = ldap_read($ldapconn, $user_dn, '(objectClass=*)', array('msDS-ResultantPSO'))) {
              if ($entry = ldap_get_entries_moodle($ldapconn, $sr)) {
                  $info = $entry[0];
                  $userpso = $info['msds-resultantpso'][0];
  
                  // If a PSO exists, FGPP is being utilized.
                  // Grab the new maxpwdage from the msDS-MaximumPasswordAge attribute of the PSO.
                  if (!empty($userpso)) {
                      $sr = ldap_read($ldapconn, $userpso, '(objectClass=*)', array('msDS-MaximumPasswordAge'));
                      if ($entry = ldap_get_entries_moodle($ldapconn, $sr)) {
                          $info = $entry[0];
                          // Default value of msds-maximumpasswordage is 42 and is always set.
                          $maxpwdage = $info['msds-maximumpasswordage'][0];
                      }
                  }
              }
          }
          // ----------------------------------------------------------------
          // MSDN says that "pwdLastSet contains the number of 100 nanosecond
          // intervals since January 1, 1601 (UTC), stored in a 64 bit integer".
          //
          // According to Perl's Date::Manip, the number of seconds between
          // this date and Unix epoch is 11644473600. So we have to
          // substract this value to calculate a Unix time, once we have
          // scaled pwdLastSet to seconds. This is the script used to
          // calculate the value shown above:
          //
          //    #!/usr/bin/perl -w
          //
          //    use Date::Manip;
          //
          //    $date1 = ParseDate ("160101010000 UTC");
          //    $date2 = ParseDate ("197001010000 UTC");
          //    $delta = DateCalc($date1, $date2, \$err);
          //    $secs = Delta_Format($delta, 0, "%st");
          //    print "$secs \n";
          //
          // MSDN also says that "maxPwdAge is stored as a large integer that
          // represents the number of 100 nanosecond intervals from the time
          // the password was set before the password expires." We also need
          // to scale this to seconds. Bear in mind that this value is stored
          // as a _negative_ quantity (at least in my AD domain).
          //
          // As a last remark, if the low 32 bits of maxPwdAge are equal to 0,
          // the maximum password age in the domain is set to 0, which means
          // passwords do not expire (see
          // http://msdn2.microsoft.com/en-us/library/ms974598.aspx)
          //
          // As the quantities involved are too big for PHP integers, we
          // need to use BCMath functions to work with arbitrary precision
          // numbers.
          // ----------------------------------------------------------------
  
          // If the low order 32 bits are 0, then passwords do not expire in
          // the domain. Just do '$maxpwdage mod 2^32' and check the result
          // (2^32 = 4294967296)
          if (bcmod ($maxpwdage, 4294967296) === '0') {
              return 0;
          }
  
          // Add up pwdLastSet and maxPwdAge to get password expiration
          // time, in MS time units. Remember maxPwdAge is stored as a
          // _negative_ quantity, so we need to substract it in fact.
          $pwdexpire = bcsub ($pwdlastset, $maxpwdage);
  
          // Scale the result to convert it to Unix time units and return
          // that value.
          return bcsub( bcdiv($pwdexpire, '10000000'), '11644473600');
      }
code_tokens: function ldap_get_ad_pwdexpire ( $ pwdlastset , $ ldapconn , $ user_dn ) { global $ CFG ; if ( ! function_exists ( 'bcsub' ) ) { error_log ( $ this -> errorlogtag . get_string ( 'needbcmath' , 'auth_ldap' ) ) ; return 0 ; } // If UF_DONT_EXPIRE_PASSWD flag is set in user's // userAccountControl attribute, the password doesn't expire. $ sr = ldap_read ( $ ldapconn , $ user_dn , '(objectClass=*)' , array ( 'userAccountControl' ) ) ; if ( ! $ sr ) { error_log ( $ this -> errorlogtag . get_string ( 'useracctctrlerror' , 'auth_ldap' , $ user_dn ) ) ; // Don't expire password, as we are not sure if it has to be // expired or not. return 0 ; } $ entry = ldap_get_entries_moodle ( $ ldapconn , $ sr ) ; $ info = $ entry [ 0 ] ; $ useraccountcontrol = $ info [ 'useraccountcontrol' ] [ 0 ] ; if ( $ useraccountcontrol & UF_DONT_EXPIRE_PASSWD ) { // Password doesn't expire. return 0 ; } // If pwdLastSet is zero, the user must change his/her password now // (unless UF_DONT_EXPIRE_PASSWD flag is set, but we already // tested this above) if ( $ pwdlastset === '0' ) { // Password has expired return - 1 ; } // ---------------------------------------------------------------- // Password expiration time in Active Directory is the composition of // two values: // //   - User's pwdLastSet attribute, that stores the last time //     the password was changed. // //   - Domain's maxPwdAge attribute, that sets how long //     passwords last in this domain. // // We already have the first value (passed in as a parameter). We // need to get the second one. As we don't know the domain DN, we // have to query rootDSE's defaultNamingContext attribute to get // it. Then we have to query that DN's maxPwdAge attribute to get // the real value. // // Once we have both values, we just need to combine them. But MS // chose to use a different base and unit for time measurements. // So we need to convert the values to Unix timestamps (see // details below). // ---------------------------------------------------------------- $ sr = ldap_read ( $ ldapconn , ROOTDSE , '(objectClass=*)' , array ( 'defaultNamingContext' ) ) ; if ( ! $ sr ) { error_log ( $ this -> errorlogtag . get_string ( 'rootdseerror' , 'auth_ldap' ) ) ; return 0 ; } $ entry = ldap_get_entries_moodle ( $ ldapconn , $ sr ) ; $ info = $ entry [ 0 ] ; $ domaindn = $ info [ 'defaultnamingcontext' ] [ 0 ] ; $ sr = ldap_read ( $ ldapconn , $ domaindn , '(objectClass=*)' , array ( 'maxPwdAge' ) ) ; $ entry = ldap_get_entries_moodle ( $ ldapconn , $ sr ) ; $ info = $ entry [ 0 ] ; $ maxpwdage = $ info [ 'maxpwdage' ] [ 0 ] ; if ( $ sr = ldap_read ( $ ldapconn , $ user_dn , '(objectClass=*)' , array ( 'msDS-ResultantPSO' ) ) ) { if ( $ entry = ldap_get_entries_moodle ( $ ldapconn , $ sr ) ) { $ info = $ entry [ 0 ] ; $ userpso = $ info [ 'msds-resultantpso' ] [ 0 ] ; // If a PSO exists, FGPP is being utilized. // Grab the new maxpwdage from the msDS-MaximumPasswordAge attribute of the PSO. if ( ! empty ( $ userpso ) ) { $ sr = ldap_read ( $ ldapconn , $ userpso , '(objectClass=*)' , array ( 'msDS-MaximumPasswordAge' ) ) ; if ( $ entry = ldap_get_entries_moodle ( $ ldapconn , $ sr ) ) { $ info = $ entry [ 0 ] ; // Default value of msds-maximumpasswordage is 42 and is always set. $ maxpwdage = $ info [ 'msds-maximumpasswordage' ] [ 0 ] ; } } } } // ---------------------------------------------------------------- // MSDN says that "pwdLastSet contains the number of 100 nanosecond // intervals since January 1, 1601 (UTC), stored in a 64 bit integer". // // According to Perl's Date::Manip, the number of seconds between // this date and Unix epoch is 11644473600. So we have to // substract this value to calculate a Unix time, once we have // scaled pwdLastSet to seconds. This is the script used to // calculate the value shown above: // //    #!/usr/bin/perl -w // //    use Date::Manip; // //    $date1 = ParseDate ("160101010000 UTC"); //    $date2 = ParseDate ("197001010000 UTC"); //    $delta = DateCalc($date1, $date2, \$err); //    $secs = Delta_Format($delta, 0, "%st"); //    print "$secs \n"; // // MSDN also says that "maxPwdAge is stored as a large integer that // represents the number of 100 nanosecond intervals from the time // the password was set before the password expires." We also need // to scale this to seconds. Bear in mind that this value is stored // as a _negative_ quantity (at least in my AD domain). // // As a last remark, if the low 32 bits of maxPwdAge are equal to 0, // the maximum password age in the domain is set to 0, which means // passwords do not expire (see // http://msdn2.microsoft.com/en-us/library/ms974598.aspx) // // As the quantities involved are too big for PHP integers, we // need to use BCMath functions to work with arbitrary precision // numbers. // ---------------------------------------------------------------- // If the low order 32 bits are 0, then passwords do not expire in // the domain. Just do '$maxpwdage mod 2^32' and check the result // (2^32 = 4294967296) if ( bcmod ( $ maxpwdage , 4294967296 ) === '0' ) { return 0 ; } // Add up pwdLastSet and maxPwdAge to get password expiration // time, in MS time units. Remember maxPwdAge is stored as a // _negative_ quantity, so we need to substract it in fact. $ pwdexpire = bcsub ( $ pwdlastset , $ maxpwdage ) ; // Scale the result to convert it to Unix time units and return // that value. return bcsub ( bcdiv ( $ pwdexpire , '10000000' ) , '11644473600' ) ; }
docstring: Get password expiration time for a given user from Active Directory
  
  @param string $pwdlastset The time last time we changed the password.
  @param resource $lcapconn The open LDAP connection.
  @param string $user_dn The distinguished name of the user we are checking.
  
  @return string $unixtime
docstring_tokens: Get password expiration time for a given user from Active Directory