serviceprincipalname
import "github.com/TheManticoreProject/Manticore/windows/kerberos/serviceprincipalname"
Package serviceprincipalname implements a parser, validator and renderer for Kerberos Service Principal Names (SPNs).
An SPN is the name a client uses to identify a service for mutual authentication. Per [MS-ADTS] it is a string with the format:
serviceclass "/" hostname [":"port | ":"instancename] ["/" servicename]
An SPN consists of either two parts or three parts, each separated by a forward slash ("/"). The first part is the service class, the second part is the host name, and the third part (if present) is the service name. The host name part can optionally be suffixed with either a “:port” component or a “:instancename” component. A port component is distinguished from an instancename component by being entirely composed of numeric digits.
For example, “ldap/dc-01.fabrikam.com/fabrikam.com” is a three-part SPN where “ldap” is the service class name, “dc-01.fabrikam.com” is the host name, and “fabrikam.com” is the service name.
Index
- Constants
- func BuiltInServiceClasses() []string
- func IsBuiltInServiceClass(class string) bool
- type ServicePrincipalName
- func FromString(spn string) (*ServicePrincipalName, error)
- func (s *ServicePrincipalName) CoveredByHostSPN() bool
- func (s *ServicePrincipalName) Equal(other *ServicePrincipalName) bool
- func (s *ServicePrincipalName) HasServiceName() bool
- func (s *ServicePrincipalName) IsBuiltInServiceClass() bool
- func (s *ServicePrincipalName) IsHostServiceClass() bool
- func (s *ServicePrincipalName) IsValid() bool
- func (s *ServicePrincipalName) String() string
- func (s *ServicePrincipalName) Validate() error
Constants
HostServiceClass is the special “HOST” service class. A HOST SPN registered on a computer account implicitly substitutes for every built-in service class SPN (see BuiltInServiceClasses): unless a built-in SPN is explicitly registered on another object, a client requesting it is satisfied by the computer’s HOST SPN. HOST itself is not one of the built-in service classes; it is the class that stands in for them.
const HostServiceClass = "HOST"
func BuiltInServiceClasses
func BuiltInServiceClasses() []string
BuiltInServiceClasses returns the built-in SPN service class names recognized for computer accounts, lowercased and sorted. The returned slice is a fresh copy the caller may modify. HOST is not included (see HostServiceClass).
func IsBuiltInServiceClass
func IsBuiltInServiceClass(class string) bool
IsBuiltInServiceClass reports whether class is one of the built-in SPN service classes recognized for computer accounts. The comparison is case-insensitive.
type ServicePrincipalName
ServicePrincipalName represents a parsed Kerberos SPN of the form:
serviceclass "/" hostname [":"port | ":"instancename] ["/" servicename]
Exactly one of Port (non-zero) or InstanceName (non-empty) may be set: the “:”-suffix on the host name is interpreted as a port when it is composed entirely of numeric digits, and as an instance name otherwise.
type ServicePrincipalName struct {
// ServiceClass is the first part of the SPN (e.g. "ldap", "cifs",
// "MSSQLSvc", "HTTP"). It is required.
ServiceClass string
// Hostname is the host portion of the second part of the SPN, with any
// ":port" or ":instancename" suffix removed. It is required.
Hostname string
// Port is the value of the optional numeric ":port" suffix on the host
// name. It is 0 when no numeric port suffix is present.
Port uint16
// InstanceName is the value of the optional non-numeric ":instancename"
// suffix on the host name. It is empty when no such suffix is present.
InstanceName string
// ServiceName is the optional third part of the SPN. It is empty for a
// two-part SPN.
ServiceName string
}
func FromString
func FromString(spn string) (*ServicePrincipalName, error)
FromString parses spn into a ServicePrincipalName and validates it.
It returns an error when spn is empty, has fewer than two or more than three “/”-separated parts, contains an empty component, or carries a numeric port suffix that does not fit in a uint16.
func (*ServicePrincipalName) CoveredByHostSPN
func (s *ServicePrincipalName) CoveredByHostSPN() bool
CoveredByHostSPN reports whether a HOST SPN on the same computer account would implicitly satisfy a request for this SPN. This is true exactly when the service class is a built-in one: per the setspn documentation, a computer’s HOST SPN substitutes for any built-in service class SPN that is not explicitly registered on another object. It does not account for such explicit registrations, which are not knowable from the SPN string alone.
func (*ServicePrincipalName) Equal
func (s *ServicePrincipalName) Equal(other *ServicePrincipalName) bool
Equal reports whether s and other describe the same SPN. Comparison is case-insensitive, matching the case-insensitive handling of SPNs in Kerberos and Active Directory.
func (*ServicePrincipalName) HasServiceName
func (s *ServicePrincipalName) HasServiceName() bool
HasServiceName reports whether the SPN is a three-part SPN (i.e. it carries a service name).
func (*ServicePrincipalName) IsBuiltInServiceClass
func (s *ServicePrincipalName) IsBuiltInServiceClass() bool
IsBuiltInServiceClass reports whether the SPN’s service class is one of the built-in service classes recognized for computer accounts (case-insensitive).
func (*ServicePrincipalName) IsHostServiceClass
func (s *ServicePrincipalName) IsHostServiceClass() bool
IsHostServiceClass reports whether the SPN’s service class is the special “HOST” class (case-insensitive).
func (*ServicePrincipalName) IsValid
func (s *ServicePrincipalName) IsValid() bool
IsValid reports whether the ServicePrincipalName is well-formed. It is a boolean convenience wrapper over Validate.
func (*ServicePrincipalName) String
func (s *ServicePrincipalName) String() string
String renders the canonical SPN string. For a value produced by FromString the result round-trips back to an equal ServicePrincipalName.
func (*ServicePrincipalName) Validate
func (s *ServicePrincipalName) Validate() error
Validate checks that the ServicePrincipalName is well-formed: the service class and host name are present, at most one of Port/InstanceName is set, and no component contains a separator ("/" or “:”) that would break round-tripping through String.
FromString calls Validate before returning, so any value produced by FromString is valid. Validate is intended for values constructed by hand.