Am Tue, 27 Jan 2009 10:56:35 -0200 schrieb Mauro Carvalho Chehab <mchehab@xxxxxxxxxxxxx>: > On Thu, 22 Jan 2009 22:12:08 +0100 > Thierry Merle <thierry.merle@xxxxxxx> wrote: > > > Laurent Pinchart a écrit : > > > On Thursday 22 January 2009, Carsten Meier wrote: > > >> Am Thu, 22 Jan 2009 00:20:00 +0100 > > >> > > >> schrieb Laurent Pinchart <laurent.pinchart@xxxxxxxxx>: > > >>> Hi Carsten, > > >>> > > >>> On Wednesday 21 January 2009, Carsten Meier wrote: > > >>>> now I want to translate bus_info into a sysfs-path to obtain > > >>>> device-info like serial numbers. Given a device reports > > >>>> "usb-0000:00:1d.2-2" as bus_info, then the device-info is > > >>>> located under "/sys/bus/usb/devices/2-2", which is a symlink > > >>>> to the appropriate /sys/devices/ directory, right? > > >>> I'm afraid not. In the above bus_info value, 0000:00:1d.2 is > > >>> the PCI bus path of your USB controller, and the last digit > > >>> after the dash is the USB device path. > > >>> > > >>>> All I have to do is to compare the first 4 chars of bus_info > > >>>> against "usb-", get the chars after "." and append it to > > >>>> "/sys/bus/usb/devices/" to obatin a sysfs-path, right? > > >>>> > > >>>> Is there a more elegant solution or already a function for > > >>>> this? Can the "." appear more than once before the last one? > > >>> Probably not before, but definitely after. > > >>> > > >>> Root hubs get a USB device path set to '0'. Every other device > > >>> is numbered according to the hub port number it is connected > > >>> to. If you have an external hub connected on port 2 of your > > >>> root hub, and have a webcam connected to port 3 of the external > > >>> hub, usb_make_path() will return "usb-0000:00:1d.2-2.3". > > >>> > > >>> Cheers, > > >>> > > >>> Laurent Pinchart > > >> Hi, > > >> > > >> On my machine, my pvrusb2 (connected directly to my mini-pc) > > >> shows up under "/sys/bus/usb/devices/7-2/" which is a symbolic > > >> link to "../../../devices/pci0000:00/0000:00:1d.7/usb7/7-2" > > > > > > You're just lucky that USB bus 7 (usb7/7) is connected to the 7th > > > function of your USB host controller (1d.7). > > > > > > Here's an example of what I get on my computer: > > > > > > /sys/bus/usb/devices/4-2 > > > -> ../../../devices/pci0000:00/0000:00:1d.2/usb4/4-2 > > > > > >> I can't test for the new bus_info-string, because it's not fixed > > >> yet in the driver. But if I got it correctly it should be > > >> "usb-0000:00:1d.7-7.2" ? > > > > > > I think you will get usb-0000:00:1d.7-2 > > > > > >> Then I've to simply take the string after the last dash, replace > > >> "." by "-" and append it to "/sys/bus/usb/devices/" for a > > >> sysfs-path? > > > > > > Unfortunately the mapping is not that direct. The part before the > > > last dash identifies the USB host controller. The part after the > > > last dash identifies the device path related to the controller, > > > expressed as a combination of port numbers. > > > > > > The sysfs device path /sys/bus/usb/devices/7-2/ includes a USB > > > bus number (in this case 7) that is not present in > > > usb_make_path()'s output. > > > > > > To find the sysfs path of your USB peripheral, you will have to > > > find out which bus number the bus name (0000:00:1d.7) corresponds > > > to. You might be able to find that by checking each usb[0-9]+ > > > links in /sys/bus/usb/devices and comparing the link's target > > > with the bus name. > > > > > To ease this processing, using libsysfs can be a good idea... > > On my system, the documentation of libsysfs is here: > > /usr/doc/sysfsutils-2.1.0/libsysfs.txt > > Knowing the bus-id, it won't be hard to look at it in data > > structures. Just my 2 cents. > > Hi Thierry, > > It may be a good idea to add some code at the v4l2-apps dir for > retrieving the sysfs place. Maybe we may add it at qv4l2 and at > v4l2-ctl. > > Cheers, > Mauro Hi, here is code which I've written for it. It is in C++ with Boost, but adaption to C shouldn't be hard. It's not extensively tested and put into the public domain. #include <stdexcept> #include <string> #include <boost/lexical_cast.hpp> #include <cstdio> extern "C" { #include <sysfs/libsysfs.h> } bool obtain_usb_sysfs_path( const char *busname, const char *usbpath, string &sysfspath_out) { bool rc = false; ::sysfs_device *usbctl = NULL; ::sysfs_bus *usb = NULL; try { // open usb host controller usbctl = ::sysfs_open_device("pci", busname); if(!usbctl) throw runtime_error( "Unable to open usb host controller"); // find matching usb bus usb = ::sysfs_open_bus("usb"); if(!usb) throw runtime_error("Unable to open usb"); ::dlist *usbdevs = ::sysfs_get_bus_devices(usb); if(!usbdevs) throw runtime_error("Unable to get usb devices"); ::sysfs_device *usbdev = NULL; dlist_for_each_data( usbdevs, usbdev, struct sysfs_device) { // compare pathes of usb host controller and // parent of enumerated usb devices ::sysfs_device *pdev = ::sysfs_get_device_parent(usbdev); if(!pdev) continue; if(strcmp(usbctl->path, pdev->path) == 0) break; } ::sysfs_close_device(usbctl); usbctl = NULL; // assemble usb device path if(usbdev) { ::sysfs_attribute *busnumattr = ::sysfs_get_device_attr(usbdev, "busnum"); if(!busnumattr) throw runtime_error( "Unable to get usb bus number"); string str(busnumattr->value, busnumattr->len); unsigned int busnum; if(sscanf(str.c_str(), "%u", &busnum) != 1) throw runtime_error( "Unable to parse usb bus number"); sysfspath_out = usbdev->path; sysfspath_out += '/'; sysfspath_out += lexical_cast<string>(busnum); sysfspath_out += '-'; sysfspath_out += usbpath; rc = true; } ::sysfs_close_bus(usb); usb = NULL; } catch(...) { if(usb) ::sysfs_close_bus(usb); if(usbctl) ::sysfs_close_device(usbctl); throw; } return rc; } Maybe it is of use for one or another. Cheers, Carsten -- To unsubscribe from this list: send the line "unsubscribe linux-media" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html