Documentation
¶
Overview ¶
Package radius terminates RADIUS Access-Request for switch and router login. The worker listens on UDP, checks the packet with the NAS shared secret, and binds to LDAP itself. factum2 is where the policy is edited and where accept/reject lines are stored; it is not on the login path.
Index ¶
- Constants
- Variables
- func EncodeReply(text string) ([]byte, error)
- func ReplyText(stored *string) string
- func Run(ctx context.Context, opt Options) error
- func StatePath(override string) string
- func ValidateListen(s string) error
- func ValidateReply(text string) error
- type Client
- type Config
- type Device
- type Event
- type Index
- type Machine
- type Options
- type Packet
- type Policy
- type Server
Constants ¶
const ( // Role is the worker.commands name that starts the UDP listener and // may fetch /api/radius-config. Role = "radius" DefaultListen = ":1812" )
const DefaultReply = `` /* 684-byte string literal not displayed */
DefaultReply is sent on Access-Accept until an administrator saves a different set. Devices ignore vendor attributes that are not theirs. Each line is one attribute. A leading # skips the line. A # after the value, outside quotes, is a comment and is not sent. =, := and += all add one attribute, so a repeated name is a second copy (FreeRADIUS +=). An unknown name can be written as 26.<vendor>.<type> = value.
Variables ¶
var ErrBadCredentials = errors.New("bad credentials")
ErrBadCredentials is a wrong username or password. Callers must not treat it as a directory outage.
Functions ¶
func EncodeReply ¶
EncodeReply turns reply lines into RADIUS attribute bytes. Message-Authenticator is not included; the caller puts that first.
func ReplyText ¶
ReplyText returns the reply lines to send. A nil stored value means the built-in set. An empty string sends no vendor attributes.
func StatePath ¶
StatePath is the on-disk config cache. Empty uses the default under /var/lib/factum2. The file holds directory and NAS secrets.
func ValidateListen ¶
ValidateListen accepts an empty address (the worker uses :1812) or a host:port string such as ":1812" or "10.0.0.5:1812".
func ValidateReply ¶
ValidateReply reports whether text can be encoded into an Access-Accept.
Types ¶
type Client ¶
type Client struct {
Name string `json:"name"`
Address string `json:"address"`
Secret string `json:"secret"`
}
Client is one NAS (router or switch) allowed to send Access-Request.
type Config ¶
type Config struct {
Enabled bool `json:"enabled"`
Listen string `json:"listen"`
LDAP ldapauth.Config `json:"ldap"`
Clients []Client `json:"clients"`
Policies []Policy `json:"policies"`
Devices []Device `json:"devices"`
// Reply is the Access-Accept attribute text. Empty sends none.
Reply string `json:"reply"`
// Machine is the AD computer account used to check MS-CHAPv2.
Machine Machine `json:"machine"`
}
Config is the snapshot a worker persists and serves from. LDAP is the directory the worker binds to; it is not read at request time from factum2.
type Device ¶
type Device struct {
Name string `json:"name"`
Role string `json:"role"`
Enabled bool `json:"enabled"`
Addresses []string `json:"addresses"`
}
Device is one NetBox device the worker can name from an address.
type Event ¶
type Event struct {
ReportedAt string `json:"reported_at"`
Username string `json:"username,omitempty"`
NASIP string `json:"nas_ip,omitempty"`
DeviceName string `json:"device_name,omitempty"`
DeviceRole string `json:"device_role,omitempty"`
Result string `json:"result"`
Reason string `json:"reason"`
Worker string `json:"worker,omitempty"`
}
Event is one login attempt safe to store. Password is never included.
type Index ¶
type Index struct {
Enabled bool
Listen string
LDAP ldapauth.Config
// contains filtered or unexported fields
}
Index is the lookup form of Config. Ambiguous addresses (two devices, or two clients) are omitted so a login against them fails closed.
func BuildIndex ¶
BuildIndex indexes clients and devices by canonical IP.
type Machine ¶
type Machine struct {
Account string `json:"account"`
Password string `json:"password"`
Domain string `json:"domain"`
}
Machine is the Active Directory computer account that opens the NETLOGON channel used to check MS-CHAPv2. Account is the SAM name, including the trailing $.
type Options ¶
type Options struct {
StatePath string
Worker string
Fetch func(ctx context.Context) ([]byte, error)
Report func(ctx context.Context, body []byte) error
// Authenticate overrides the LDAP bind. Tests set it. Nil uses ldapauth.
Authenticate func(cfg ldapauth.Config, username, password string) (groups []string, ok bool, err error)
// VerifyMSCHAP overrides the Active Directory NETLOGON check. Nil uses
// verifyMSCHAP. A nil error and a 16-byte session key means the response
// was accepted. ErrBadCredentials is a wrong password.
VerifyMSCHAP func(ctx context.Context, cfg ldapauth.Config, machine Machine, username string, challenge, ntResponse []byte) ([]byte, error)
// LookupGroups overrides the directory group search used after MS-CHAPv2.
LookupGroups func(cfg ldapauth.Config, username string) (groups []string, found bool, err error)
}
Options wires the listener to the hub. Fetch and Report may fail while factum2 is down; the last Config on disk keeps answering.
type Packet ¶
Packet is a parsed RADIUS message. Raw is the on-wire bytes of Length, which is what the Message-Authenticator covers.