Commit 86f6453de032f012deae5af921cdac9b39472c55

Authored by maxnet
Committed by GitHub
1 parent 98390497

Allow members of plugdev group to execute rpiboot without root (#27)

* Do not require root privileges

Give members of plugdev group access to the usb device by udev
rules.

* Disallow requests for files outside directory

* Be more verbose about errors

* Error out if permission was denied while opening device.
* Show error if request for file containing .. was denied.
debian/99-rpiboot.rules 0 → 100644
  1 +ACTION=="add", SUBSYSTEM=="usb", ATTR{idVendor}=="0a5c", ATTR{idProduct}=="276[34]", GROUP="plugdev"
debian/rpiboot.install
1 rpiboot usr/bin 1 rpiboot usr/bin
2 msd usr/share/rpiboot 2 msd usr/share/rpiboot
  3 +debian/99-rpiboot.rules /lib/udev/rules.d
@@ -129,7 +129,12 @@ libusb_device_handle * LIBUSB_CALL open_device_with_vid( @@ -129,7 +129,12 @@ libusb_device_handle * LIBUSB_CALL open_device_with_vid(
129 if (found) { 129 if (found) {
130 sleep(1); 130 sleep(1);
131 r = libusb_open(found, &handle); 131 r = libusb_open(found, &handle);
132 - if (r < 0) 132 + if (r == LIBUSB_ERROR_ACCESS)
  133 + {
  134 + printf("Permission to access USB device denied. Make sure you are a member of the plugdev group.\n");
  135 + exit(-1);
  136 + }
  137 + else if (r < 0)
133 { 138 {
134 if(verbose) printf("Failed to open the requested device\n"); 139 if(verbose) printf("Failed to open the requested device\n");
135 handle = NULL; 140 handle = NULL;
@@ -398,6 +403,13 @@ FILE * check_file(char * dir, char *fname) @@ -398,6 +403,13 @@ FILE * check_file(char * dir, char *fname)
398 FILE * fp = NULL; 403 FILE * fp = NULL;
399 char path[256]; 404 char path[256];
400 405
  406 + // Prevent USB device from requesting files in parent directories
  407 + if(strstr(fname, ".."))
  408 + {
  409 + printf("Denying request for filename containing .. to prevent path traversal\n");
  410 + return NULL;
  411 + }
  412 +
401 // Check directory first then /usr/share/rpiboot 413 // Check directory first then /usr/share/rpiboot
402 if(dir) 414 if(dir)
403 { 415 {
@@ -566,17 +578,9 @@ int main(int argc, char *argv[]) @@ -566,17 +578,9 @@ int main(int argc, char *argv[])
566 // flush immediately 578 // flush immediately
567 setbuf(stdout, NULL); 579 setbuf(stdout, NULL);
568 580
569 -#if defined (__CYGWIN__)  
570 - //printf("Running under Cygwin\n");  
571 -#else  
572 - //exit if not run as sudo  
573 - if(getuid() != 0)  
574 - {  
575 - printf("Must be run with sudo...\n");  
576 - exit(-1);  
577 - }  
578 -#endif  
579 - 581 + // Default to standard msd directory
  582 + if(directory == NULL)
  583 + directory = "msd";
580 584
581 second_stage = check_file(directory, "bootcode.bin"); 585 second_stage = check_file(directory, "bootcode.bin");
582 if(second_stage == NULL) 586 if(second_stage == NULL)