diff options
author | Eric Hameleers <alien@slackware.com> | 2007-09-16 17:10:01 +0000 |
---|---|---|
committer | Eric Hameleers <alien@slackware.com> | 2007-09-16 17:10:01 +0000 |
commit | bb77c16ca36a7f67342984823056707c3b61fd24 (patch) | |
tree | 67a1c01dd9a7ad0a4f26d402375324b1671a506b /libgphoto2 | |
parent | 791624f39bc5bab0960d7b912d8ee74727be1cdd (diff) | |
download | asb-bb77c16ca36a7f67342984823056707c3b61fd24.tar.gz asb-bb77c16ca36a7f67342984823056707c3b61fd24.tar.xz |
Initial revision
Diffstat (limited to 'libgphoto2')
-rw-r--r-- | libgphoto2/build/print-udev-rules.c | 246 |
1 files changed, 246 insertions, 0 deletions
diff --git a/libgphoto2/build/print-udev-rules.c b/libgphoto2/build/print-udev-rules.c new file mode 100644 index 00000000..fe90a380 --- /dev/null +++ b/libgphoto2/build/print-udev-rules.c @@ -0,0 +1,246 @@ +/* $Id$ + * + * Copyright 2002 Hans Ulrich Niedermann <hun@users.sourceforge.net> + * Portions Copyright 2002 Lutz Mller <lutz@users.sourceforge.net> + * Portions Copyright 2002 FIXME + * Portions Copyright 2005 Julien BLACHE <jblache@debian.org> + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the + * Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + */ + +/* + * Found at http://linuxfromscratch.org/pipermail/blfs-dev/2006-May/015009.html + * Eric Hameleers <alien@slackware.com> + */ +#define GP_USB_HOTPLUG_SCRIPT "/etc/hotplug/usb/usbcam" +#define GP_CAMERA_GROUP "camera" + +#define HELP_TEXT \ +"print-udev-rules - print rules file for udev\n" \ +"\n" \ +"Syntax:\n" \ +" print-udev-rules [ --verbose ] [ --debug ] [ <scriptname> ]\n" \ +"\n" \ +" --verbose also print comments with camera model names\n" \ +" --debug print all debug output\n" \ +"\n" \ +"print-udev-rules prints the lines for the rules file on stdout.\n" \ +"All other messages are printed on stderr. In case of any error, the \n" \ +"program aborts regardless of data printed on stdout and returns a non-zero\n" \ +"status code.\n" \ +"If no <scriptname> is given, print-udev-rules uses the script name\n" \ +"\"" GP_USB_HOTPLUG_SCRIPT "\"." + +#include <stdio.h> +#include <sys/time.h> +#include <time.h> +#include <string.h> + +#include <gphoto2-camera.h> +#include <gphoto2-port-log.h> + +#ifndef TRUE +#define TRUE (0==0) +#endif +#ifndef FALSE +#define FALSE (0!=0) +#endif + +#define GP_USB_HOTPLUG_MATCH_VENDOR_ID 0x0001 +#define GP_USB_HOTPLUG_MATCH_PRODUCT_ID 0x0002 + +#define GP_USB_HOTPLUG_MATCH_DEV_CLASS 0x0080 +#define GP_USB_HOTPLUG_MATCH_DEV_SUBCLASS 0x0100 +#define GP_USB_HOTPLUG_MATCH_DEV_PROTOCOL 0x0200 + +#ifdef __GNUC__ +#define CR(result) \ + do { \ + int r = (result); \ + if (r < 0) { \ + fprintf(stderr, "print-usb-usermap: " \ + "Fatal error running `%s'.\n" \ + "Aborting.\n", #result ); \ + return (r); \ + } \ + } while (0) +#else /* !__GNUC__ */ +#define CR(result) \ + do { \ + int r = (result); \ + if (r < 0) { \ + fprintf(stderr, "print-usb-usermap: " \ + "Fatal error detected, aborting.\n"); \ + return (r); \ + } \ + } while (0) +#endif /* __GNUC__ */ + +/* print-udev-rules + * + * Print out lines that can be included into an udev rules file + * - for all cams supported by our instance of libgphoto2. + * + * written after list_cameras & print_usb_usermap + */ + +static int print_udev_rules (const char *hotplug_script, const int add_comments) +{ + int x, n; + CameraAbilitiesList *al; + CameraAbilities a; + + CR (gp_abilities_list_new (&al)); + CR (gp_abilities_list_load (al, NULL)); /* use NULL context */ + CR (n = gp_abilities_list_count (al)); + + printf ("# udev rules file for libgphoto2\n#\n"); + printf ("ACTION!=\"add\", GOTO=\"libgphoto2_rules_end\"\n\n"); + + for (x = 0; x < n; x++) { + int flags = 0; + int class = 0, subclass = 0, proto = 0; + int usb_vendor = 0, usb_product = 0; + + CR (gp_abilities_list_get_abilities (al, x, &a)); + + if (!(a.port & GP_PORT_USB)) + continue; + + if (a.usb_vendor) { /* usb product id may be 0! */ + class = 0; + subclass = 0; + proto = 0; + flags = GP_USB_HOTPLUG_MATCH_VENDOR_ID | GP_USB_HOTPLUG_MATCH_PRODUCT_ID; + usb_vendor = a.usb_vendor; + usb_product = a.usb_product; + } else if (a.usb_class) { + class = a.usb_class; + subclass = a.usb_subclass; + proto = a.usb_protocol; + flags = GP_USB_HOTPLUG_MATCH_DEV_CLASS; + if (subclass != -1) + flags |= GP_USB_HOTPLUG_MATCH_DEV_SUBCLASS; + else + subclass = 0; + if (proto != -1) + flags |= GP_USB_HOTPLUG_MATCH_DEV_PROTOCOL; + else + proto = 0; + usb_vendor = 0; + usb_product = 0; + } else { + flags = 0; + } + + if (flags != 0) { + printf ("# %s\n", + a.model); + + if (flags & GP_USB_HOTPLUG_MATCH_DEV_CLASS) { + printf("SYSFS{bDeviceClass}==\"%02x\", ", class); + if (flags & GP_USB_HOTPLUG_MATCH_DEV_SUBCLASS) { + printf("SYSFS{bDeviceSubClass}==\"%02x\", ", subclass); + } + if (flags & GP_USB_HOTPLUG_MATCH_DEV_PROTOCOL) { + printf("SYSFS{bDeviceProtocol}==\"%02x\", ", proto); + } + } else { + printf ("SYSFS{idVendor}==\"%04x\", SYSFS{idProduct}==\"%04x\", ", + a.usb_vendor, a.usb_product); + } + printf("MODE=\"0660\", GROUP=\"%s\"\n", GP_CAMERA_GROUP); + } else { + fputs ("Error: Neither vendor/product nor class/subclass matched\n", stderr); + return 2; + } + } + printf ("\nLABEL=\"libgphoto2_rules_end\"\n"); + + CR (gp_abilities_list_free (al)); + + return (0); +} + +/* time zero for debug log time stamps */ +struct timeval glob_tv_zero = { 0, 0 }; + +static void +debug_func (GPLogLevel level, const char *domain, const char *format, + va_list args, void *data) +{ + struct timeval tv; + gettimeofday (&tv,NULL); + fprintf (stderr, "%li.%06li %s(%i): ", + tv.tv_sec - glob_tv_zero.tv_sec, + (1000000 + tv.tv_usec - glob_tv_zero.tv_usec) % 1000000, + domain, level); + vfprintf (stderr, format, args); + fprintf (stderr, "\n"); +} + +int main(int argc, char *argv[]) +{ + char *hotplug_script = NULL; /* script name to use */ + int add_comments = FALSE; /* whether to add cam model as a comment */ + int debug_mode = FALSE; /* whether we should output debug messages */ + + int i; + + /* check command line arguments */ + for (i=1; i<argc; i++) { + if (0 == strcmp(argv[i], "--verbose")) { + if (add_comments) { + fprintf(stderr, "Error: duplicate parameter: option \"%s\"\n", argv[i]); + return 1; + } + add_comments = TRUE; + } else if (0 == strcmp(argv[i], "--debug")) { + if (debug_mode) { + fprintf(stderr, "Error: duplicate parameter: option \"%s\"\n", argv[i]); + return 1; + } + debug_mode = TRUE; + /* now is time zero for debug log time stamps */ + gettimeofday (&glob_tv_zero, NULL); + gp_log_add_func (GP_LOG_ALL, debug_func, NULL); + } else if (0 == strcmp(argv[i], "--help")) { + puts(HELP_TEXT); + return 0; + } else { + if (hotplug_script != NULL) { + fprintf(stderr, "Error: duplicate script parameter: \"%s\"\n", argv[i]); + return 1; + } + /* assume script name */ + hotplug_script = argv[i]; + } + } + + if (NULL == hotplug_script) { + hotplug_script = GP_USB_HOTPLUG_SCRIPT; + } + + return print_udev_rules(hotplug_script, add_comments); +} + +/* + * Local Variables: + * c-file-style:"linux" + * indent-tabs-mode:t + * End: + */ + |