Chromium OS‎ > ‎packages‎ > ‎

biod: Biometrics Daemon

Introduction

The biometrics daemon (biod for short) handles pulling in biometrics data from Chrome OS device sensors, like a fingerprint scanner, and processing the data using closed and open source userspace drivers. In addition, it is Chrome's point of contact for enrolling these biometric data and for unlocking the device upon successful authentication.


Installation and Basic Usage

If your board overlay doesn't already install biod for you, these instructions apply if you'd like to install it manually. All these command run inside the CrOS chroot, unless otherwise noted.
  1. Add a line with USE="${USE} biod" in the make.conf file of your overlay (i.e. ~/trunk/src/overlays/overlay-${BOARD}/make.conf inside the CrOS chroot).
  2. Cros work on start the biod:  cros_workon-${BOARD} start biod
  3. Build: cros_workon_make --board=${BOARD} --install biod
  4. Deploy: cros deploy ${DUT_IP_ADDR} biod
  5. On the device: start biod
(TEMPORARY, as of 12/21/2016) A few other things worth checking:
  1. In (dut) /etc, check that both passwd and group file contain biod. If not, copy both files from (chroot) /build/${BOARD}/etc.
Assuming you don't see any errors up to this point, you can confirm everything is running with the following diagnostic tests. Each of these is run on the CrOS device your are testing with.
  1. Check for biod log files under /var/log/biod/biod.LATEST (this one is opened by the biod process) or /var/log/biod.out (this one is the stdout of biod redirected by upstart/init). 
  2. Check that dbus-send --system --dest=org.freedesktop.DBus --type=method_call --print-reply /org/freedesktop/DBus org.freedesktop.DBus.ListNames returns an array with "org.chromium.BiometricsDaemon" in it. If this command fails entirely, your DBus daemon is broken. If the BiometricsDaemon entry is missing, biod is not connected to the DBus, likely because it lacked permissions to claim the bus name or it crashed.
  3. Check the output of biod_client_tool list <hash of user id>. It should show you all biometric devices and their enrollments for a specific user. If that command doesn't exist, your biod deployment is broken, perhaps because it's old. If the command does run but has errors resembling "ServiceUnknown", it failed to connect to biod for some reason. If you see proper output but the biometric device you expected to be there is missing, there is likely some kind of error in the logs mentioned above you should check. 
You should always see the FakeBiometric device and you can use that for exercising biod without requiring any special biometric hardware. The "biometric" device in this case is emulated with a tool called fake_biometric_tool that should be installed along with biod. Use that in combination with biod_client_tool enroll and biod_client_tool authenticate to check that the DBus communication is working properly. If you have a real biometric device you'd like to test with biod, those biod_client_tool commands should still work with your actual biometric device, without requiring any usage of the fake biometric suite. See those commands' associated --help for more information on their usage.

D-Bus API

Service Name: org.chromium.BiometricsDaemon
Root Object: /org/chromium/BiometricsDaemon

The root object implements the org.freedesktop.DBus.ObjectManager interface which should be used to enumerate the available Biometric devices. Each Biometric device implements the org.chromium.BiometricsDaemon.BiometricsManager interface, which is used to retrieve previously made records or to start an Enroll or Authenticate session. Enroll sessions are for making new records. Authenticate sessions are for authenticating scanned biometric data against those previously made records. Each session object is useful for ending the session, but signals still go through the BiometricsManager object to avoid a race condition between starting a session and connecting to the session's signals. Something to note about the session objects is that they will automatically be ended when the D-Bus client that created them (whomever called StartEnrollSession or StartAuthSession). This is to prevent the BiometricsManager from entering a stuck state in case the client crashes and nobody comes around to end the session. This shouldn't be an issue unless one expects the session to continue after the D-Bus client disconnects, for example while testing out biod using dbus-send or other single shot command line dbus tool. Each BiometricsManager can have only one session running concurrently.

The 'UINT32 scan_result' values are meant to be instructions to the user on how to get a better scan. They are as follows (Note: Pretty much ripped off from AOSP's fingerprint_acquired_info in fingerprint.h)
  • 0 = Success (the sensor captured good data)
  • 1 = Partial (sensor needs more data)
  • 2 = Insufficient (too little detail for recognition)
  • 3 = Sensor Dirty
  • 4 = Too Slow (tell user to speed up)
  • 5 = Too Fast (tell user to slow down)
  • 6 = Immobile (tell user to move a little to get more data)
Interfaces:     org.chromium.BiometricsDaemon.BiometricsManager
        Methods             StartEnrollSession(in STRING user_id, in STRING label, out OBJECTPATH enroll_session)
                The user_id refers to the sanitized user name returned by SanitizeUserName in libbrillo.
                The label is an arbitrary string chosen to be human readable by the user.
                The returned enroll object path implements the org.chromium.BiometricsDaemon.EnrollSession interface, but EnrollScanDone and SessionFailed signals still come from this BiometricsManager.             GetRecords(out ARRAY<OBJECTPATH> records)
                Each returned object path implements the org.chromium.BiometricsDaemon.Record interface.             DestroyAllRecords()             StartAuthSession(out OBJECTPATH auth_session)
                The returned object path implements the org.chromium.BiometricsDaemon.AuthSession interface, but AuthScanDone and SessionFailed signals still come from this BiometricsManager.         Signals             EnrollScanDone(UINT32 scan_result, BOOL complete)
                If complete is true, the enrollment was successfully finished and saved
            AuthScanDone(UINT32 scan_result, std::unordered_map<std::string, std::vector<std::string>> matches)
                The returned matches are a map from user id to a list of biometric record ids. The user ids are the same ones given to StartEnrollSession in previous enroll sessions. Each user in the list have one or more records that indicate a match. Note that a piece of biometric data could be registered multiple times under the same or different users.             SessionFailed()
                General failure of enroll session and/or authenticate session that can not be recovered from         Properties            UINT32 Type
                Type has one of the following values:
      • 0 = Unknown
      • 1 = Fingerprint
    org.chromium.BiometricsDaemon.AuthSession         Methods             End()
                Ends the authenticate session and destroys this object path. Generally, the client should call this at some point because authentication sessions do not end on their own, unless there is some error.
    org.chromium.BiometricsDaemon.EnrollSession         Methods             Cancel()
                Ends the enroll session without storing the enrollment and destroys this object path. Generally, the client should not call this as the Enroll session will end automatically once enough data is collected. Exceptions to this rule being that there was some error on the client side, the user explicitly canceled the session, or the client has determined the user to have given up, perhaps after some timeout has elapsed.
    org.chromium.BiometricsDaemon.Record         Methods            Remove()
                Deletes this record object from memory and persistent storage. It will no longer participate in any future Authenticate sessions.             SetLabel(in STRING label)
                Sets the human readable label of this Record object.         Properties             STRING Label
                Read only property that gets the previously set (by either StartEnrollSession or SetLabel) human readable label of this record object.

Example Usage
The symbol <- means chrome sends the command to org.chromium.BiometricsDaemon The symbol -> is either a response or a signal from org.chromium.BiometricsDaemon
1. Logged in user clicks enroll in UI:
<- Object:/org/chromium/BiometricsDaemon Method:org.freedesktop.DBus.ObjectManager.GetManagedObjects -> [         "/org/chromium/BiometricsDaemon/BiometricsManager0"     ] <- Object:/org/chromium/BiometricsDaemon/BiometricsManager0 Method:org.chromium.BiometricsDaemon.BiometricsManager.StartEnrollSession "<user id hash>" "Data 1" -> "/org/chromium/BiometricsDaemon/BiometricsManager0/EnrollSession"
2. User presses finger onto sensor
-> org.chromium.BiometricsDaemon.BiometricsManager.EnrollScanDone (Success) false

3. Chrome UI shows encouraging message about that scan to user 4. User presses finger again but too quickly
-> org.chromium.BiometricsDaemon.BiometricsManager.EnrollScanDone (Too Fast) false

5. Chrome UI shows a stern message about how the user's finger is too fast.
6. [...] Continued until biod determines there is enough data
-> org.chromium.BiometricsDaemon.BiometricsManager.EnrollScanDone (Success) true
7. Chrome displays successful enrollment message 8. Logged in user locks screen
<- Object:/org/chromium/BiometricsDaemon/BiometricsManager0 Method:org.chromium.BiometricsDaemon.BiometricsManager.StartAuthSession -> /org/chromium/BiometricsDaemon/BiometricsManager0/AuthSession
9. User does a scan with dirty sensor and lock screen informs the user of this
-> org.chromium.BiometricsDaemon.BiometricsManager.AuthScanDone (Sensor Dirty) [empty array]

10. User cleans sensor and tries again with success */
-> org.chromium.BiometricsDaemon.BiometricsManager.AuthScanDone (Success) ["unordered_map<string user_id, vector<string record_id>>"]
11. Lock screen lets user in
 

Comments