Authenticate checks validity of provided token.
(token []byte, remoteAddr string)
| 93 | |
| 94 | // Authenticate checks validity of provided token. |
| 95 | func (ta *authenticator) Authenticate(token []byte, remoteAddr string) (*auth.Rec, []byte, error) { |
| 96 | var tl tokenLayout |
| 97 | dataSize := binary.Size(&tl) |
| 98 | if len(token) < dataSize+sha256.Size { |
| 99 | // Token is too short |
| 100 | return nil, nil, types.ErrMalformed |
| 101 | } |
| 102 | |
| 103 | buf := bytes.NewBuffer(token) |
| 104 | err := binary.Read(buf, binary.LittleEndian, &tl) |
| 105 | if err != nil { |
| 106 | return nil, nil, types.ErrMalformed |
| 107 | } |
| 108 | |
| 109 | hbuf := new(bytes.Buffer) |
| 110 | binary.Write(hbuf, binary.LittleEndian, &tl) |
| 111 | |
| 112 | // Check signature. |
| 113 | hasher := hmac.New(sha256.New, ta.hmacSalt) |
| 114 | hasher.Write(hbuf.Bytes()) |
| 115 | if !hmac.Equal(token[dataSize:dataSize+sha256.Size], hasher.Sum(nil)) { |
| 116 | return nil, nil, types.ErrFailed |
| 117 | } |
| 118 | |
| 119 | // Check authentication level for validity. |
| 120 | if auth.Level(tl.AuthLevel) > auth.LevelRoot { |
| 121 | return nil, nil, types.ErrMalformed |
| 122 | } |
| 123 | |
| 124 | // Check serial number. |
| 125 | if int(tl.SerialNumber) != ta.serialNumber { |
| 126 | return nil, nil, types.ErrFailed |
| 127 | } |
| 128 | |
| 129 | // Check token expiration time. |
| 130 | expires := time.Unix(int64(tl.Expires), 0).UTC() |
| 131 | if expires.Before(time.Now().Add(1 * time.Second)) { |
| 132 | return nil, nil, types.ErrExpired |
| 133 | } |
| 134 | |
| 135 | return &auth.Rec{ |
| 136 | Uid: types.Uid(tl.Uid), |
| 137 | AuthLevel: auth.Level(tl.AuthLevel), |
| 138 | Lifetime: auth.Duration(time.Until(expires)), |
| 139 | Features: auth.Feature(tl.Features), |
| 140 | State: types.StateUndefined}, nil, nil |
| 141 | } |
| 142 | |
| 143 | // GenSecret generates a new token. |
| 144 | func (ta *authenticator) GenSecret(rec *auth.Rec) ([]byte, time.Time, error) { |