Many companies want to enhance security without investing in expensive hardware tokens. A standard USB flash drive can serve as a cost-effective alternative for user authentication. This approach leverages something the user has (the USB drive) alongside something they know (a password), adding an extra layer of security.
The idea is simple: the system checks for the presence of a specific file or a unique identifier on the USB drive during login. If the file or identifier is missing or incorrect, access is denied. This can be implemented using scripts or lightweight applications.
Below is a basic example using Python to check for a USB drive with a specific file:
import os
import sys
def check_usb_token():
# Define the expected token file path (adjust for your OS)
token_path = "/media/usb/token.txt" # Linux example
if not os.path.exists(token_path):
print("Security token not found. Access denied.")
sys.exit(1)
with open(token_path, 'r') as f:
token = f.read().strip()
if token != "your_secret_token":
print("Invalid token. Access denied.")
sys.exit(1)
print("Access granted.")
if __name__ == "__main__":
check_usb_token()
For Windows, you can use a batch script to achieve similar functionality:
@echo off
set "token_file=E:\token.txt"
if not exist "%token_file%" (
echo Security token not found. Access denied.
exit /b 1
)
set /p token=<"%token_file%"
if not "%token%"=="your_secret_token" (
echo Invalid token. Access denied.
exit /b 1
)
echo Access granted.
To make this more secure:
- Encrypt the token file.
- Use a unique identifier per user (e.g., a hash of the USB drive's serial number).
- Combine with a password for multi-factor authentication.
While this method is cost-effective, it has some limitations:
- USB drives can be lost or stolen.
- The system is only as secure as the token file (avoid plaintext secrets).
- Not as secure as dedicated hardware tokens with cryptographic capabilities.
For a more robust solution, you can check the USB drive's serial number instead of a file:
import subprocess
def get_usb_serial():
# Linux example: list USB devices and their serial numbers
result = subprocess.run(["lsusb", "-v"], capture_output=True, text=True)
lines = result.stdout.split('\n')
for line in lines:
if "SerialNumber" in line:
return line.split()[-1]
return None
if __name__ == "__main__":
serial = get_usb_serial()
if serial != "expected_serial_number":
print("Invalid USB device. Access denied.")
sys.exit(1)
print("Access granted.")
This approach is harder to spoof but requires more setup and may vary by operating system.
Many organizations seek cost-effective alternatives to commercial USB security tokens for workstation authentication. Standard USB flash drives can serve this purpose when properly configured with unique identifiers and cryptographic functions.
The solution involves three key components:
- USB device identification through hardware signatures
- Local credential storage encryption
- Custom GINA/credential provider implementation
First, create a device identification script to extract unique USB attributes:
// PowerShell script to get USB device info
$usbDevices = Get-WmiObject Win32_USBControllerDevice | ForEach-Object {
[PSCustomObject]@{
DeviceID = $_.Dependent.DeviceID
PNPDeviceID = $_.Dependent.PNPDeviceID
Description = $_.Dependent.Description
Manufacturer = $_.Dependent.Manufacturer
SerialNumber = (Get-WmiObject Win32_PhysicalMedia | Where-Object {$_.SerialNumber}).SerialNumber
}
}
$usbDevices | Export-Csv -Path "C:\auth\usb_ids.csv" -NoTypeInformation
For Windows systems, you'll need to implement a custom credential provider. Here's a basic C# example:
public class USBTokenProvider : ICredentialProvider
{
public void SetUsageScenario(CREDENTIAL_PROVIDER_USAGE_SCENARIO cpus, uint dwFlags)
{
// Implementation for logon scenario
}
public void CheckUSBPresence()
{
ManagementObjectSearcher searcher = new ManagementObjectSearcher(
"SELECT * FROM Win32_DiskDrive WHERE InterfaceType='USB'");
foreach (ManagementObject device in searcher.Get())
{
string serial = device["SerialNumber"]?.ToString();
if (IsValidToken(serial))
{
// Grant authentication
}
}
}
}
Important security measures to implement:
- Use AES encryption for any stored credentials
- Implement rate limiting for authentication attempts
- Maintain fallback authentication methods
- Regularly rotate cryptographic keys
For Linux systems, PAM modules offer easier integration:
# /etc/pam.d/usb_auth
auth sufficient pam_exec.so /usr/local/bin/check_usb_token.sh
#!/bin/bash
# check_usb_token.sh
USB_SERIAL=$(udevadm info -q property -n /dev/sda | grep ID_SERIAL_SHORT | cut -d= -f2)
VALID_TOKENS="/etc/usb_tokens.db"
grep -q "$USB_SERIAL" "$VALID_TOKENS" && exit 0 || exit 1
Consider these operational aspects:
- Centralized management of authorized USB tokens
- Automated provisioning scripts for new employees
- Regular audits of authentication logs
- User education about token protection