ssha

ssha, or salted sha is a password encryption method for LDAP, see the OpenLDAP Faq-O-Matic page for details.

To create an LDAP SSHA password entry in Tcl do something along the following lines:

package require sha1
proc ldapPasswordStringSSHA {clear salt} {
    # return ldap password string from clear, generated with SSHA
    
    set salted [sha1::sha1 -bin ${clear}${salt}]
    return [binary encode base64 ${salted}${salt}]
}

Notes:

  • You must use a salt with length 4, this seems to be a convention used in OpenLDAP
  • This example requires Tcllib to be installed
  • base64 encoding is done using Tcl 8.6 features - see base64 for alternatives
  • OpenLDAP claims that SSHA is defined in RFC 3112, but I could not confirm that. Only SHA is mentioned there.

To create a random salt on *nix* like operating systems you can use the following:

proc createRandomSalt n {
    # return a random string with length n
    
    set fd [open /dev/random]
    set salt [read $fd $n]
    close $fd
    return $salt
}

Notes:

  • /dev/random is a magic file on *nix* like operating systems, yielding random bytes when read. Replace with any suitable source of cryptographically strong randomness.

To compare a password with its LDIF representation use the following:

proc matchLdapSshaPassword {ldif clear} {
    # decode ldif, get schema, encode clear with schema and compare

    set ldapPasswordString [binary decode base64 $ldif]
    lassign [split $ldapPasswordString \}] schema encodedPassword
    set schema [string range $schema 1 end]
    set salt ""
    switch -exact -- $schema {
        SSHA {set salt [string range [binary decode base64 $encodedPassword] end-3 end]}
        default {
            error "password schema not handled: $ldapPasswordString"
        }
    }
    return [expr {$ldapPasswordString eq [ldapPasswordStringSSHA $clear $salt]}]
}

Notes:

  • Passwords in LDIF exports are always base64 encoded
  • The salt is the last four bytes of the decoded password string

Example:

  • Password abcd
  • Salt 0123
  • LDAP SSHA password string: {SSHA}pnv8w4j8hjggzs/O8y0uo9qOuw0wMTIz
  • LDIF encoded: e1NTSEF9cG52OHc0ajhoamdnenMvTzh5MHVvOXFPdXcwd01USXo=

LEG has wrapped up this code into a Tcl script. See his page for reference.


LEG - 2021-04-02 13:17:53

The edit by bairul is justified but not completely functional, since it misses the {SSHA} prefix in the LDIF string. I'd fix this up right now, if I'd time, but I don't. Either use the refrenced ldappw "wrapper" or think it through by yourself.