diff options
Diffstat (limited to 'drivers/usb/misc')
-rw-r--r-- | drivers/usb/misc/Kconfig | 11 | ||||
-rw-r--r-- | drivers/usb/misc/chaoskey.c | 21 |
2 files changed, 25 insertions, 7 deletions
diff --git a/drivers/usb/misc/Kconfig b/drivers/usb/misc/Kconfig index e9e5ae521fa6..6e705971d637 100644 --- a/drivers/usb/misc/Kconfig +++ b/drivers/usb/misc/Kconfig @@ -260,11 +260,12 @@ config USB_CHAOSKEY tristate "ChaosKey random number generator driver support" depends on HW_RANDOM help - Say Y here if you want to connect an AltusMetrum ChaosKey to - your computer's USB port. The ChaosKey is a hardware random - number generator which hooks into the kernel entropy pool to - ensure a large supply of entropy for /dev/random and - /dev/urandom and also provides direct access via /dev/chaoskeyX + Say Y here if you want to connect an AltusMetrum ChaosKey or + Araneus Alea I to your computer's USB port. These devices + are hardware random number generators which hook into the + kernel entropy pool to ensure a large supply of entropy for + /dev/random and /dev/urandom and also provides direct access + via /dev/chaoskeyX To compile this driver as a module, choose M here: the module will be called chaoskey. diff --git a/drivers/usb/misc/chaoskey.c b/drivers/usb/misc/chaoskey.c index 76350e4ee807..6ddd08a32777 100644 --- a/drivers/usb/misc/chaoskey.c +++ b/drivers/usb/misc/chaoskey.c @@ -55,9 +55,13 @@ MODULE_LICENSE("GPL"); #define CHAOSKEY_VENDOR_ID 0x1d50 /* OpenMoko */ #define CHAOSKEY_PRODUCT_ID 0x60c6 /* ChaosKey */ +#define ALEA_VENDOR_ID 0x12d8 /* Araneus */ +#define ALEA_PRODUCT_ID 0x0001 /* Alea I */ + #define CHAOSKEY_BUF_LEN 64 /* max size of USB full speed packet */ -#define NAK_TIMEOUT (HZ) /* stall/wait timeout for device */ +#define NAK_TIMEOUT (HZ) /* normal stall/wait timeout */ +#define ALEA_FIRST_TIMEOUT (HZ*3) /* first stall/wait timeout for Alea */ #ifdef CONFIG_USB_DYNAMIC_MINORS #define USB_CHAOSKEY_MINOR_BASE 0 @@ -69,6 +73,7 @@ MODULE_LICENSE("GPL"); static const struct usb_device_id chaoskey_table[] = { { USB_DEVICE(CHAOSKEY_VENDOR_ID, CHAOSKEY_PRODUCT_ID) }, + { USB_DEVICE(ALEA_VENDOR_ID, ALEA_PRODUCT_ID) }, { }, }; MODULE_DEVICE_TABLE(usb, chaoskey_table); @@ -84,6 +89,7 @@ struct chaoskey { int open; /* open count */ bool present; /* device not disconnected */ bool reading; /* ongoing IO */ + bool reads_started; /* track first read for Alea */ int size; /* size of buf */ int valid; /* bytes of buf read */ int used; /* bytes of buf consumed */ @@ -188,6 +194,9 @@ static int chaoskey_probe(struct usb_interface *interface, dev->in_ep = in_ep; + if (udev->descriptor.idVendor != ALEA_VENDOR_ID) + dev->reads_started = 1; + dev->size = size; dev->present = 1; @@ -357,6 +366,7 @@ static int _chaoskey_fill(struct chaoskey *dev) { DEFINE_WAIT(wait); int result; + bool started; usb_dbg(dev->interface, "fill"); @@ -389,10 +399,17 @@ static int _chaoskey_fill(struct chaoskey *dev) goto out; } + /* The first read on the Alea takes a little under 2 seconds. + * Reads after the first read take only a few microseconds + * though. Presumably the entropy-generating circuit needs + * time to ramp up. So, we wait longer on the first read. + */ + started = dev->reads_started; + dev->reads_started = true; result = wait_event_interruptible_timeout( dev->wait_q, !dev->reading, - NAK_TIMEOUT); + (started ? NAK_TIMEOUT : ALEA_FIRST_TIMEOUT) ); if (result < 0) goto out; |