指纹解锁结果如何回传到上层的

指纹设别流程_liujun3512159的博客-CSDN博客

最后部分,有介绍。

final ClientMonitorCallbackConverter listener = getListener();
。。。
。。。 
if (listener != null) {
                        try {
                            // Explicitly have if/else here to make it super obvious in case the
                            // code is touched in the future.
                            if (!mIsRestricted) {
                                listener.onAuthenticationSucceeded(getSensorId(),
                                        identifier,
                                        byteToken,
                                        getTargetUserId(),
                                        mIsStrongBiometric);
                            } else {
                                listener.onAuthenticationSucceeded(getSensorId(),
                                        null /* identifier */,
                                        byteToken,
                                        getTargetUserId(),
                                        mIsStrongBiometric);
                            }
                        } catch (RemoteException e) {
                            Slog.e(TAG, "Unable to notify listener", e);
                        }
                    } else {
                        Slog.w(TAG, "Client not listening");
                    }

现在看看listener是如何一步一步的回传到最上层的?

经过分析,我们发现在AuthenticationClient类的构造函数中有listener,进一步发现,这个listener实际上在其子类FingerprintAuthenticationClient中传进来的

继续追踪发现,在类Fingerprint21类中scheduleAuthenticate方法中new FingerprintAuthenticationClient,然后传入了listener对象实例,需要跟踪listener在哪儿定义的

    @Override
    public void scheduleAuthenticate(int sensorId, @NonNull IBinder token, long operationId,
            int userId, int cookie, @NonNull ClientMonitorCallbackConverter listener,
            @NonNull String opPackageName, long requestId, boolean restricted, int statsClient,
            boolean allowBackgroundAuthentication) {
        mHandler.post(() -> {
            scheduleUpdateActiveUserWithoutHandler(userId);

            final boolean isStrongBiometric = Utils.isStrongBiometric(mSensorProperties.sensorId);
            final FingerprintAuthenticationClient client = new FingerprintAuthenticationClient(
                    mContext, mLazyDaemon, token, requestId, listener, userId, operationId,
                    restricted, opPackageName, cookie, false /* requireConfirmation */,
                    mSensorProperties.sensorId, isStrongBiometric, statsClient,
                    mTaskStackListener, mLockoutTracker,
                    mUdfpsOverlayController, mSidefpsController,
                    allowBackgroundAuthentication, mSensorProperties);
            mScheduler.scheduleClientMonitor(client, mFingerprintStateCallback);
        });
    }

继续往下看,在下面的FingerprintService类的authenticate方法中,第63行调用scheduleAuthenticate方法

@SuppressWarnings("deprecation")
        @Override // Binder call
        public long authenticate(final IBinder token, final long operationId,
                final int sensorId, final int userId, final IFingerprintServiceReceiver receiver,
                final String opPackageName, boolean ignoreEnrollmentState) {
            final int callingUid = Binder.getCallingUid();
            final int callingPid = Binder.getCallingPid();
            final int callingUserId = UserHandle.getCallingUserId();

            if (!canUseFingerprint(opPackageName, true /* requireForeground */, callingUid,
                    callingPid, callingUserId)) {
                Slog.w(TAG, "Authenticate rejecting package: " + opPackageName);
                return -1;
            }

            // Keyguard check must be done on the caller's binder identity, since it also checks
            // permission.
            final boolean isKeyguard = Utils.isKeyguard(getContext(), opPackageName);

            // Clear calling identity when checking LockPatternUtils for StrongAuth flags.
            long identity = Binder.clearCallingIdentity();
            try {
                if (isKeyguard && Utils.isUserEncryptedOrLockdown(mLockPatternUtils, userId)) {
                    // If this happens, something in KeyguardUpdateMonitor is wrong.
                    // SafetyNet for b/79776455
                    EventLog.writeEvent(0x534e4554, "79776455");
                    Slog.e(TAG, "Authenticate invoked when user is encrypted or lockdown");
                    return -1;
                }
            } finally {
                Binder.restoreCallingIdentity(identity);
            }

            final boolean restricted = getContext().checkCallingPermission(MANAGE_FINGERPRINT)
                    != PackageManager.PERMISSION_GRANTED;
            final int statsClient = isKeyguard ? BiometricsProtoEnums.CLIENT_KEYGUARD
                    : BiometricsProtoEnums.CLIENT_FINGERPRINT_MANAGER;

            final Pair<Integer, ServiceProvider> provider;
            if (sensorId == FingerprintManager.SENSOR_ID_ANY) {
                provider = getSingleProvider();
            } else {
                Utils.checkPermission(getContext(), USE_BIOMETRIC_INTERNAL);
                provider = new Pair<>(sensorId, getProviderForSensor(sensorId));
            }
            if (provider == null) {
                Slog.w(TAG, "Null provider for authenticate");
                return -1;
            }

            final FingerprintSensorPropertiesInternal sensorProps =
                    provider.second.getSensorProperties(sensorId);
            if (!isKeyguard && !Utils.isSettings(getContext(), opPackageName)
                    && sensorProps != null && sensorProps.isAnyUdfpsType()) {
                identity = Binder.clearCallingIdentity();
                try {
                    return authenticateWithPrompt(operationId, sensorProps, userId, receiver,
                            ignoreEnrollmentState);
                } finally {
                    Binder.restoreCallingIdentity(identity);
                }
            }
            return provider.second.scheduleAuthenticate(provider.first, token, operationId, userId,
                    0 /* cookie */, new ClientMonitorCallbackConverter(receiver), opPackageName,
                    restricted, statsClient, isKeyguard);
        }

第64行new ClientMonitorCallbackConverter(receiver) 就是这个listener

这里关键参数receiver是通过aidl传到FingerprintService下的authenticate方法中

显然,这里是通过调用FingerprintManager类的authenticate传进来的

/**
  * Per-user and per-sensor version of authenticate.
  * @hide
*/
@RequiresPermission(anyOf = {USE_BIOMETRIC, USE_FINGERPRINT})
    public void authenticate(@Nullable CryptoObject crypto, @Nullable CancellationSignal cancel,
            @NonNull AuthenticationCallback callback, Handler handler, int sensorId, int userId,
            int flags) {

        FrameworkStatsLog.write(FrameworkStatsLog.AUTH_DEPRECATED_API_USED,
                AUTH_DEPRECATED_APIUSED__DEPRECATED_API__API_FINGERPRINT_MANAGER_AUTHENTICATE,
                mContext.getApplicationInfo().uid,
                mContext.getApplicationInfo().targetSdkVersion);

        if (callback == null) {
            throw new IllegalArgumentException("Must supply an authentication callback");
        }

        if (cancel != null && cancel.isCanceled()) {
            Slog.w(TAG, "authentication already canceled");
            return;
        }

        final boolean ignoreEnrollmentState = flags == 0 ? false : true;

        if (mService != null) {
            try {
                useHandler(handler);
                mAuthenticationCallback = callback;
                mCryptoObject = crypto;
                final long operationId = crypto != null ? crypto.getOpId() : 0;
                final long authId = mService.authenticate(mToken, operationId, sensorId, userId,
                        mServiceReceiver, mContext.getOpPackageName(), ignoreEnrollmentState);
                if (cancel != null) {
                    cancel.setOnCancelListener(new OnAuthenticationCancelListener(authId));
                }
            } catch (RemoteException e) {
                Slog.w(TAG, "Remote exception while authenticating: ", e);
                // Though this may not be a hardware issue, it will cause apps to give up or try
                // again later.
                callback.onAuthenticationError(FINGERPRINT_ERROR_HW_UNAVAILABLE,
                        getErrorString(mContext, FINGERPRINT_ERROR_HW_UNAVAILABLE,
                                0 /* vendorCode */));
            }
        }
    }

第32行参数mServiceReceiver就是这个了

private IFingerprintServiceReceiver mServiceReceiver = new IFingerprintServiceReceiver.Stub() {

        @Override // binder call
        public void onEnrollResult(Fingerprint fp, int remaining) {
            mHandler.obtainMessage(MSG_ENROLL_RESULT, remaining, 0, fp).sendToTarget();
        }

        @Override // binder call
        public void onAcquired(int acquireInfo, int vendorCode) {
            mHandler.obtainMessage(MSG_ACQUIRED, acquireInfo, vendorCode).sendToTarget();
        }

        @Override // binder call
        public void onAuthenticationSucceeded(Fingerprint fp, int userId,
                boolean isStrongBiometric) {
            mHandler.obtainMessage(MSG_AUTHENTICATION_SUCCEEDED, userId, isStrongBiometric ? 1 : 0,
                    fp).sendToTarget();
        }

        @Override
        public void onFingerprintDetected(int sensorId, int userId, boolean isStrongBiometric) {
            mHandler.obtainMessage(MSG_FINGERPRINT_DETECTED, sensorId, userId, isStrongBiometric)
                    .sendToTarget();
        }

        @Override // binder call
        public void onAuthenticationFailed() {
            mHandler.obtainMessage(MSG_AUTHENTICATION_FAILED).sendToTarget();
        }

        @Override // binder call
        public void onError(int error, int vendorCode) {
            mHandler.obtainMessage(MSG_ERROR, error, vendorCode).sendToTarget();
        }

        @Override // binder call
        public void onRemoved(Fingerprint fp, int remaining) {
            mHandler.obtainMessage(MSG_REMOVED, remaining, 0, fp).sendToTarget();
        }

        @Override // binder call
        public void onChallengeGenerated(int sensorId, int userId, long challenge) {
            mHandler.obtainMessage(MSG_CHALLENGE_GENERATED, sensorId, userId, challenge)
                    .sendToTarget();
        }

        @Override // binder call
        public void onUdfpsPointerDown(int sensorId) {
            mHandler.obtainMessage(MSG_UDFPS_POINTER_DOWN, sensorId, 0).sendToTarget();
        }

        @Override // binder call
        public void onUdfpsPointerUp(int sensorId) {
            mHandler.obtainMessage(MSG_UDFPS_POINTER_UP, sensorId, 0).sendToTarget();
        }
    }

这里,我们看第16行

case MSG_AUTHENTICATION_SUCCEEDED:
                    sendAuthenticatedSucceeded((Fingerprint) msg.obj, msg.arg1 /* userId */,
                            msg.arg2 == 1 /* isStrongBiometric */);

 private void sendAuthenticatedSucceeded(Fingerprint fp, int userId, boolean isStrongBiometric) {
        if (mAuthenticationCallback != null) {
            final AuthenticationResult result =
                    new AuthenticationResult(mCryptoObject, fp, userId, isStrongBiometric);
            mAuthenticationCallback.onAuthenticationSucceeded(result);
        }
    }

第5行,变量mAuthenticationCallback 是从哪儿来的?

见博客

​​​​​​生物解锁--指纹服务注册流程_liujun3512159的博客-CSDN博客

mFpm.authenticate(null /* crypto */, mFingerprintCancelSignal,
                        mFingerprintAuthenticationCallback, null /* handler */,
                        FingerprintManager.SENSOR_ID_ANY, userId, 0 /* flags */);

实际上就是mFingerprintAuthenticationCallback 对象实例。

从这里,我们发现,底软那边解锁成功,一步步的回调到这里,告知上层用户,解锁成功,分析结束。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

liujun3512159

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值