#223 Fingerprint auth integration test
Closed: Fixed 2 years ago by benzea. Opened 3 years ago by benzea.

Recent we had a number of issues with the authentication stack. Many of these are hard to find unless a full integration test is done.

Ideally, we would test the following scenarios:

  • Login without a (fingerprint) reader
  • Login with a reader, but no enrolled prints
  • Login using fingerprint
  • Password login after failed fingerprint login (broken as of 2020-03-29)

We can do so, using one of the virtual devices. In principle, this works by modifying fprintd.service (environment variable and relaxing the safeguards). After that, we can control the virtual device by writing to a socket.

Doing this means we can test the entire stack in one go (fprintd, pam, authselect configuration, gdm, gnome-shell).

Please ping me for details. The virtual device setup is simple and I can provide the relevant scripts.


Hello @benzea,

I would like to hear more about this, I might be able to create the testcase for testing it in OpenQA if you help me with the background, as I do not have any experience with fprintd.service and I do not have a fingerprint reader on any of my device.

You should only be aware that openQA does not enable using any hardware gadget (there is no way to put your finger on the reader), so you need to know a way how to simulate such behaviour programatically.

Let me know.

Metadata Update from @lruzicka:
- Issue assigned to lruzicka

2 years ago

You should only be aware that openQA does not enable using any hardware gadget (there is no way to put your finger on the reader), so you need to know a way how to simulate such behaviour programatically.

Yup, but we have that (I cannot guarantee that the emulation protocol will never break, but any necessary update will be simple) :-)

A small example, to test just GDM + login (i.e. not the enroll UI), we should not need much:

NOTE: Requires a libfprint update in F34, I should be doing that soon though! This is because current libfprint only has a virtual "image" device, but that is a lot less convenient for these tests.

First, we create a systemd drop-in:

[Service]
# Enable debugging output from fprintd
Environment=G_MESSAGES_DEBUG=all

# Allow access to /run and put socket there; we also need to disable SE
# linux enforcing!
Environment=FP_VIRTUAL_DEVICE=%t/fprintd-virt
ReadWritePaths=%t

# Disable USB (local testing with reader installed)
DevicePolicy=closed

We need to disable selinux with setenforce 0. Also, a systemctl daemon-reload and we should ensure fprintd is restarted systemctl restart fprintd.service just in case it was running. If GDM was already running, then it might be a good idea to restart it too.

To enroll a print, we can (run as root): fprintd-enroll USER

Each time we "scan" an virtual finger, we need to send something on the socket (which is only created once the reader is "active"). For that, we send an arbitrary string identifier for the finger we are scanning, e.g.: echo SCAN user-finger-1 | socat STDIN UNIX-CONNECT:/run/fprintd-virt. For enroll, this needs to be repeated a few times.

We can send a different ID like wrong-finger to test an authentication failure, ask for a retry using RETRY 1 (0: generic, 1: "too short", 2: "center finger", 3: "remove finger"; not sure what GDM shows for these) or even throw an error ERROR 0 (0: "generic", there are more, but not really relevant, I think).

I'll update this ticket once libfprint is updated in F34 and the virtual device is available. I have not fully verified tested the above, but am pretty sure it is accurate.

I see https://bodhi.fedoraproject.org/updates/FEDORA-2021-0787b217cf went through recently, but the description doesn't mention this. @benzea , does it have the necessary bits? Thanks!

No, these tests require libfprint 1.92.x. Which is no in rawhide, but not in F34.

I might push all this also into F34 eventually. But don't have a fixed timeframe for that as there are regression potentials.

EDIT: Sorry, I didn't follow the link and thought this was the F35 update for 1.92.0 libfprint.

OK, gotcha. I'll look at working on this just for Rawhide initially, then.

Metadata Update from @adamwill:
- Issue assigned to adamwill (was: lruzicka)
- Issue tagged with: newtest

2 years ago

So I'm trying to do this, but it's failing when I follow (I think) the advised procedure. When I run fprintd-enroll test on a console, after doing all the previous steps, it exits almost immediately - less than a second later - with Enroll result: enroll-unknown-error. The system logs show:

Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Requesting authorization from :1.284 to call method 'EnrollStart' for device 'Virtual device for debugging'
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Getting authorization to perform Polkit action net.reactivated.fprint.device.enroll
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Authorization granted to :1.284 to call method 'EnrollStart' for device 'Virtual device for debugging'!
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: file_storage_print_data_load(): loaded '/var/lib/fprint/adamw/virtual_device/0/7' Unknown error -2
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: start enrollment device 0 finger 7
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Failed to clear storage before first enrollment: Device has no storage.
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Device Virtual device for debugging does not support duplicate identification and so fprintd duplicate detection won't work
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Device reported finger status change: FP_FINGER_STATUS_NEEDED
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Finger present 0
Jul 23 15:27:05 xps13k.happyassassin.net fprintd[21140]: Finger needed 1
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: Device reported generic error (No commands arrived in time to run!) during action; action was: FPI_DEVICE_ACTION_ENROLL
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: Device reported enroll completion
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: Device reported finger status change: FP_FINGER_STATUS_NONE
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: Finger present 0
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: Finger needed 0
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: Completing action FPI_DEVICE_ACTION_ENROLL in idle!
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: enroll_cb: result enroll-unknown-error
Jul 23 15:27:06 xps13k.happyassassin.net fprintd[21140]: Device reported an error during enroll: No commands arrived in time to run!

(that's from a test on my own laptop, as you can see, but I see the same in the openQA environment). Did I miss something, or does fprintd-enroll give you a microscopically small window to actually scan a fingerprint? Thanks!

Hrm, yeah, the virtual reader has an internal timeout of 500ms. Which is not causing issues in the fprintd CI because it is doing the DBus calls itself, thereby making it easy to time everything appropriately.

I need to make some changes to the virtual device code. Maybe we can just remove the timeout (at least in most cases). For these kind of tests you really want to be able to send the command whenever everything else is ready.

yeah, it would be difficult to reliably time it to a 0.5s window in openQA, given how it works, unfortunately. If the timeout was say 10 secs it'd be easy.

First, there is an error. To disable the local USB device, you should use:

# Disable USB (local testing with reader installed)
DeviceAllow=

https://koji.fedoraproject.org/koji/taskinfo?taskID=72700721 will work now.

After starting the first command you can also do:

echo SET_KEEP_ALIVE 1 | socat STDIN UNIX-CONNECT:/run/fprintd-virt

That will cause the socket to remain open, enabling you to queue up commands in advance. You could e.g. do:

echo SLEEP 10 | socat STDIN UNIX-CONNECT:/run/fprintd-virt
echo SCAN benjamin-1 | socat STDIN UNIX-CONNECT:/run/fprintd-virt
echo SLEEP 10 | socat STDIN UNIX-CONNECT:/run/fprintd-virt
echo ERROR 0 | socat STDIN UNIX-CONNECT:/run/fprintd-virt

But, be warned. If you queue up commands like that you might need to send "CONT" commands in some cases. Not for SCAN, but for ERROR implicit commands that must happen (opening/closing the device) might receive the message as they would automatically succeed after the 500ms timeout.

Thanks! It's actually working so far with the original version of the config, but I'll change it anyway, unless that doesn't work. I'm just tweaking the logic and timing ATM. The new build with longer timeout for enrolment did the trick.

OK, so my latest sticking point...I've got this far:

  • Log in as user without a reader
  • Set up the reader, log out and log back in with reader but no fingerprints enrolled
  • Enrol a print
  • Log out and back in again with fingerprint enrolled

However, at that last re-login, it doesn't prompt me to swipe a finger, which I expected it would. I know the enrolment worked and it can prompt, because it actually does prompt me to swipe a finger sometimes at an "authorization required" that appears when switching between the desktop and a console (to send the 'swipe' commands).

Is it expected to prompt for a swipe on login?

OK, so I got this pretty much working and sent #246 . An example test run is at https://openqa.stg.fedoraproject.org/tests/1263662 .

Great stuff, I think this can be closed with #246 merged!

Thanks Adam!

Metadata Update from @benzea:
- Issue close_status updated to: Fixed
- Issue status updated to: Closed (was: Open)

2 years ago

No problem, thanks for the help and sorry it took a while!

Login to comment on this ticket.

Metadata