RSS Feed
Download our iPhone app
Browse DevX
Sign up for e-mail newsletters from DevX


Add Fingerprint Scan-based Security to Your .NET Applications Today : Page 2

It wasn't all that long ago that biometric authentication seemed like the kind of sci-fi technology that might never be practical outside of top-secret government laboratories. But believe it or not, you can build a fingerprint scanner into any .NET application you like just by following these simple instructions.

Coding the Application
The GrFinger SDK comes with a sample application written in different languages: VB6, Java, C++, VB.NET, etc. For the VB.NET version of this sample, there are two useful libraries that Griaule has provided: DBClass.vb and Util.vb. The DBClass.vb contains routines to add/retrieve users' information to/from a database. The Util.vb contains all the necessary routines to use the GrFingerXCtrl control and other supporting Win32 APIs. Rather than reinvent the wheel, I have decided to make use of them in my application. Hence, I will add the DBClass.vb and Util.vb files into my project (see Figure 6). Right-click on Solution Explorer and then select Add—>Existing Item…. Listings 1 and 2 show the full source of Util.vb and DBClass.vb. I will also modify the sample application provided by Griaule to suit the purpose of my application.

Figure 6. Add the two useful libraries provided by Griaule, Util.vb and DBClass.vb, to your solution.
Figure 7. Add five new fields to the enroll table to associate the data the sample application needs.

To keep the code in the DBClass.vb intact, I will use the sample Access database provided by Griaule. The original Access database is named GrFingerSample.mdb and contains one single table called enroll. The original enroll table contains only two fields: ID and template (for storing the fingerprint image). For this application, I will add five more fields to the enroll table. They are: SSN, Name, Company, ContactNumber, and Email (see Figure 7).

Save the database GrFingerSample.mdb in C:\Fingerprintreader\bin\.

Let's now switch to the code-behind of Form1 and write the code to wire up all the controls.

First, import the GrFingerXLib namespace:

Imports GrFingerXLib
Declare the following constants and member variables:

    '---name of the database---
    Const DBFile = "GrFingerSample.mdb"

    Const ConnectionString = "Provider=Microsoft.Jet.OLEDB.4.0;Data Source="

    '---for an instance of the Util.vb class---
    Private myUtil As Util
    '---for storing user's ID---
    Private _UserID As Integer
    '---database connection string---
    Private connection As System.Data.OleDb.OleDbConnection
In the Form1_Load event, code the following:

    Private Sub Form1_Load( _
       ByVal sender As System.Object, _
       ByVal e As System.EventArgs) _
       Handles MyBase.Load

        Dim err As Integer
        ' initialize util class
        myUtil = New Util(ListBox1, PictureBox1, AxGrFingerXCtrl1)
        ' Initialize GrFingerX Library
        err = myUtil.InitializeGrFinger()
        ' Print result in log
        If err < 0 Then
            Exit Sub
            myUtil.WriteLog( _
               "**GrFingerX Initialized Successfull**")
        End If

        '---create a log file---
        If Not System.IO.File.Exists(Logfile) Then
        End If

    End Sub
Here, you create an instance of the Util class. The constructor of the Util class takes in three arguments: the ListBox control to display the status of the GrFingerXCtrl control, a PictureBox control to display the captured fingerprint image, and finally the GrFingerXCtrl control itself. You then initialize the GrFingerX library and create a log file (if it is not already present). This log file is a comma-separated value (CSV) file that contains users' IDs and login times.

Next, service all the necessary events of the GrFingerXCtrl control:

    ' -----------------------------------------------------------------------------------
    ' GrFingerX events
    ' -----------------------------------------------------------------------------------
    ' A fingerprint reader was plugged on system
    Private Sub AxGrFingerXCtrl1_SensorPlug( _
       ByVal sender As System.Object, _
       ByVal e As AxGrFingerXLib._IGrFingerXCtrlEvents_SensorPlugEvent) _
       Handles AxGrFingerXCtrl1.SensorPlug
        myUtil.WriteLog("Sensor: " & e.idSensor & ". Event: Plugged.")
    End Sub

    ' A fingerprint reader was unplugged from system
    Private Sub AxGrFingerXCtrl1_SensorUnplug( _
       ByVal sender As System.Object, _
       ByVal e As AxGrFingerXLib._IGrFingerXCtrlEvents_SensorUnplugEvent) _
       Handles AxGrFingerXCtrl1.SensorUnplug
        myUtil.WriteLog("Sensor: " & e.idSensor & ". Event: Unplugged.")
    End Sub

    ' A finger was placed on reader
    Private Sub AxGrFingerXCtrl1_FingerDown( _
       ByVal sender As System.Object, _
       ByVal e As AxGrFingerXLib._IGrFingerXCtrlEvents_FingerDownEvent) _
       Handles AxGrFingerXCtrl1.FingerDown
        myUtil.WriteLog("Sensor: " & e.idSensor & ". Event: Finger Placed.")
    End Sub

    ' A finger was removed from reader
    Private Sub AxGrFingerXCtrl1_FingerUp( _
       ByVal sender As System.Object, _
       ByVal e As AxGrFingerXLib._IGrFingerXCtrlEvents_FingerUpEvent) _
       Handles AxGrFingerXCtrl1.FingerUp
        myUtil.WriteLog("Sensor: " & e.idSensor & ". Event: Finger removed.")
    End Sub
These events are raised when:
  • A fingerprint reader is plugged or unplugged from the computer
  • A finger is placed or removed from the fingerprint reader
Also, you need to service the ImageAcquired event of the GrFingerXCtrl control. This event is fired whenever a fingerprint image is acquired. Once the image is acquired, you call the ExtractTemplate() function (explained in the subsequent paragraphs) and then the IdentifyFingerprint() subroutine to identify the user's fingerprint:

    ' An image was acquired from reader
    Private Sub AxGrFingerXCtrl1_ImageAcquired( _
       ByVal sender As System.Object, _
       ByVal e As AxGrFingerXLib._IGrFingerXCtrlEvents_ImageAcquiredEvent) _
       Handles AxGrFingerXCtrl1.ImageAcquired

        ' Copying aquired image
        myUtil.raw.height = e.height
        myUtil.raw.width = e.width
        myUtil.raw.res = e.res
        myUtil.raw.img = e.rawImage

        ' Signaling that an Image Event occurred.
        myUtil.WriteLog("Sensor: " & e.idSensor & ". Event: Image captured.")

        ' display fingerprint image
        myUtil.PrintBiometricDisplay(False, GRConstants.GR_DEFAULT_CONTEXT)

        '---extract the template from the fingerprint scanned---

        '---identify who the user is---
        _UserID = IdentifyFingerprint()
        If _UserID > 0 Then
            '---user found---
            btnRegister.Enabled = False
            '---display user's information---
            '---writes to log file---
            '---user not found---
            btnRegister.Enabled = True
            lblMessage.Text = "User not found! Please register your information below"
        End If
    End Sub
Once the user's identity is found, you will display the user's particulars by calling the GetUserInfo() subroutine. You will also write an entry to the log file by calling the WriteToLog() subroutine.

Once a fingerprint image is captured, you need to extract some characteristic points from the image; these are called minutiae. One regular fingerprint has approximately 50 minutiae. To identify a user, you need about 13 of them. When all the minutiae are extracted, they are put together into a structure called a Template, which is the joining of all the extracted minutiae in a fingerprint. According to Griaule, the identification is made by a triangulation process and geometrical relation between the minutiae only, not the entire image. This process is accomplished by the ExtractTemplate() function:

    ' Extract a template from a fingerprint image
    Private Function ExtractTemplate() As Integer
        Dim ret As Integer
        ' extract template
        ret = myUtil.ExtractTemplate()
        ' write template quality to log
        If ret = GRConstants.GR_BAD_QUALITY Then
            myUtil.WriteLog("Template extracted successfully. Bad quality.")
        ElseIf ret = GRConstants.GR_MEDIUM_QUALITY Then
            myUtil.WriteLog("Template extracted successfully. Medium quality.")
        ElseIf ret = GRConstants.GR_HIGH_QUALITY Then
            myUtil.WriteLog("Template extracted successfully. High quality.")
        End If
        If ret >= 0 Then
            ' if no error, display minutiae/segments/directions into the image
            myUtil.PrintBiometricDisplay(True, GRConstants.GR_NO_CONTEXT)
            ' write error to log
        End If
        Return ret
    End Function
The IdentifyFingerprint() function locates the identity of the user by calling the Identify() method located in the Util.vb class. It returns the ID of the identified user:

    '---Identify a fingerprint; returns the ID of the user---
    Private Function IdentifyFingerprint() As Integer
        Dim ret As Integer, score As Integer
        score = 0
        ' identify it
        ret = myUtil.Identify(score)
        ' write result to log
        If ret > 0 Then
            myUtil.WriteLog("Fingerprint identified. ID = " & ret & ". Score = " & score & ".")
            myUtil.PrintBiometricDisplay(True, GRConstants.GR_DEFAULT_CONTEXT)
        ElseIf ret = 0 Then
            myUtil.WriteLog("Fingerprint not Found.")
        End If
        Return ret
    End Function
The GetUserInfo() subroutine retrieves the user's particulars using the value of the _UserID variable:

    '---get user's information---
    Public Sub GetUserInfo()
        Dim filePath As String
            filePath = Application.StartupPath() & "\" & DBFile
            connection = New OleDb.OleDbConnection(ConnectionString & filePath)
            Dim reader As OleDb.OleDbDataReader
            Dim command As OleDb.OleDbCommand = New OleDb.OleDbCommand
            command.Connection = connection
            '---retrieve user's particulars---
            command.CommandText = "SELECT * FROM Enroll WHERE ID=" & _UserID
            reader = command.ExecuteReader(CommandBehavior.CloseConnection)

            '---display user's particulars---
            lblMessage.Text = "Welcome, " & reader("name")
            txtSSN.Text = reader("SSN")
            txtName.Text = reader("Name")
            txtCompany.Text = reader("Company")
            txtContactNumber.Text = reader("ContactNumber")
            txtEmail.Text = reader("Email")

            '---reset the timer to another 5 seconds---
            Timer1.Enabled = False
            Timer1.Enabled = True
        Catch ex As Exception
        End Try
    End Sub
When a new user scans his fingerprint for the first time, naturally, thefingerprint is not recognized. The user can then register the fingerprint by filling his identifying data, in this case the SSN, name, company name, contact number, and email address. This is accomplished using the Register button, which first adds the fingerprint to the database (via the EnrollFingerprint() function) and then adds the particulars of the user using the AddNewUser() subroutine:

    '---Register button---
    Private Sub btnRegister_Click( _
       ByVal sender As System.Object, _
       ByVal e As System.EventArgs) _
       Handles btnRegister.Click
        '---first add the fingerprint---
        _UserID = EnrollFingerprint()
        '---then add the particulars---
        '---clears the display---
        '---writes to log file---
    End Sub
The EnrollFingerprint() function enrolls a fingerprint into the database using the Enroll() method defined in the Util.vb class:

    '---adds a fingerprint to the database; returns the ID of the user---
    Private Function EnrollFingerprint() As Integer
        Dim id As Integer
        ' add fingerprint
        id = myUtil.Enroll()
        ' write result to log
        If id >= 0 Then
            myUtil.WriteLog("Fingerprint enrolled with id = " & id)
            myUtil.WriteLog("Error: Fingerprint not enrolled")
        End If
        Return id
    End Function
The AddNewUser() subroutine saves the user's particulars into the database:

    '---Add a new user's information to the database---
    Public Sub AddNewUser()
        Dim filePath As String
            filePath = Application.StartupPath() & "\" & DBFile
            connection = New OleDb.OleDbConnection(ConnectionString & filePath)
            Dim command As OleDb.OleDbCommand = New OleDb.OleDbCommand
            command.Connection = connection

            '---set the user's particulars in the table---
            Dim sql As String = "UPDATE enroll SET SSN='" & txtSSN.Text & "', " & _
               "Name='" & txtName.Text & "', " & _
               "Company='" & txtCompany.Text & "', " & _
               "ContactNumber='" & txtContactNumber.Text & "', " & _
               "Email='" & txtEmail.Text & "' " & _
               " WHERE ID=" & _UserID
            command.CommandText = sql
            MsgBox("User added successfully!")
        Catch ex As Exception
        End Try
    End Sub
The ClearDisplay() subroutine clears away the information displayed in the various TextBox controls:

    '---Clears the user's particulars---
    Public Sub ClearDisplay()
        lblMessage.Text = _
           "Please place your index finger on the fingerprint reader"
        PictureBox1.Image = ImageList1.Images(0)
        txtSSN.Text = String.Empty
        txtName.Text = String.Empty
        txtCompany.Text = String.Empty
        txtContactNumber.Text = String.Empty
        txtEmail.Text = String.Empty
    End Sub
When the Timer1_Tick event is fired (every 5 seconds), call the ClearDisplay() subroutine to clear the display:

    '---the Timer control---
    Private Sub Timer1_Tick( _
       ByVal sender As System.Object, _
       ByVal e As System.EventArgs) _
       Handles Timer1.Tick
        Timer1.Enabled = False
    End Sub
The WriteToLog() subroutine writes to the log file an entry containing user's ID and the current time:

    Public Sub WriteToLog(ByVal ID As String)
        '---write to a log file---
        Dim sw As New System.IO.StreamWriter( _
           Logfile, True, System.Text.Encoding.ASCII)
        sw.WriteLine(id & "," & Now.ToString)
    End Sub

Close Icon
Thanks for your registration, follow us on our social networks to keep up-to-date