Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

usb: Add driver for Altus Metrum ChaosKey device (v2)

This is a hardware random number generator. The driver provides both a
/dev/chaoskeyX entry and hooks the entropy source up to the kernel
hwrng interface. More information about the device can be found at
http://chaoskey.org

The USB ID for ChaosKey was allocated from the OpenMoko USB vendor
space and is visible as 'USBtrng' here:

http://wiki.openmoko.org/wiki/USB_Product_IDs

v2: Respond to review from Oliver Neukum <oneukum@suse.de>

* Delete extensive debug infrastructure and replace it with calls to
dev_dbg.

* Allocate I/O buffer separately from device structure to obey
requirements for non-coherant architectures.

* Initialize mutexes before registering device to ensure that open
cannot be invoked before the device is ready to proceed.

* Return number of bytes read instead of -EINTR when partial read
operation is aborted due to a signal.

* Make sure device mutex is unlocked in read error paths.

* Add MAINTAINERS entry for the driver

Signed-off-by: Keith Packard <keithp@keithp.com>
Cc: Oliver Neukum <oneukum@suse.de>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

authored by

Keith Packard and committed by
Greg Kroah-Hartman
66e3e591 1fcefbdf

+549
+6
MAINTAINERS
··· 10129 10129 F: drivers/net/usb/cdc_*.c 10130 10130 F: include/uapi/linux/usb/cdc.h 10131 10131 10132 + USB CHAOSKEY DRIVER 10133 + M: Keith Packard <keithp@keithp.com> 10134 + L: linux-usb@vger.kernel.org 10135 + S: Maintained 10136 + F: drivers/usb/misc/chaoskey.c 10137 + 10132 10138 USB CYPRESS C67X00 DRIVER 10133 10139 M: Peter Korsgaard <jacmet@sunsite.dk> 10134 10140 L: linux-usb@vger.kernel.org
+12
drivers/usb/misc/Kconfig
··· 255 255 This driver is for generating specific traffic for Super Speed Link 256 256 Layer Test Device. Say Y only when you want to conduct USB Super Speed 257 257 Link Layer Test for host controllers. 258 + 259 + config USB_CHAOSKEY 260 + tristate "ChaosKey random number generator driver support" 261 + help 262 + Say Y here if you want to connect an AltusMetrum ChaosKey to 263 + your computer's USB port. The ChaosKey is a hardware random 264 + number generator which hooks into the kernel entropy pool to 265 + ensure a large supply of entropy for /dev/random and 266 + /dev/urandom and also provides direct access via /dev/chaoskeyX 267 + 268 + To compile this driver as a module, choose M here: the 269 + module will be called chaoskey.
+1
drivers/usb/misc/Makefile
··· 25 25 obj-$(CONFIG_USB_SEVSEG) += usbsevseg.o 26 26 obj-$(CONFIG_USB_YUREX) += yurex.o 27 27 obj-$(CONFIG_USB_HSIC_USB3503) += usb3503.o 28 + obj-$(CONFIG_USB_CHAOSKEY) += chaoskey.o 28 29 29 30 obj-$(CONFIG_USB_SISUSBVGA) += sisusbvga/ 30 31 obj-$(CONFIG_USB_LINK_LAYER_TEST) += lvstest.o
+530
drivers/usb/misc/chaoskey.c
··· 1 + /* 2 + * chaoskey - driver for ChaosKey device from Altus Metrum. 3 + * 4 + * This device provides true random numbers using a noise source based 5 + * on a reverse-biased p-n junction in avalanche breakdown. More 6 + * details can be found at http://chaoskey.org 7 + * 8 + * The driver connects to the kernel hardware RNG interface to provide 9 + * entropy for /dev/random and other kernel activities. It also offers 10 + * a separate /dev/ entry to allow for direct access to the random 11 + * bit stream. 12 + * 13 + * Copyright © 2015 Keith Packard <keithp@keithp.com> 14 + * 15 + * This program is free software; you can redistribute it and/or modify 16 + * it under the terms of the GNU General Public License as published by 17 + * the Free Software Foundation; version 2 of the License. 18 + * 19 + * This program is distributed in the hope that it will be useful, but 20 + * WITHOUT ANY WARRANTY; without even the implied warranty of 21 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 22 + * General Public License for more details. 23 + */ 24 + 25 + #include <linux/module.h> 26 + #include <linux/slab.h> 27 + #include <linux/usb.h> 28 + #include <linux/wait.h> 29 + #include <linux/hw_random.h> 30 + 31 + static struct usb_driver chaoskey_driver; 32 + static struct usb_class_driver chaoskey_class; 33 + static int chaoskey_rng_read(struct hwrng *rng, void *data, 34 + size_t max, bool wait); 35 + 36 + #define usb_dbg(usb_if, format, arg...) \ 37 + dev_dbg(&(usb_if)->dev, format, ## arg) 38 + 39 + #define usb_err(usb_if, format, arg...) \ 40 + dev_err(&(usb_if)->dev, format, ## arg) 41 + 42 + /* Version Information */ 43 + #define DRIVER_VERSION "v0.1" 44 + #define DRIVER_AUTHOR "Keith Packard, keithp@keithp.com" 45 + #define DRIVER_DESC "Altus Metrum ChaosKey driver" 46 + #define DRIVER_SHORT "chaoskey" 47 + 48 + MODULE_VERSION(DRIVER_VERSION); 49 + MODULE_AUTHOR(DRIVER_AUTHOR); 50 + MODULE_DESCRIPTION(DRIVER_DESC); 51 + MODULE_LICENSE("GPL"); 52 + 53 + #define CHAOSKEY_VENDOR_ID 0x1d50 /* OpenMoko */ 54 + #define CHAOSKEY_PRODUCT_ID 0x60c6 /* ChaosKey */ 55 + 56 + #define CHAOSKEY_BUF_LEN 64 /* max size of USB full speed packet */ 57 + 58 + #define NAK_TIMEOUT (HZ) /* stall/wait timeout for device */ 59 + 60 + #ifdef CONFIG_USB_DYNAMIC_MINORS 61 + #define USB_CHAOSKEY_MINOR_BASE 0 62 + #else 63 + 64 + /* IOWARRIOR_MINOR_BASE + 16, not official yet */ 65 + #define USB_CHAOSKEY_MINOR_BASE 224 66 + #endif 67 + 68 + static const struct usb_device_id chaoskey_table[] = { 69 + { USB_DEVICE(CHAOSKEY_VENDOR_ID, CHAOSKEY_PRODUCT_ID) }, 70 + { }, 71 + }; 72 + MODULE_DEVICE_TABLE(usb, chaoskey_table); 73 + 74 + /* Driver-local specific stuff */ 75 + struct chaoskey { 76 + struct usb_interface *interface; 77 + char in_ep; 78 + struct mutex lock; 79 + struct mutex rng_lock; 80 + int open; /* open count */ 81 + int present; /* device not disconnected */ 82 + int size; /* size of buf */ 83 + int valid; /* bytes of buf read */ 84 + int used; /* bytes of buf consumed */ 85 + char *name; /* product + serial */ 86 + struct hwrng hwrng; /* Embedded struct for hwrng */ 87 + int hwrng_registered; /* registered with hwrng API */ 88 + wait_queue_head_t wait_q; /* for timeouts */ 89 + char *buf; 90 + }; 91 + 92 + static void chaoskey_free(struct chaoskey *dev) 93 + { 94 + usb_dbg(dev->interface, "free"); 95 + kfree(dev->name); 96 + kfree(dev->buf); 97 + kfree(dev); 98 + } 99 + 100 + static int chaoskey_probe(struct usb_interface *interface, 101 + const struct usb_device_id *id) 102 + { 103 + struct usb_device *udev = interface_to_usbdev(interface); 104 + struct usb_host_interface *altsetting = interface->cur_altsetting; 105 + int i; 106 + int in_ep = -1; 107 + struct chaoskey *dev; 108 + int result; 109 + int size; 110 + 111 + usb_dbg(interface, "probe %s-%s", udev->product, udev->serial); 112 + 113 + /* Find the first bulk IN endpoint and its packet size */ 114 + for (i = 0; i < altsetting->desc.bNumEndpoints; i++) { 115 + if (usb_endpoint_is_bulk_in(&altsetting->endpoint[i].desc)) { 116 + in_ep = altsetting->endpoint[i].desc.bEndpointAddress; 117 + size = altsetting->endpoint[i].desc.wMaxPacketSize; 118 + break; 119 + } 120 + } 121 + 122 + /* Validate endpoint and size */ 123 + if (in_ep == -1) { 124 + usb_dbg(interface, "no IN endpoint found"); 125 + return -ENODEV; 126 + } 127 + if (size <= 0) { 128 + usb_dbg(interface, "invalid size (%d)", size); 129 + return -ENODEV; 130 + } 131 + 132 + if (size > CHAOSKEY_BUF_LEN) { 133 + usb_dbg(interface, "size reduced from %d to %d\n", 134 + size, CHAOSKEY_BUF_LEN); 135 + size = CHAOSKEY_BUF_LEN; 136 + } 137 + 138 + /* Looks good, allocate and initialize */ 139 + 140 + dev = kzalloc(sizeof(struct chaoskey), GFP_KERNEL); 141 + 142 + if (dev == NULL) 143 + return -ENOMEM; 144 + 145 + dev->buf = kmalloc(size, GFP_KERNEL); 146 + 147 + if (dev->buf == NULL) { 148 + kfree(dev); 149 + return -ENOMEM; 150 + } 151 + 152 + /* Construct a name using the product and serial values. Each 153 + * device needs a unique name for the hwrng code 154 + */ 155 + 156 + if (udev->product && udev->serial) { 157 + dev->name = kmalloc(strlen(udev->product) + 1 + 158 + strlen(udev->serial) + 1, GFP_KERNEL); 159 + if (dev->name == NULL) { 160 + kfree(dev->buf); 161 + kfree(dev); 162 + return -ENOMEM; 163 + } 164 + 165 + strcpy(dev->name, udev->product); 166 + strcat(dev->name, "-"); 167 + strcat(dev->name, udev->serial); 168 + } 169 + 170 + dev->interface = interface; 171 + 172 + dev->in_ep = in_ep; 173 + 174 + dev->size = size; 175 + dev->present = 1; 176 + 177 + init_waitqueue_head(&dev->wait_q); 178 + 179 + mutex_init(&dev->lock); 180 + mutex_init(&dev->rng_lock); 181 + 182 + usb_set_intfdata(interface, dev); 183 + 184 + result = usb_register_dev(interface, &chaoskey_class); 185 + if (result) { 186 + usb_err(interface, "Unable to allocate minor number."); 187 + usb_set_intfdata(interface, NULL); 188 + chaoskey_free(dev); 189 + return result; 190 + } 191 + 192 + dev->hwrng.name = dev->name ? dev->name : chaoskey_driver.name; 193 + dev->hwrng.read = chaoskey_rng_read; 194 + 195 + /* Set the 'quality' metric. Quality is measured in units of 196 + * 1/1024's of a bit ("mills"). This should be set to 1024, 197 + * but there is a bug in the hwrng core which masks it with 198 + * 1023. 199 + * 200 + * The patch that has been merged to the crypto development 201 + * tree for that bug limits the value to 1024 at most, so by 202 + * setting this to 1024 + 1023, we get 1023 before the fix is 203 + * merged and 1024 afterwards. We'll patch this driver once 204 + * both bits of code are in the same tree. 205 + */ 206 + dev->hwrng.quality = 1024 + 1023; 207 + 208 + dev->hwrng_registered = (hwrng_register(&dev->hwrng) == 0); 209 + if (!dev->hwrng_registered) 210 + usb_err(interface, "Unable to register with hwrng"); 211 + 212 + usb_enable_autosuspend(udev); 213 + 214 + usb_dbg(interface, "chaoskey probe success, size %d", dev->size); 215 + return 0; 216 + } 217 + 218 + static void chaoskey_disconnect(struct usb_interface *interface) 219 + { 220 + struct chaoskey *dev; 221 + 222 + usb_dbg(interface, "disconnect"); 223 + dev = usb_get_intfdata(interface); 224 + if (!dev) { 225 + usb_dbg(interface, "disconnect failed - no dev"); 226 + return; 227 + } 228 + 229 + if (dev->hwrng_registered) 230 + hwrng_unregister(&dev->hwrng); 231 + 232 + usb_deregister_dev(interface, &chaoskey_class); 233 + 234 + usb_set_intfdata(interface, NULL); 235 + mutex_lock(&dev->lock); 236 + 237 + dev->present = 0; 238 + 239 + if (!dev->open) { 240 + mutex_unlock(&dev->lock); 241 + chaoskey_free(dev); 242 + } else 243 + mutex_unlock(&dev->lock); 244 + 245 + usb_dbg(interface, "disconnect done"); 246 + } 247 + 248 + static int chaoskey_open(struct inode *inode, struct file *file) 249 + { 250 + struct chaoskey *dev; 251 + struct usb_interface *interface; 252 + 253 + /* get the interface from minor number and driver information */ 254 + interface = usb_find_interface(&chaoskey_driver, iminor(inode)); 255 + if (!interface) 256 + return -ENODEV; 257 + 258 + usb_dbg(interface, "open"); 259 + 260 + dev = usb_get_intfdata(interface); 261 + if (!dev) { 262 + usb_dbg(interface, "open (dev)"); 263 + return -ENODEV; 264 + } 265 + 266 + file->private_data = dev; 267 + mutex_lock(&dev->lock); 268 + ++dev->open; 269 + mutex_unlock(&dev->lock); 270 + 271 + usb_dbg(interface, "open success"); 272 + return 0; 273 + } 274 + 275 + static int chaoskey_release(struct inode *inode, struct file *file) 276 + { 277 + struct chaoskey *dev = file->private_data; 278 + struct usb_interface *interface; 279 + 280 + if (dev == NULL) 281 + return -ENODEV; 282 + 283 + interface = dev->interface; 284 + 285 + usb_dbg(interface, "release"); 286 + 287 + mutex_lock(&dev->lock); 288 + 289 + usb_dbg(interface, "open count at release is %d", dev->open); 290 + 291 + if (dev->open <= 0) { 292 + usb_dbg(interface, "invalid open count (%d)", dev->open); 293 + mutex_unlock(&dev->lock); 294 + return -ENODEV; 295 + } 296 + 297 + --dev->open; 298 + 299 + if (!dev->present) { 300 + if (dev->open == 0) { 301 + mutex_unlock(&dev->lock); 302 + chaoskey_free(dev); 303 + } else 304 + mutex_unlock(&dev->lock); 305 + } else 306 + mutex_unlock(&dev->lock); 307 + 308 + usb_dbg(interface, "release success"); 309 + return 0; 310 + } 311 + 312 + /* Fill the buffer. Called with dev->lock held 313 + */ 314 + static int _chaoskey_fill(struct chaoskey *dev) 315 + { 316 + DEFINE_WAIT(wait); 317 + int result; 318 + int this_read; 319 + struct usb_device *udev = interface_to_usbdev(dev->interface); 320 + 321 + usb_dbg(dev->interface, "fill"); 322 + 323 + /* Return immediately if someone called before the buffer was 324 + * empty */ 325 + if (dev->valid != dev->used) { 326 + usb_dbg(dev->interface, "not empty yet (valid %d used %d)", 327 + dev->valid, dev->used); 328 + return 0; 329 + } 330 + 331 + /* Bail if the device has been removed */ 332 + if (!dev->present) { 333 + usb_dbg(dev->interface, "device not present"); 334 + return -ENODEV; 335 + } 336 + 337 + /* Make sure the device is awake */ 338 + result = usb_autopm_get_interface(dev->interface); 339 + if (result) { 340 + usb_dbg(dev->interface, "wakeup failed (result %d)", result); 341 + return result; 342 + } 343 + 344 + result = usb_bulk_msg(udev, 345 + usb_rcvbulkpipe(udev, dev->in_ep), 346 + dev->buf, dev->size, &this_read, 347 + NAK_TIMEOUT); 348 + 349 + /* Let the device go back to sleep eventually */ 350 + usb_autopm_put_interface(dev->interface); 351 + 352 + if (result == 0) { 353 + dev->valid = this_read; 354 + dev->used = 0; 355 + } 356 + 357 + usb_dbg(dev->interface, "bulk_msg result %d this_read %d", 358 + result, this_read); 359 + 360 + return result; 361 + } 362 + 363 + static ssize_t chaoskey_read(struct file *file, 364 + char __user *buffer, 365 + size_t count, 366 + loff_t *ppos) 367 + { 368 + struct chaoskey *dev; 369 + ssize_t read_count = 0; 370 + int this_time; 371 + int result = 0; 372 + unsigned long remain; 373 + 374 + dev = file->private_data; 375 + 376 + if (dev == NULL || !dev->present) 377 + return -ENODEV; 378 + 379 + usb_dbg(dev->interface, "read %zu", count); 380 + 381 + while (count > 0) { 382 + 383 + /* Grab the rng_lock briefly to ensure that the hwrng interface 384 + * gets priority over other user access 385 + */ 386 + result = mutex_lock_interruptible(&dev->rng_lock); 387 + if (result) 388 + goto bail; 389 + mutex_unlock(&dev->rng_lock); 390 + 391 + result = mutex_lock_interruptible(&dev->lock); 392 + if (result) 393 + goto bail; 394 + if (dev->valid == dev->used) { 395 + result = _chaoskey_fill(dev); 396 + if (result) { 397 + mutex_unlock(&dev->lock); 398 + goto bail; 399 + } 400 + 401 + /* Read returned zero bytes */ 402 + if (dev->used == dev->valid) { 403 + mutex_unlock(&dev->lock); 404 + goto bail; 405 + } 406 + } 407 + 408 + this_time = dev->valid - dev->used; 409 + if (this_time > count) 410 + this_time = count; 411 + 412 + remain = copy_to_user(buffer, dev->buf + dev->used, this_time); 413 + if (remain) { 414 + result = -EFAULT; 415 + 416 + /* Consume the bytes that were copied so we don't leak 417 + * data to user space 418 + */ 419 + dev->used += this_time - remain; 420 + mutex_unlock(&dev->lock); 421 + goto bail; 422 + } 423 + 424 + count -= this_time; 425 + read_count += this_time; 426 + buffer += this_time; 427 + dev->used += this_time; 428 + mutex_unlock(&dev->lock); 429 + } 430 + bail: 431 + if (read_count) { 432 + usb_dbg(dev->interface, "read %zu bytes", read_count); 433 + return read_count; 434 + } 435 + usb_dbg(dev->interface, "empty read, result %d", result); 436 + return result; 437 + } 438 + 439 + static int chaoskey_rng_read(struct hwrng *rng, void *data, 440 + size_t max, bool wait) 441 + { 442 + struct chaoskey *dev = container_of(rng, struct chaoskey, hwrng); 443 + int this_time; 444 + 445 + usb_dbg(dev->interface, "rng_read max %zu wait %d", max, wait); 446 + 447 + if (!dev->present) { 448 + usb_dbg(dev->interface, "device not present"); 449 + return 0; 450 + } 451 + 452 + /* Hold the rng_lock until we acquire the device lock so that 453 + * this operation gets priority over other user access to the 454 + * device 455 + */ 456 + mutex_lock(&dev->rng_lock); 457 + 458 + mutex_lock(&dev->lock); 459 + 460 + mutex_unlock(&dev->rng_lock); 461 + 462 + /* Try to fill the buffer if empty. It doesn't actually matter 463 + * if _chaoskey_fill works; we'll just return zero bytes as 464 + * the buffer will still be empty 465 + */ 466 + if (dev->valid == dev->used) 467 + (void) _chaoskey_fill(dev); 468 + 469 + this_time = dev->valid - dev->used; 470 + if (this_time > max) 471 + this_time = max; 472 + 473 + memcpy(data, dev->buf, this_time); 474 + 475 + dev->used += this_time; 476 + 477 + mutex_unlock(&dev->lock); 478 + 479 + usb_dbg(dev->interface, "rng_read this_time %d\n", this_time); 480 + return this_time; 481 + } 482 + 483 + #ifdef CONFIG_PM 484 + static int chaoskey_suspend(struct usb_interface *interface, 485 + pm_message_t message) 486 + { 487 + usb_dbg(interface, "suspend"); 488 + return 0; 489 + } 490 + 491 + static int chaoskey_resume(struct usb_interface *interface) 492 + { 493 + usb_dbg(interface, "resume"); 494 + return 0; 495 + } 496 + #else 497 + #define chaoskey_suspend NULL 498 + #define chaoskey_resume NULL 499 + #endif 500 + 501 + /* file operation pointers */ 502 + static const struct file_operations chaoskey_fops = { 503 + .owner = THIS_MODULE, 504 + .read = chaoskey_read, 505 + .open = chaoskey_open, 506 + .release = chaoskey_release, 507 + .llseek = default_llseek, 508 + }; 509 + 510 + /* class driver information */ 511 + static struct usb_class_driver chaoskey_class = { 512 + .name = "chaoskey%d", 513 + .fops = &chaoskey_fops, 514 + .minor_base = USB_CHAOSKEY_MINOR_BASE, 515 + }; 516 + 517 + /* usb specific object needed to register this driver with the usb subsystem */ 518 + static struct usb_driver chaoskey_driver = { 519 + .name = DRIVER_SHORT, 520 + .probe = chaoskey_probe, 521 + .disconnect = chaoskey_disconnect, 522 + .suspend = chaoskey_suspend, 523 + .resume = chaoskey_resume, 524 + .reset_resume = chaoskey_resume, 525 + .id_table = chaoskey_table, 526 + .supports_autosuspend = 1, 527 + }; 528 + 529 + module_usb_driver(chaoskey_driver); 530 +