diff --git a/commands/constructors.go b/commands/constructors.go index 0f3c238..fc1e973 100644 --- a/commands/constructors.go +++ b/commands/constructors.go @@ -248,3 +248,31 @@ func CreateGetPseudoRandomCommand(numBytes uint16) *CommandMessage { return command } + +func CreatePutWrapkeyCommand(objID uint16, label []byte, domains uint16, capabilities, delegated uint64, wrapkey []byte) (*CommandMessage, error) { + if len(label) > LabelLength { + return nil, errors.New("label is too long") + } + if len(label) < LabelLength { + label = append(label, bytes.Repeat([]byte{0x00}, LabelLength-len(label))...) + } + if keyLen := len(wrapkey); keyLen != 16 && keyLen != 24 && keyLen != 32 { + return nil, errors.New("wrapkey is wrong length") + } + + command := &CommandMessage{ + CommandType: CommandTypePutWrapKey, + } + + payload := bytes.NewBuffer([]byte{}) + binary.Write(payload, binary.BigEndian, objID) + payload.Write(label) + binary.Write(payload, binary.BigEndian, domains) + binary.Write(payload, binary.BigEndian, capabilities) + binary.Write(payload, binary.BigEndian, delegated) + payload.Write(wrapkey) + + command.Data = payload.Bytes() + + return command, nil +} diff --git a/commands/response.go b/commands/response.go index 276f031..d107205 100644 --- a/commands/response.go +++ b/commands/response.go @@ -83,6 +83,10 @@ type ( ChangeAuthenticationKeyResponse struct { ObjectID uint16 } + + PutWrapkeyResponse struct { + ObjectID uint16 + } ) // ParseResponse parses the binary response from the card to the relevant Response type. @@ -139,6 +143,8 @@ func ParseResponse(data []byte) (Response, error) { return parseChangeAuthenticationKeyResponse(payload) case CommandTypeGetPseudoRandom: return parseGetPseudoRandomResponse(payload), nil + case CommandTypePutWrapKey: + return parsePutWrapkeyResponse(payload) case ErrorResponseCode: return nil, parseErrorResponse(payload) default: @@ -288,6 +294,19 @@ func parseGetPseudoRandomResponse(payload []byte) Response { return payload } +func parsePutWrapkeyResponse(payload []byte) (Response, error) { + if len(payload) != 2 { + return nil, errors.New("invalid response payload length") + } + + var objectID uint16 + err := binary.Read(bytes.NewReader(payload), binary.BigEndian, &objectID) + if err != nil { + return nil, err + } + return &PutWrapkeyResponse{ObjectID: objectID}, nil +} + // Error formats a card error message into a human readable format func (e *Error) Error() string { message := ""