Beispiel #1
0
        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);
        }
Beispiel #2
0
        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);
        }
Beispiel #3
0
        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);
        }
Beispiel #4
0
        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);
        }