mirror of
https://gitlab.freedesktop.org/libfprint/libfprint.git
synced 2025-11-15 07:38:12 +00:00
Compare commits
53 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
a5ec0b30e1 | ||
|
|
29cf86a02e | ||
|
|
7892c943e6 | ||
|
|
a7d6b7c30a | ||
|
|
258ac2d4da | ||
|
|
31cf7a9383 | ||
|
|
f335256cbe | ||
|
|
c02cb3083d | ||
|
|
2084724115 | ||
|
|
59925d2027 | ||
|
|
118c610e29 | ||
|
|
313bfede77 | ||
|
|
c1da647aed | ||
|
|
22d204cc68 | ||
|
|
bc497f1b26 | ||
|
|
8c5f2e6434 | ||
|
|
5b20892dd4 | ||
|
|
b2a53a459c | ||
|
|
45ac0eefb0 | ||
|
|
ea6d5ba6d6 | ||
|
|
ed2c75842a | ||
|
|
b307dd1a6a | ||
|
|
39902374ce | ||
|
|
9e92d4cf2c | ||
|
|
6b84c6664f | ||
|
|
f569d0bf44 | ||
|
|
1cfd14b7fe | ||
|
|
5d32102efe | ||
|
|
9e10edd422 | ||
|
|
fecf6d6fe5 | ||
|
|
e32fa8cc38 | ||
|
|
d8aae30a67 | ||
|
|
84b97ea15b | ||
|
|
8f98743857 | ||
|
|
be29f27e25 | ||
|
|
d003f08855 | ||
|
|
0f7ad00fc4 | ||
|
|
83333bce3f | ||
|
|
132b178304 | ||
|
|
c3689665db | ||
|
|
3d222ddda7 | ||
|
|
080c414ce9 | ||
|
|
ff02115b0f | ||
|
|
3b409c767c | ||
|
|
d05c69698c | ||
|
|
2d09b10a27 | ||
|
|
bc03d56186 | ||
|
|
96e7224a23 | ||
|
|
0f4a75ff61 | ||
|
|
dfff16f3e3 | ||
|
|
3d2e545264 | ||
|
|
c96fa32da4 | ||
|
|
48ec64f683 |
2
AUTHORS
2
AUTHORS
@@ -4,7 +4,7 @@ Copyright (C) 2006 Pavel Machek <pavel@suse.cz>
|
||||
Copyright (C) 1999 Erik Walthinsen <omega@cse.ogi.edu>
|
||||
Copyright (C) 2004,2006 Thomas Vander Stichele <thomas at apestaart dot org>
|
||||
Copyright (C) 2007 Cyrille Bagard
|
||||
Copyright (C) 2007 Vasily Khoruzhick
|
||||
Copyright (C) 2007-2008,2012 Vasily Khoruzhick <anarsoul@gmail.com>
|
||||
Copyright (C) 2007 Jan-Michael Brummer <buzz2@gmx.de>
|
||||
Copyright (C) 2007 Anthony Bretaudeau <wxcover@users.sourceforge.net>
|
||||
Copyright (C) 2010 Hugo Grostabussiat <dw23.devel@gmail.com>
|
||||
|
||||
6
HACKING
6
HACKING
@@ -85,11 +85,11 @@ be reflected by updating the appropriate doxygen comments.
|
||||
Contributing
|
||||
============
|
||||
|
||||
Patches should be sent to the fprint mailing list detailed on the website.
|
||||
A subscription is required.
|
||||
Patches should be sent to the fprint bugzilla:
|
||||
https://bugs.freedesktop.org/enter_bug.cgi?product=libfprint
|
||||
|
||||
Information about libfprint development repositories can be found here:
|
||||
http://www.reactivated.net/fprint/Libfprint_development
|
||||
http://www.freedesktop.org/wiki/Software/fprint/libfprint
|
||||
|
||||
If you're looking for ideas for things to work on, look at the TODO file or
|
||||
grep the source code for FIXMEs.
|
||||
|
||||
@@ -1,4 +1,3 @@
|
||||
AUTOMAKE_OPTIONS = dist-bzip2
|
||||
ACLOCAL_AMFLAGS = -I m4
|
||||
EXTRA_DIST = THANKS TODO HACKING libfprint.pc.in
|
||||
DISTCLEANFILES = ChangeLog libfprint.pc
|
||||
@@ -9,6 +8,10 @@ if BUILD_EXAMPLES
|
||||
SUBDIRS += examples
|
||||
endif
|
||||
|
||||
DIST_SUBDIRS = libfprint doc examples
|
||||
|
||||
DISTCHECK_CONFIGURE_FLAGS = --with-drivers=all --enable-examples-build --enable-x11-examples-build --with-udev-rules-dir='$${libdir}/udev/rules.d-distcheck'
|
||||
|
||||
pkgconfigdir=$(libdir)/pkgconfig
|
||||
pkgconfig_DATA=libfprint.pc
|
||||
|
||||
|
||||
25
NEWS
25
NEWS
@@ -1,6 +1,31 @@
|
||||
This file lists notable changes in each release. For the full history of all
|
||||
changes, see ChangeLog.
|
||||
|
||||
2012-12-03: v0.5.0 release
|
||||
|
||||
* Drivers:
|
||||
- New VFS300/VFS301 driver
|
||||
- New AES2550/AES2810 drivers
|
||||
- New AES1660 driver
|
||||
- New AES2660 driver
|
||||
- New DigitalPersona URU4500 driver
|
||||
- Avoid empty capture and improve image contrast in the
|
||||
AES2501 and AES2550 drivers
|
||||
- Update upektc driver, add support for Eikon Touch 300
|
||||
- Fix UrU4000 image capture on ARM
|
||||
|
||||
* Library:
|
||||
- Fix global variable collisions with libusb and other system headers
|
||||
- Fix possible crash in NBIS image processing with some fingerprints
|
||||
|
||||
* Udev rules:
|
||||
- Fix power control path for newer kernels
|
||||
- Move udev rules to the correct directory
|
||||
- Don't print duplicated udev rules
|
||||
- Include udev rules in the tarball
|
||||
- Allow disabling of udev rules for cross-compiling
|
||||
- Add driver names in the generated rules
|
||||
|
||||
2011-04-18: v0.4.0 release
|
||||
* Add support for Validity VFS101 (USB ID 138a:0001)
|
||||
* Fix crasher when resizing a fingerprint image
|
||||
|
||||
1
THANKS
1
THANKS
@@ -8,3 +8,4 @@ Toby Howard (University of Manchester)
|
||||
Seemant Kulleen
|
||||
Pavel Herrman
|
||||
Bastien Nocera
|
||||
Greg Kerr and Martin Konecny from AuthenTec Inc - hardware donations (AES2550 device), datasheets for AES2550 and AES2810
|
||||
|
||||
@@ -4,5 +4,7 @@ aclocal || exit 1
|
||||
autoheader || exit 1
|
||||
autoconf || exit 1
|
||||
automake -a -c || exit 1
|
||||
./configure --enable-maintainer-mode --enable-examples-build \
|
||||
if test -z "$NOCONFIGURE"; then
|
||||
exec ./configure --enable-maintainer-mode --enable-examples-build \
|
||||
--enable-x11-examples-build --enable-debug-log $*
|
||||
fi
|
||||
|
||||
102
configure.ac
102
configure.ac
@@ -1,5 +1,5 @@
|
||||
AC_INIT([libfprint], [0.4.0])
|
||||
AM_INIT_AUTOMAKE([1.11 dist-bzip2 no-dist-gzip check-news])
|
||||
AC_INIT([libfprint], [0.5.0])
|
||||
AM_INIT_AUTOMAKE([1.11 no-dist-gzip dist-xz check-news])
|
||||
AC_CONFIG_MACRO_DIR([m4])
|
||||
AC_CONFIG_SRCDIR([libfprint/core.c])
|
||||
AM_CONFIG_HEADER([config.h])
|
||||
@@ -23,10 +23,11 @@ AC_SUBST(lt_major)
|
||||
AC_SUBST(lt_revision)
|
||||
AC_SUBST(lt_age)
|
||||
|
||||
all_drivers="upeke2 upekts upektc upeksonly vcom5s uru4000 fdu2000 aes1610 aes2501 aes4000 vfs101"
|
||||
all_drivers="upeke2 upekts upektc upeksonly vcom5s uru4000 fdu2000 aes1610 aes1660 aes2501 aes2550 aes2660 aes4000 vfs101 vfs301"
|
||||
|
||||
require_imaging='no'
|
||||
require_aeslib='no'
|
||||
require_aesX660='no'
|
||||
enable_upeke2='no'
|
||||
enable_upekts='no'
|
||||
enable_upektc='no'
|
||||
@@ -35,15 +36,23 @@ enable_vcom5s='no'
|
||||
enable_uru4000='no'
|
||||
enable_fdu2000='no'
|
||||
enable_aes1610='no'
|
||||
enable_aes1660='no'
|
||||
enable_aes2501='no'
|
||||
enable_aes2550='no'
|
||||
enable_aes2660='no'
|
||||
enable_aes4000='no'
|
||||
enable_vfs101='no'
|
||||
enable_vfs301='no'
|
||||
|
||||
AC_ARG_WITH([drivers],[AS_HELP_STRING([--with-drivers],
|
||||
[List of drivers to enable])],
|
||||
[drivers="$withval"],
|
||||
[drivers="$all_drivers"])
|
||||
|
||||
if test "x$drivers" = "xall" ; then
|
||||
drivers=$all_drivers
|
||||
fi
|
||||
|
||||
for driver in `echo ${drivers} | sed -e 's/,/ /g' -e 's/,$//g'`; do
|
||||
case ${driver} in
|
||||
upekts)
|
||||
@@ -56,8 +65,7 @@ for driver in `echo ${drivers} | sed -e 's/,/ /g' -e 's/,$//g'`; do
|
||||
;;
|
||||
upektc)
|
||||
AC_DEFINE([ENABLE_UPEKTC], [], [Build UPEK TouchChip driver])
|
||||
enable_upektc="no"
|
||||
# Driver not ported
|
||||
enable_upektc="yes"
|
||||
;;
|
||||
upeksonly)
|
||||
AC_DEFINE([ENABLE_UPEKSONLY], [], [Build UPEK TouchStrip sensor-only driver])
|
||||
@@ -81,11 +89,28 @@ for driver in `echo ${drivers} | sed -e 's/,/ /g' -e 's/,$//g'`; do
|
||||
require_aeslib="yes"
|
||||
enable_aes2501="yes"
|
||||
;;
|
||||
aes2550)
|
||||
AC_DEFINE([ENABLE_AES2550], [], [Build AuthenTec AES2550/AES2810 driver])
|
||||
require_aeslib="yes"
|
||||
enable_aes2550="yes"
|
||||
;;
|
||||
aes1610)
|
||||
AC_DEFINE([ENABLE_AES1610], [], [Build AuthenTec AES1610 driver])
|
||||
require_aeslib="yes"
|
||||
enable_aes1610="yes"
|
||||
;;
|
||||
aes1660)
|
||||
AC_DEFINE([ENABLE_AES1660], [], [Build AuthenTec AES1660 driver])
|
||||
require_aeslib="yes"
|
||||
require_aesX660="yes"
|
||||
enable_aes1660="yes"
|
||||
;;
|
||||
aes2660)
|
||||
AC_DEFINE([ENABLE_AES2660], [], [Build AuthenTec AES1660 driver])
|
||||
require_aeslib="yes"
|
||||
require_aesX660="yes"
|
||||
enable_aes2660="yes"
|
||||
;;
|
||||
aes4000)
|
||||
AC_DEFINE([ENABLE_AES4000], [], [Build AuthenTec AES4000 driver])
|
||||
require_aeslib="yes"
|
||||
@@ -96,21 +121,30 @@ for driver in `echo ${drivers} | sed -e 's/,/ /g' -e 's/,$//g'`; do
|
||||
AC_DEFINE([ENABLE_VFS101], [], [Build Validity VFS101 driver])
|
||||
enable_vfs101="yes"
|
||||
;;
|
||||
vfs301)
|
||||
AC_DEFINE([ENABLE_VFS301], [], [Build Validity VFS301/VFS300 driver])
|
||||
enable_vfs301="yes"
|
||||
;;
|
||||
esac
|
||||
done
|
||||
|
||||
AM_CONDITIONAL([ENABLE_UPEKTS], [test "$enable_upekts" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_UPEKE2], [test "$enable_upeke2" = "yes"])
|
||||
#AM_CONDITIONAL([ENABLE_UPEKTC], [test "$enable_upektc" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_UPEKTC], [test "$enable_upektc" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_UPEKSONLY], [test "$enable_upeksonly" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_VCOM5S], [test "$enable_vcom5s" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_URU4000], [test "$enable_uru4000" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_FDU2000], [test "$enable_fdu2000" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_AES1610], [test "$enable_aes1610" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_AES1660], [test "$enable_aes1660" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_AES2501], [test "$enable_aes2501" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_AES2550], [test "$enable_aes2550" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_AES2660], [test "$enable_aes2660" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_AES4000], [test "$enable_aes4000" = "yes"])
|
||||
AM_CONDITIONAL([REQUIRE_AESLIB], [test "$require_aeslib" = "yes"])
|
||||
AM_CONDITIONAL([REQUIRE_AESX660], [test "$require_aesX660" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_VFS101], [test "$enable_vfs101" = "yes"])
|
||||
AM_CONDITIONAL([ENABLE_VFS301], [test "$enable_vfs301" = "yes"])
|
||||
|
||||
|
||||
PKG_CHECK_MODULES(LIBUSB, [libusb-1.0 >= 0.9.1])
|
||||
@@ -129,6 +163,27 @@ AC_SUBST(GLIB_LIBS)
|
||||
imagemagick_found=no
|
||||
gdkpixbuf_found=no
|
||||
|
||||
AC_ARG_ENABLE(udev-rules,
|
||||
AC_HELP_STRING([--enable-udev-rules],[Update the udev rules]),
|
||||
[case "${enableval}" in
|
||||
yes) ENABLE_UDEV_RULES=yes ;;
|
||||
no) ENABLE_UDEV_RULES=no ;;
|
||||
*) AC_MSG_ERROR(bad value ${enableval} for --enable-udev-rules) ;;
|
||||
esac],
|
||||
[ENABLE_UDEV_RULES=yes]) dnl Default value
|
||||
AM_CONDITIONAL(ENABLE_UDEV_RULES, test x$ENABLE_UDEV_RULES = "xyes")
|
||||
|
||||
AC_ARG_WITH(udev-rules-dir,
|
||||
AS_HELP_STRING([--with-udev-rules-dir=DIR],[Installation path for udev rules @<:@auto@:>@]),
|
||||
[ac_with_udev_rules_dir=$withval],
|
||||
[ac_with_udev_rules_dir=""])
|
||||
|
||||
if test "${ac_with_udev_rules_dir}" = ""; then
|
||||
ac_with_udev_rules_dir=`$PKG_CONFIG --variable=udevdir udev`/rules.d
|
||||
fi
|
||||
AC_MSG_NOTICE([installing udev rules in ${ac_with_udev_rules_dir}])
|
||||
AC_SUBST([udev_rulesdir],[${ac_with_udev_rules_dir}])
|
||||
|
||||
if test "$require_imaging" = "yes"; then
|
||||
PKG_CHECK_MODULES(IMAGING, gthread-2.0 gdk-pixbuf-2.0, [gdkpixbuf_found=yes], [gdkpixbuf_found=no])
|
||||
if test "$gdkpixbuf_found" != "yes"; then
|
||||
@@ -171,17 +226,17 @@ if test "x$build_x11_examples" != "xno"; then
|
||||
AC_MSG_CHECKING(for Xv extensions)
|
||||
AC_TRY_COMPILE([
|
||||
#include <X11/Xlib.h>
|
||||
#include <X11/extensions/Xvlib.h>],[
|
||||
#include <X11/extensions/Xvlib.h>],[
|
||||
int main(void) { (void) XvGetPortAttribute(0, 0, 0, 0); return 0; }
|
||||
],xv=yes,xv=no);
|
||||
AC_MSG_RESULT($xv)
|
||||
if test x$xv = xyes; then
|
||||
XV_LIBS="-lXv -lXext"
|
||||
XV_CFLAGS=""
|
||||
if test x$xv = xyes; then
|
||||
XV_LIBS="-lXv -lXext"
|
||||
XV_CFLAGS=""
|
||||
AC_DEFINE(HAVE_XV,1,[defined if XV video overlay is available])
|
||||
else
|
||||
AC_MSG_ERROR([XV is required for X11 examples])
|
||||
fi
|
||||
fi
|
||||
])
|
||||
AC_CHECK_XV
|
||||
fi
|
||||
@@ -262,11 +317,26 @@ if test x$enable_aes1610 != xno ; then
|
||||
else
|
||||
AC_MSG_NOTICE([ aes1610 driver disabled])
|
||||
fi
|
||||
if test x$enable_aes1660 != xno ; then
|
||||
AC_MSG_NOTICE([** aes1660 driver enabled])
|
||||
else
|
||||
AC_MSG_NOTICE([ aes1660 driver disabled])
|
||||
fi
|
||||
if test x$enable_aes2501 != xno ; then
|
||||
AC_MSG_NOTICE([** aes2501 driver enabled])
|
||||
else
|
||||
AC_MSG_NOTICE([ aes2501 driver disabled])
|
||||
fi
|
||||
if test x$enable_aes2550 != xno ; then
|
||||
AC_MSG_NOTICE([** aes2550/aes2810 driver enabled])
|
||||
else
|
||||
AC_MSG_NOTICE([ aes2550/aes2810 driver disabled])
|
||||
fi
|
||||
if test x$enable_aes2660 != xno ; then
|
||||
AC_MSG_NOTICE([** aes2660 driver enabled])
|
||||
else
|
||||
AC_MSG_NOTICE([ aes2660 driver disabled])
|
||||
fi
|
||||
if test x$enable_aes4000 != xno ; then
|
||||
AC_MSG_NOTICE([** aes4000 driver enabled])
|
||||
else
|
||||
@@ -277,11 +347,21 @@ if test x$enable_vfs101 != xno ; then
|
||||
else
|
||||
AC_MSG_NOTICE([ vfs101 driver disabled])
|
||||
fi
|
||||
if test x$enable_vfs301 != xno ; then
|
||||
AC_MSG_NOTICE([** vfs301 driver enabled])
|
||||
else
|
||||
AC_MSG_NOTICE([ vfs301 driver disabled])
|
||||
fi
|
||||
if test x$require_aeslib != xno ; then
|
||||
AC_MSG_NOTICE([** aeslib helper functions enabled])
|
||||
else
|
||||
AC_MSG_NOTICE([ aeslib helper functions disabled])
|
||||
fi
|
||||
if test x$require_aesX660 != xno ; then
|
||||
AC_MSG_NOTICE([** aesX660 common routines enabled])
|
||||
else
|
||||
AC_MSG_NOTICE([ aesX660 common routines disabled])
|
||||
fi
|
||||
|
||||
AC_CONFIG_FILES([libfprint.pc] [Makefile] [libfprint/Makefile] [examples/Makefile] [doc/Makefile])
|
||||
AC_OUTPUT
|
||||
|
||||
@@ -29,7 +29,7 @@
|
||||
#define FORMAT 0x32595559
|
||||
|
||||
static int adaptor = -1;
|
||||
static unsigned char *framebuffer = NULL;
|
||||
static char *framebuffer = NULL;
|
||||
|
||||
static Display *display = NULL;
|
||||
static Window window=(Window)NULL;
|
||||
@@ -50,7 +50,7 @@ static int connection = -1;
|
||||
u = u > 255 ? 255 : u;\
|
||||
v = v > 255 ? 255 : v
|
||||
|
||||
static void grey2yuy2 (unsigned char *grey, unsigned char *YUV, int num) {
|
||||
static void grey2yuy2 (unsigned char *grey, char *YUV, int num) {
|
||||
int i, j;
|
||||
int y0, y1, u0, u1, v0, v1;
|
||||
int gval;
|
||||
@@ -86,7 +86,7 @@ static void display_frame(struct fp_img *img)
|
||||
|
||||
static void QueryXv()
|
||||
{
|
||||
int num_adaptors;
|
||||
unsigned int num_adaptors;
|
||||
int num_formats;
|
||||
XvImageFormatValues *formats = NULL;
|
||||
int i,j;
|
||||
|
||||
@@ -4,15 +4,19 @@ MOSTLYCLEANFILES = $(udev_rules_DATA)
|
||||
|
||||
UPEKE2_SRC = drivers/upeke2.c
|
||||
UPEKTS_SRC = drivers/upekts.c
|
||||
UPEKTC_SRC = drivers/upektc.c
|
||||
UPEKTC_SRC = drivers/upektc.c drivers/upektc.h
|
||||
UPEKSONLY_SRC = drivers/upeksonly.c
|
||||
URU4000_SRC = drivers/uru4000.c
|
||||
AES1610_SRC = drivers/aes1610.c
|
||||
AES1660_SRC = drivers/aes1660.c drivers/aes1660.h
|
||||
AES2501_SRC = drivers/aes2501.c drivers/aes2501.h
|
||||
AES2550_SRC = drivers/aes2550.c drivers/aes2550.h
|
||||
AES2660_SRC = drivers/aes2660.c drivers/aes2660.h
|
||||
AES4000_SRC = drivers/aes4000.c
|
||||
FDU2000_SRC = drivers/fdu2000.c
|
||||
VCOM5S_SRC = drivers/vcom5s.c
|
||||
VFS101_SRC = drivers/vfs101.c
|
||||
VFS301_SRC = drivers/vfs301.c drivers/vfs301_proto.c drivers/vfs301_proto.h drivers/vfs301_proto_fragments.h
|
||||
|
||||
EXTRA_DIST = \
|
||||
$(UPEKE2_SRC) \
|
||||
@@ -21,14 +25,22 @@ EXTRA_DIST = \
|
||||
$(UPEKSONLY_SRC) \
|
||||
$(URU4000_SRC) \
|
||||
$(AES1610_SRC) \
|
||||
$(AES1660_SRC) \
|
||||
$(AES2501_SRC) \
|
||||
$(AES2550_SRC) \
|
||||
$(AES2660_SRC) \
|
||||
$(AES4000_SRC) \
|
||||
$(FDU2000_SRC) \
|
||||
$(VCOM5S_SRC) \
|
||||
$(VFS101_SRC) \
|
||||
$(VFS301_SRC) \
|
||||
drivers/aesx660.c \
|
||||
drivers/aesx660.h \
|
||||
drivers/driver_ids.h \
|
||||
aeslib.c aeslib.h \
|
||||
imagemagick.c \
|
||||
gdkpixbuf.c
|
||||
gdkpixbuf.c \
|
||||
60-fprint-autosuspend.rules
|
||||
|
||||
DRIVER_SRC =
|
||||
OTHER_SRC =
|
||||
@@ -79,10 +91,11 @@ fprint_list_udev_rules_CFLAGS = -fvisibility=hidden -I$(srcdir)/nbis/include $(L
|
||||
fprint_list_udev_rules_LDADD = $(builddir)/libfprint.la
|
||||
|
||||
udev_rules_DATA = 60-fprint-autosuspend.rules
|
||||
udev_rulesdir = $(sysconfdir)/udev/rules.d/
|
||||
|
||||
if ENABLE_UDEV_RULES
|
||||
$(udev_rules_DATA): fprint-list-udev-rules
|
||||
$(builddir)/fprint-list-udev-rules > $@
|
||||
endif
|
||||
|
||||
if ENABLE_UPEKE2
|
||||
DRIVER_SRC += $(UPEKE2_SRC)
|
||||
@@ -96,9 +109,9 @@ if ENABLE_UPEKSONLY
|
||||
DRIVER_SRC += $(UPEKSONLY_SRC)
|
||||
endif
|
||||
|
||||
#if ENABLE_UPEKTC
|
||||
#DRIVER_SRC += $(UPEKTC_SRC)
|
||||
#endif
|
||||
if ENABLE_UPEKTC
|
||||
DRIVER_SRC += $(UPEKTC_SRC)
|
||||
endif
|
||||
|
||||
if ENABLE_URU4000
|
||||
DRIVER_SRC += $(URU4000_SRC)
|
||||
@@ -116,10 +129,22 @@ if ENABLE_AES1610
|
||||
DRIVER_SRC += $(AES1610_SRC)
|
||||
endif
|
||||
|
||||
if ENABLE_AES1660
|
||||
DRIVER_SRC += $(AES1660_SRC)
|
||||
endif
|
||||
|
||||
if ENABLE_AES2501
|
||||
DRIVER_SRC += $(AES2501_SRC)
|
||||
endif
|
||||
|
||||
if ENABLE_AES2550
|
||||
DRIVER_SRC += $(AES2550_SRC)
|
||||
endif
|
||||
|
||||
if ENABLE_AES2660
|
||||
DRIVER_SRC += $(AES2660_SRC)
|
||||
endif
|
||||
|
||||
if ENABLE_AES4000
|
||||
DRIVER_SRC += $(AES4000_SRC)
|
||||
endif
|
||||
@@ -128,6 +153,10 @@ if ENABLE_VFS101
|
||||
DRIVER_SRC += $(VFS101_SRC)
|
||||
endif
|
||||
|
||||
if ENABLE_VFS301
|
||||
DRIVER_SRC += $(VFS301_SRC)
|
||||
endif
|
||||
|
||||
if REQUIRE_IMAGEMAGICK
|
||||
OTHER_SRC += imagemagick.c
|
||||
libfprint_la_CFLAGS += $(IMAGING_CFLAGS)
|
||||
@@ -144,6 +173,10 @@ if REQUIRE_AESLIB
|
||||
OTHER_SRC += aeslib.c aeslib.h
|
||||
endif
|
||||
|
||||
if REQUIRE_AESX660
|
||||
OTHER_SRC += drivers/aesx660.c drivers/aesx660.h
|
||||
endif
|
||||
|
||||
libfprint_la_SOURCES = \
|
||||
fp_internal.h \
|
||||
async.c \
|
||||
|
||||
@@ -20,6 +20,7 @@
|
||||
#define FP_COMPONENT "aeslib"
|
||||
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
|
||||
#include <libusb.h>
|
||||
#include <glib.h>
|
||||
@@ -164,10 +165,120 @@ void aes_assemble_image(unsigned char *input, size_t width, size_t height,
|
||||
|
||||
for (column = 0; column < width; column++) {
|
||||
for (row = 0; row < height; row += 2) {
|
||||
output[width * row + column] = (*input & 0x07) * 36;
|
||||
output[width * (row + 1) + column] = ((*input & 0x70) >> 4) * 36;
|
||||
output[width * row + column] = (*input & 0x0f) * 17;
|
||||
output[width * (row + 1) + column] = ((*input & 0xf0) >> 4) * 17;
|
||||
input++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* find overlapping parts of frames */
|
||||
static unsigned int find_overlap(unsigned char *first_frame,
|
||||
unsigned char *second_frame, unsigned int *min_error,
|
||||
unsigned int frame_width, unsigned int frame_height)
|
||||
{
|
||||
unsigned int dy;
|
||||
unsigned int not_overlapped_height = 0;
|
||||
/* 255 is highest brightness value for an 8bpp image */
|
||||
*min_error = 255 * frame_width * frame_height;
|
||||
for (dy = 0; dy < frame_height; dy++) {
|
||||
/* Calculating difference (error) between parts of frames */
|
||||
unsigned int i;
|
||||
unsigned int error = 0;
|
||||
for (i = 0; i < frame_width * (frame_height - dy); i++) {
|
||||
/* Using ? operator to avoid abs function */
|
||||
error += first_frame[i] > second_frame[i] ?
|
||||
(first_frame[i] - second_frame[i]) :
|
||||
(second_frame[i] - first_frame[i]);
|
||||
}
|
||||
|
||||
/* Normalize error */
|
||||
error *= 15;
|
||||
error /= i;
|
||||
if (error < *min_error) {
|
||||
*min_error = error;
|
||||
not_overlapped_height = dy;
|
||||
}
|
||||
first_frame += frame_width;
|
||||
}
|
||||
|
||||
return not_overlapped_height;
|
||||
}
|
||||
|
||||
/* assemble a series of frames into a single image */
|
||||
static unsigned int assemble(GSList *list_entry, size_t num_stripes,
|
||||
unsigned int frame_width, unsigned int frame_height,
|
||||
unsigned char *output, gboolean reverse, unsigned int *errors_sum)
|
||||
{
|
||||
uint8_t *assembled = output;
|
||||
int frame;
|
||||
uint32_t image_height = frame_height;
|
||||
unsigned int min_error, frame_size = frame_width * frame_height;
|
||||
*errors_sum = 0;
|
||||
|
||||
if (reverse)
|
||||
output += (num_stripes - 1) * frame_size;
|
||||
for (frame = 0; frame < num_stripes; frame++) {
|
||||
aes_assemble_image(list_entry->data, frame_width, frame_height, output);
|
||||
|
||||
if (reverse)
|
||||
output -= frame_size;
|
||||
else
|
||||
output += frame_size;
|
||||
list_entry = g_slist_next(list_entry);
|
||||
}
|
||||
|
||||
/* Detecting where frames overlaped */
|
||||
output = assembled;
|
||||
for (frame = 1; frame < num_stripes; frame++) {
|
||||
int not_overlapped;
|
||||
|
||||
output += frame_size;
|
||||
not_overlapped = find_overlap(assembled, output, &min_error,
|
||||
frame_width, frame_height);
|
||||
*errors_sum += min_error;
|
||||
image_height += not_overlapped;
|
||||
assembled += frame_width * not_overlapped;
|
||||
memcpy(assembled, output, frame_size);
|
||||
}
|
||||
return image_height;
|
||||
}
|
||||
|
||||
struct fp_img *aes_assemble(GSList *stripes, size_t stripes_len,
|
||||
unsigned int frame_width, unsigned int frame_height)
|
||||
{
|
||||
size_t final_size;
|
||||
struct fp_img *img;
|
||||
unsigned int frame_size = frame_width * frame_height;
|
||||
unsigned int errors_sum, r_errors_sum;
|
||||
|
||||
BUG_ON(stripes_len == 0);
|
||||
|
||||
/* create buffer big enough for max image */
|
||||
img = fpi_img_new(stripes_len * frame_size);
|
||||
|
||||
img->flags = FP_IMG_COLORS_INVERTED;
|
||||
img->height = assemble(stripes, stripes_len,
|
||||
frame_width, frame_height,
|
||||
img->data, FALSE, &errors_sum);
|
||||
img->height = assemble(stripes, stripes_len,
|
||||
frame_width, frame_height,
|
||||
img->data, TRUE, &r_errors_sum);
|
||||
|
||||
if (r_errors_sum > errors_sum) {
|
||||
img->height = assemble(stripes, stripes_len,
|
||||
frame_width, frame_height,
|
||||
img->data, FALSE, &errors_sum);
|
||||
img->flags |= FP_IMG_V_FLIPPED | FP_IMG_H_FLIPPED;
|
||||
fp_dbg("normal scan direction");
|
||||
} else {
|
||||
fp_dbg("reversed scan direction");
|
||||
}
|
||||
|
||||
/* now that overlap has been removed, resize output image buffer */
|
||||
final_size = img->height * frame_width;
|
||||
img = fpi_img_resize(img, final_size);
|
||||
img->width = frame_width;
|
||||
|
||||
return img;
|
||||
}
|
||||
|
||||
@@ -36,5 +36,8 @@ void aes_write_regv(struct fp_img_dev *dev, const struct aes_regwrite *regs,
|
||||
void aes_assemble_image(unsigned char *input, size_t width, size_t height,
|
||||
unsigned char *output);
|
||||
|
||||
struct fp_img *aes_assemble(GSList *stripes, size_t stripes_len,
|
||||
unsigned int frame_width, unsigned int frame_height);
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
@@ -291,25 +291,25 @@ void fpi_log(enum fpi_log_level level, const char *component,
|
||||
#ifndef ENABLE_DEBUG_LOGGING
|
||||
if (!log_level)
|
||||
return;
|
||||
if (level == LOG_LEVEL_WARNING && log_level < 2)
|
||||
if (level == FPRINT_LOG_LEVEL_WARNING && log_level < 2)
|
||||
return;
|
||||
if (level == LOG_LEVEL_INFO && log_level < 3)
|
||||
if (level == FPRINT_LOG_LEVEL_INFO && log_level < 3)
|
||||
return;
|
||||
#endif
|
||||
|
||||
switch (level) {
|
||||
case LOG_LEVEL_INFO:
|
||||
case FPRINT_LOG_LEVEL_INFO:
|
||||
prefix = "info";
|
||||
break;
|
||||
case LOG_LEVEL_WARNING:
|
||||
case FPRINT_LOG_LEVEL_WARNING:
|
||||
stream = stderr;
|
||||
prefix = "warning";
|
||||
break;
|
||||
case LOG_LEVEL_ERROR:
|
||||
case FPRINT_LOG_LEVEL_ERROR:
|
||||
stream = stderr;
|
||||
prefix = "error";
|
||||
break;
|
||||
case LOG_LEVEL_DEBUG:
|
||||
case FPRINT_LOG_LEVEL_DEBUG:
|
||||
stream = stderr;
|
||||
prefix = "debug";
|
||||
break;
|
||||
@@ -355,6 +355,9 @@ static struct fp_img_driver * const img_drivers[] = {
|
||||
#ifdef ENABLE_AES2501
|
||||
&aes2501_driver,
|
||||
#endif
|
||||
#ifdef ENABLE_AES2550
|
||||
&aes2550_driver,
|
||||
#endif
|
||||
#ifdef ENABLE_URU4000
|
||||
&uru4000_driver,
|
||||
#endif
|
||||
@@ -368,13 +371,22 @@ static struct fp_img_driver * const img_drivers[] = {
|
||||
#ifdef ENABLE_AES1610
|
||||
&aes1610_driver,
|
||||
#endif
|
||||
#ifdef ENABLE_AES1660
|
||||
&aes1660_driver,
|
||||
#endif
|
||||
#ifdef ENABLE_AES2660
|
||||
&aes2660_driver,
|
||||
#endif
|
||||
#ifdef ENABLE_VFS101
|
||||
&vfs101_driver,
|
||||
#endif
|
||||
/*#ifdef ENABLE_UPEKTC
|
||||
#ifdef ENABLE_VFS301
|
||||
&vfs301_driver,
|
||||
#endif
|
||||
#ifdef ENABLE_UPEKTC
|
||||
&upektc_driver,
|
||||
#endif
|
||||
#ifdef ENABLE_FDU2000
|
||||
/*#ifdef ENABLE_FDU2000
|
||||
&fdu2000_driver,
|
||||
#endif
|
||||
*/
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
* Copyright (C) 2007 Cyrille Bagard
|
||||
* Copyright (C) 2007 Vasily Khoruzhick
|
||||
* Copyright (C) 2009 Guido Grazioli <guido.grazioli@gmail.com>
|
||||
* Copyright (C) 2012 Vasily Khoruzhick <anarsoul@gmail.com>
|
||||
*
|
||||
* Based on code from libfprint aes2501 driver.
|
||||
*
|
||||
@@ -32,6 +33,8 @@
|
||||
#include <aeslib.h>
|
||||
#include <fp_internal.h>
|
||||
|
||||
#include "driver_ids.h"
|
||||
|
||||
static void start_capture(struct fp_img_dev *dev);
|
||||
static void complete_deactivation(struct fp_img_dev *dev);
|
||||
static int adjust_gain(unsigned char *buffer, int status);
|
||||
@@ -110,103 +113,6 @@ static void generic_ignore_data_cb(struct libusb_transfer *transfer)
|
||||
libusb_free_transfer(transfer);
|
||||
}
|
||||
|
||||
|
||||
static void read_regs_data_cb(struct libusb_transfer *transfer)
|
||||
{
|
||||
struct aes1610_read_regs *rdata = transfer->user_data;
|
||||
unsigned char *retdata = NULL;
|
||||
int r;
|
||||
|
||||
if (transfer->status != LIBUSB_TRANSFER_COMPLETED) {
|
||||
r = -EIO;
|
||||
} else if (transfer->length != transfer->actual_length) {
|
||||
r = -EPROTO;
|
||||
} else {
|
||||
r = 0;
|
||||
retdata = transfer->buffer;
|
||||
}
|
||||
|
||||
rdata->callback(rdata->dev, r, retdata, rdata->user_data);
|
||||
g_free(rdata);
|
||||
g_free(transfer->buffer);
|
||||
libusb_free_transfer(transfer);
|
||||
}
|
||||
|
||||
static void read_regs_rq_cb(struct fp_img_dev *dev, int result, void *user_data)
|
||||
{
|
||||
struct aes1610_read_regs *rdata = user_data;
|
||||
struct libusb_transfer *transfer;
|
||||
unsigned char *data;
|
||||
int r;
|
||||
|
||||
g_free(rdata->regwrite);
|
||||
if (result != 0)
|
||||
goto err;
|
||||
|
||||
transfer = libusb_alloc_transfer(0);
|
||||
if (!transfer) {
|
||||
result = -ENOMEM;
|
||||
goto err;
|
||||
}
|
||||
|
||||
data = g_malloc(126);
|
||||
libusb_fill_bulk_transfer(transfer, dev->udev, EP_IN, data, 126,
|
||||
read_regs_data_cb, rdata, BULK_TIMEOUT);
|
||||
|
||||
r = libusb_submit_transfer(transfer);
|
||||
if (r < 0) {
|
||||
g_free(data);
|
||||
libusb_free_transfer(transfer);
|
||||
result = -EIO;
|
||||
goto err;
|
||||
}
|
||||
|
||||
return;
|
||||
err:
|
||||
rdata->callback(dev, result, NULL, rdata->user_data);
|
||||
g_free(rdata);
|
||||
}
|
||||
|
||||
|
||||
// XXX: this comes from aes2501 driver but it is unused here
|
||||
static void read_regs(struct fp_img_dev *dev, aes1610_read_regs_cb callback,
|
||||
void *user_data)
|
||||
{
|
||||
/* FIXME: regwrite is dynamic because of asynchronity. is this really
|
||||
* required? */
|
||||
struct aes_regwrite *regwrite = g_malloc(sizeof(*regwrite));
|
||||
struct aes1610_read_regs *rdata = g_malloc(sizeof(*rdata));
|
||||
|
||||
fp_dbg("");
|
||||
//regwrite->reg = AES1610_REG_CTRL2;
|
||||
//regwrite->value = AES1610_CTRL2_READ_REGS;
|
||||
rdata->dev = dev;
|
||||
rdata->callback = callback;
|
||||
rdata->user_data = user_data;
|
||||
rdata->regwrite = regwrite;
|
||||
|
||||
//aes_write_regv(dev, (const struct aes_regwrite *) regwrite, 1,
|
||||
// read_regs_rq_cb, rdata);
|
||||
}
|
||||
|
||||
/* Read the value of a specific register from a register dump */
|
||||
static int regval_from_dump(unsigned char *data, uint8_t target)
|
||||
{
|
||||
if (*data != FIRST_AES1610_REG) {
|
||||
fp_err("not a register dump");
|
||||
return -EILSEQ;
|
||||
}
|
||||
|
||||
if (!(FIRST_AES1610_REG <= target && target <= LAST_AES1610_REG)) {
|
||||
fp_err("out of range");
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
target -= FIRST_AES1610_REG;
|
||||
target *= 2;
|
||||
return data[target + 1];
|
||||
}
|
||||
|
||||
static void generic_write_regv_cb(struct fp_img_dev *dev, int result,
|
||||
void *user_data)
|
||||
{
|
||||
@@ -217,8 +123,6 @@ static void generic_write_regv_cb(struct fp_img_dev *dev, int result,
|
||||
fpi_ssm_mark_aborted(ssm, result);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* read the specified number of bytes from the IN endpoint but throw them
|
||||
* away, then increment the SSM */
|
||||
static void generic_read_ignore_data(struct fpi_ssm *ssm, size_t bytes)
|
||||
@@ -244,150 +148,6 @@ static void generic_read_ignore_data(struct fpi_ssm *ssm, size_t bytes)
|
||||
}
|
||||
}
|
||||
|
||||
/****** IMAGE PROCESSING ******/
|
||||
|
||||
static int sum_histogram_values(unsigned char *data, uint8_t threshold)
|
||||
{
|
||||
int r = 0;
|
||||
int i;
|
||||
uint16_t *histogram = (uint16_t *)(data + 1);
|
||||
|
||||
if (*data != 0xde)
|
||||
return -EILSEQ;
|
||||
|
||||
if (threshold > 0x0f)
|
||||
return -EINVAL;
|
||||
|
||||
/* FIXME endianness */
|
||||
for (i = threshold; i < 16; i++)
|
||||
r += histogram[i];
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
/* find overlapping parts of frames */
|
||||
static unsigned int find_overlap(unsigned char *first_frame,
|
||||
unsigned char *second_frame, unsigned int *min_error)
|
||||
{
|
||||
unsigned int dy;
|
||||
unsigned int not_overlapped_height = 0;
|
||||
*min_error = 255 * FRAME_SIZE;
|
||||
for (dy = 0; dy < FRAME_HEIGHT; dy++) {
|
||||
/* Calculating difference (error) between parts of frames */
|
||||
unsigned int i;
|
||||
unsigned int error = 0;
|
||||
for (i = 0; i < FRAME_WIDTH * (FRAME_HEIGHT - dy); i++) {
|
||||
/* Using ? operator to avoid abs function */
|
||||
error += first_frame[i] > second_frame[i] ?
|
||||
(first_frame[i] - second_frame[i]) :
|
||||
(second_frame[i] - first_frame[i]);
|
||||
}
|
||||
|
||||
/* Normalize error */
|
||||
error *= 15;
|
||||
error /= i;
|
||||
if (error < *min_error) {
|
||||
*min_error = error;
|
||||
not_overlapped_height = dy;
|
||||
}
|
||||
first_frame += FRAME_WIDTH;
|
||||
}
|
||||
|
||||
return not_overlapped_height;
|
||||
}
|
||||
|
||||
/* assemble a series of frames into a single image */
|
||||
static unsigned int assemble(struct aes1610_dev *aesdev, unsigned char *output,
|
||||
gboolean reverse, unsigned int *errors_sum)
|
||||
{
|
||||
uint8_t *assembled = output;
|
||||
int frame;
|
||||
uint32_t image_height = FRAME_HEIGHT;
|
||||
unsigned int min_error;
|
||||
size_t num_strips = aesdev->strips_len;
|
||||
GSList *list_entry = aesdev->strips;
|
||||
*errors_sum = 0;
|
||||
|
||||
if (num_strips < 1)
|
||||
return 0;
|
||||
|
||||
/* Rotating given data by 90 degrees
|
||||
* Taken from document describing aes1610 image format
|
||||
* TODO: move reversing detection here */
|
||||
|
||||
if (reverse)
|
||||
output += (num_strips - 1) * FRAME_SIZE;
|
||||
for (frame = 0; frame < num_strips; frame++) {
|
||||
aes_assemble_image(list_entry->data, FRAME_WIDTH, FRAME_HEIGHT, output);
|
||||
|
||||
if (reverse)
|
||||
output -= FRAME_SIZE;
|
||||
else
|
||||
output += FRAME_SIZE;
|
||||
list_entry = g_slist_next(list_entry);
|
||||
}
|
||||
|
||||
/* Detecting where frames overlaped */
|
||||
output = assembled;
|
||||
for (frame = 1; frame < num_strips; frame++) {
|
||||
int not_overlapped;
|
||||
|
||||
output += FRAME_SIZE;
|
||||
not_overlapped = find_overlap(assembled, output, &min_error);
|
||||
*errors_sum += min_error;
|
||||
image_height += not_overlapped;
|
||||
assembled += FRAME_WIDTH * not_overlapped;
|
||||
memcpy(assembled, output, FRAME_SIZE);
|
||||
}
|
||||
return image_height;
|
||||
}
|
||||
|
||||
static void assemble_and_submit_image(struct fp_img_dev *dev)
|
||||
{
|
||||
struct aes1610_dev *aesdev = dev->priv;
|
||||
size_t final_size;
|
||||
struct fp_img *img;
|
||||
unsigned int errors_sum, r_errors_sum;
|
||||
|
||||
fp_dbg("");
|
||||
|
||||
BUG_ON(aesdev->strips_len == 0);
|
||||
|
||||
/* reverse list */
|
||||
aesdev->strips = g_slist_reverse(aesdev->strips);
|
||||
|
||||
/* create buffer big enough for max image */
|
||||
img = fpi_img_new(aesdev->strips_len * FRAME_SIZE);
|
||||
|
||||
img->flags = FP_IMG_COLORS_INVERTED;
|
||||
img->height = assemble(aesdev, img->data, FALSE, &errors_sum);
|
||||
img->height = assemble(aesdev, img->data, TRUE, &r_errors_sum);
|
||||
|
||||
if (r_errors_sum > errors_sum) {
|
||||
img->height = assemble(aesdev, img->data, FALSE, &errors_sum);
|
||||
img->flags |= FP_IMG_V_FLIPPED | FP_IMG_H_FLIPPED;
|
||||
fp_dbg("normal scan direction");
|
||||
} else {
|
||||
fp_dbg("reversed scan direction");
|
||||
}
|
||||
|
||||
/* now that overlap has been removed, resize output image buffer */
|
||||
final_size = img->height * FRAME_WIDTH;
|
||||
img = fpi_img_resize(img, final_size);
|
||||
/* FIXME: ugly workaround */
|
||||
if (img->height < 12)
|
||||
img->height = 12;
|
||||
fpi_imgdev_image_captured(dev, img);
|
||||
|
||||
/* free strips and strip list */
|
||||
g_slist_foreach(aesdev->strips, (GFunc) g_free, NULL);
|
||||
g_slist_free(aesdev->strips);
|
||||
aesdev->strips = NULL;
|
||||
aesdev->strips_len = 0;
|
||||
aesdev->blanks_count = 0;
|
||||
}
|
||||
|
||||
|
||||
/****** FINGER PRESENCE DETECTION ******/
|
||||
|
||||
|
||||
@@ -416,15 +176,6 @@ static const struct aes_regwrite finger_det_reqs[] = {
|
||||
{ 0x81, 0x04 }
|
||||
};
|
||||
|
||||
static const struct aes_regwrite finger_det_none[] = {
|
||||
{ 0x80, 0x01 },
|
||||
{ 0x82, 0x00 },
|
||||
{ 0x86, 0x00 },
|
||||
{ 0xB1, 0x28 },
|
||||
{ 0x1D, 0x00 }
|
||||
};
|
||||
|
||||
|
||||
static void start_finger_detection(struct fp_img_dev *dev);
|
||||
|
||||
static void finger_det_data_cb(struct libusb_transfer *transfer)
|
||||
@@ -461,12 +212,6 @@ out:
|
||||
libusb_free_transfer(transfer);
|
||||
}
|
||||
|
||||
|
||||
static void finger_det_none_cb(struct fp_img_dev *dev, int result, void *user_data) | ||||