public static async Task <CommandStatus> ChangePin(DevParam devParam, string newpin, string currentpin) { var status = new CommandStatus(); try { var ctap = new CTAPauthenticatorClientPIN(); var st = await ctap.GetKeyAgreement(devParam); status.commands.Add(new CommandStatus.CommandInfo(ctap, st)); if (st.Status != 0) { throw (new Exception("GetKeyAgreement")); } var sharedSecret = ctap.createSharedSecret(ctap.Authenticator_KeyAgreement); // pinAuth: // LEFT(HMAC-SHA-256(sharedSecret, newPinEnc || pinHashEnc), 16). var pinAuth = ctap.createPinAuthforChangePin(sharedSecret, newpin, currentpin); // newPinEnc: AES256-CBC(sharedSecret, IV = 0, newPin) byte[] newPinEnc = ctap.createNewPinEnc(sharedSecret, newpin); // pinHashEnc: // Encrypted first 16 bytes of SHA - 256 hash of curPin using sharedSecret: // AES256-CBC(sharedSecret, IV = 0, LEFT(SHA-256(curPin), 16)). var pinHashEnc = ctap.createPinHashEnc(currentpin, sharedSecret); var st2 = await ctap.ChangePIN(devParam, pinAuth, newPinEnc, pinHashEnc); status.commands.Add(new CommandStatus.CommandInfo(ctap, st2)); if (st2.Status != 0) { throw (new Exception("ChangePIN")); } status.isSuccess = true; } catch (Exception ex) { status.setErrorMsg(ex); } return(status); }
public static async Task <CommandStatus> SetPin(DevParam devParam, string newpin) { var status = new CommandStatus(); try { var ctap = new CTAPauthenticatorClientPIN(); var st = await ctap.GetKeyAgreement(devParam); status.commands.Add(new CommandStatus.CommandInfo(ctap, st)); if (st.Status != 0) { throw (new Exception("GetKeyAgreement")); } var sharedSecret = ctap.createSharedSecret(ctap.Authenticator_KeyAgreement); // pinAuth = LEFT(HMAC-SHA-256(sharedSecret, newPinEnc), 16) var pinAuth = ctap.createPinAuthforSetPin(sharedSecret, newpin); // newPinEnc: AES256-CBC(sharedSecret, IV = 0, newPin) byte[] newPinEnc = ctap.createNewPinEnc(sharedSecret, newpin); var st2 = await ctap.SetPIN(devParam, pinAuth, newPinEnc); status.commands.Add(new CommandStatus.CommandInfo(ctap, st2)); if (st2.Status != 0) { throw (new Exception("SetPIN")); } status.isSuccess = true; } catch (Exception ex) { status.setErrorMsg(ex); } return(status); }
public static async Task <CreateCommandStatus> Create(DevParam devParam, PublicKeyforCreate publickey) { var status = new CreateCommandStatus(); try { if (publickey.rp == null || publickey.user == null || publickey.challenge == null) { throw (new Exception("Param Error")); } var ctap = new CTAPauthenticatorMakeCredential(); ctap.RpId = publickey.rp.id; ctap.RpName = publickey.rp.name; ctap.UserId = publickey.user.id; ctap.UserId_bytearray = publickey.user.id_bytearray; ctap.UserName = publickey.user.name; ctap.UserDisplayName = publickey.user.displayName; ctap.ClientDataHash = CTAPauthenticator.CreateClientDataHash(publickey.challenge); ctap.TimeoutMs = publickey.timeout; ctap.Option_rk = publickey.authenticatorSelection.requireResidentKey; if (publickey.authenticatorSelection.userVerification == UserVerificationRequirement.discouraged) { ctap.Option_uv = false; } else { ctap.Option_uv = true; } if (publickey.pin.Length > 0) { string pin = publickey.pin; var ctap2 = new CTAPauthenticatorClientPIN(); var st1 = await ctap2.GetKeyAgreement(devParam); status.commands.Add(new CommandStatus.CommandInfo(ctap2, st1)); if (st1.Status != 0) { throw (new Exception("GetKeyAgreement")); } var sharedSecret = ctap2.createSharedSecret(ctap2.Authenticator_KeyAgreement); var pinHashEnc = ctap2.createPinHashEnc(pin, sharedSecret); var token = await ctap2.GetPINToken(devParam, pinHashEnc); status.commands.Add(new CommandStatus.CommandInfo(ctap2, token)); if (token.Status != 0) { throw (new Exception("GetPINToken")); } ctap.PinAuth = ctap2.createPinAuth(sharedSecret, ctap.ClientDataHash, token.PinTokenEnc); } var att = await ctap.SendAndResponse(devParam); status.commands.Add(new CommandStatus.CommandInfo(ctap, att)); if (att.Status != 0) { throw (new Exception("MakeCredential")); } status.attestation = att; status.isSuccess = true; } catch (Exception ex) { status.setErrorMsg(ex); } return(status); }
public static async Task <GetCommandStatus> Get(DevParam devParam, PublicKeyforGet publickey) { var status = new GetCommandStatus(); try { string rpid = publickey.rpId; var ctap = new CTAPauthenticatorGetAssertion(); ctap.RpId = rpid; ctap.ClientDataHash = CTAPauthenticator.CreateClientDataHash(publickey.challenge); ctap.Timeout = publickey.timeout; // credential-id if (publickey.allowCredentials != null && publickey.allowCredentials.Count > 0 && publickey.allowCredentials[0] != null && publickey.allowCredentials[0].id != null && publickey.allowCredentials[0].id.Length > 0) { ctap.AllowList_CredentialId = publickey.allowCredentials[0].id; } ctap.Option_up = publickey.requireUserPresence; if (publickey.userVerification == UserVerificationRequirement.discouraged) { ctap.Option_uv = false; } else { ctap.Option_uv = true; } // pin if (publickey.pin.Length > 0) { string pin = publickey.pin; var ctap2 = new CTAPauthenticatorClientPIN(); var st1 = await ctap2.GetKeyAgreement(devParam); status.commands.Add(new CommandStatus.CommandInfo(ctap2, st1)); if (st1.Status != 0) { throw (new Exception("GetKeyAgreement")); } var sharedSecret = ctap2.createSharedSecret(ctap2.Authenticator_KeyAgreement); var pinHashEnc = ctap2.createPinHashEnc(pin, sharedSecret); var token = await ctap2.GetPINToken(devParam, pinHashEnc); status.commands.Add(new CommandStatus.CommandInfo(ctap2, token)); if (token.Status != 0) { throw (new Exception("GetPINToken")); } ctap.PinAuth = ctap2.createPinAuth(sharedSecret, ctap.ClientDataHash, token.PinTokenEnc); } var ret = await ctap.SendAndResponse(devParam); status.commands.Add(new CommandStatus.CommandInfo(ctap, ret)); if (ret.Status != 0) { throw (new Exception("GetAssertion")); } status.assertions.Add(ret); if (ret.NumberOfCredentials > 0) { for (int intIc = 0; intIc < ret.NumberOfCredentials - 1; intIc++) { var next = new CTAPauthenticatorGetNextAssertion(); var nextret = await next.SendAndResponse(devParam); status.commands.Add(new CommandStatus.CommandInfo(next, nextret)); if (ret.Status != 0) { throw (new Exception("GetNextAssertion")); } status.assertions.Add(nextret); } } // uv=trueでリクエストしてuvされていなければエラー if (ctap.Option_uv) { if (ret.Flags_UserVerifiedResult == false) { throw (new Exception("UserVerifiedResult False")); } } status.isSuccess = true; } catch (Exception ex) { status.setErrorMsg(ex); } return(status); }