Attributes for AD Users : lastLogon
The Active Directory attribute lastLogon shows the exact timestamp of the user's last successful domain authentication on the regarding domain controller. It doesn't matter here how the user performed this logon operation - interactive, network, passed-through from a radius service or another kerberos realm. If the user never did logon to the DC, the value of lastLogon is zero.
|Data type||Integer8 (64 bit signed numeric)|
|In Global Catalog?||No|
|AD DB attribute name||Last-Logon|
|ADSI datatype||10 - LargeInteger|
|LDAP syntax||1.2.840.1135184.108.40.2066 - Microsoft Large Integer|
|Used in ...||> W2K|
|Schema Doku||Microsoft - MSDN|
Please note that this value is NOT replicated between domain controllers - if you want to know the exact last logon time for an account in a domain with more than one domain controllers, you have to check this value on all domain controllers! In Windows 2003 Active Directory, Microsoft introduced another user attribute named lastLogonTimestamp. This attribute is replicated to other DCs, but only after two weeks (minus a random percentage of 5 days), so it is suitable to locate inactive accounts which did not logon to the domain for a long time.
The lastLogon value is a Microsoft Large Integer, these are signed numeric values of 8 Byte (64 bit) - those are often called Integer8 values for this reason:
-9223372036854775808 (-2^63) or
Maximum value:9223372036854775807 (2^63 - 1) or
There is another article in the SelfADSI Tutorial about the Microsoft Integer8 values which represent date and time or time intervals.
The value stored in the lastLogon attribute represents the date and time of the account logon, expressed in 100-nanosecond steps since 12:00 AM, January 1, 1601.
By the way, this is a specification which is also used in the Microsoft FileTime structure. Additionally, it is important to know that an Active Directory domain controller stores the date and time always in the UTC time format (Universal Coordinated Time) - this is (almost) the former Greenwich Meantime (GMT). So if your systems are for example in Pacific Standard Time (PST, which is GMT-8), so you have to recalculate the Integer8 attribute values if you want to know the date and times in your local time.
If you want to read the lastLogon attribute of a certain user, you first have to handle the returned Large Integer which is divided into two 32bit parts: The HighPart and the LowPart. These parts are accessible in the ADSI interface for this datatype. But: You always have to use a leading 'Set' statement when reading a Large Integer/Integer8 attribute in an ADSI script. Otherwise you can't access the ADSI interface properties 'Highpart' and 'Lowpart'.
Convert a lastLogon value to a readable date and time value
So here is the script code to convert an Integer8 into a date and time, including the local time zone adjustment (we take the time abbreviation from UTC from the registry):
Search for all users which logged on to a domain controller in the last week
Here comes another script where you need to convert a date and time value to the according Integer8 - we want to find all users which logged on to a certain domain controller in the last week. To build a correct LDAP filter, we need the Large Integer value for the date and time one week ago.... If you don't know exactly how the script searches for the objects - there is a detailed article here in the SelfADSI Tutorial which explains the LDAP search with ADO techniques.