/** * \brief Get a list of interface association Descriptors from the device */ std::list<USBDescriptorPtr> Device::interfaceAssociationDescriptors( bool videoonly) throw(USBError) { std::list<USBDescriptorPtr> iadescriptors; // see whether there is any additional data that could contain // an interface association descriptor ConfigurationPtr config = activeConfig(); if (config->extra().size() == 0) { debug(LOG_DEBUG, DEBUG_LOG, 0, "no data for descriptors"); return iadescriptors; } // try to parse additional descriptors DescriptorFactory f(*this); std::vector<USBDescriptorPtr> list = f.descriptors(config->extra()); debug(LOG_DEBUG, DEBUG_LOG, 0, "found %d additional descriptors", list.size()); // no check whether they are InterfaceAssociationDescriptors std::vector<USBDescriptorPtr>::const_iterator i; for (i = list.begin(); i != list.end(); i++) { USBDescriptorPtr dp = *i; if (isPtr<InterfaceAssociationDescriptor>(dp)) { InterfaceAssociationDescriptor *iad = getPtr<InterfaceAssociationDescriptor>(dp); bool isvideo = iad->isVideoInterfaceCollection(); debug(LOG_DEBUG, DEBUG_LOG, 0, "isvideo = %s", (isvideo) ? "YES" : "NO"); if ((!videoonly) || (isvideo)) { iadescriptors.push_back(dp); } } } // return all the interface association descriptors we have found return iadescriptors; }
/** * \brief Construct a camera from a USB Device * * The constructor undertakes an extensive analysis of the descriptors * to find the video control and video streaming interfaces of the video * function of the device. It also makes sure no kernel driver is attached * to the device. It does not, however, claim any of the interfaces, this * is done when the device is really used. * \param _device an USB device to open as a UVC camera * \param force force opening as camera even if the * interface associaten descriptor does not * declare itself as a video interface association * descriptor (handles the TIS camera) * XXX apparently the force parameter is never used, so the question should be * asked whether we can remove it. */ UVCCamera::UVCCamera(Device& _device, bool /* force */) throw(USBError) : device(_device) { debug(LOG_DEBUG, DEBUG_LOG, 0, "create a UVC camera object"); // make sure the camera is open, this most probably will not have // any effect device.open(); // scan the active configuration for one that has an Interface // association descriptor ConfigurationPtr config = device.activeConfig(); if (config->extra().size() == 0) { debug(LOG_ERR, DEBUG_LOG, 0, "no extra descriptors"); throw USBError("no InterfaceAssociationDescriptor"); } // get the list of interface association descriptors std::list<USBDescriptorPtr> iadlist = device.interfaceAssociationDescriptors(true); if (0 == iadlist.size()) { throw USBError("no Video Interface Association found"); } iadptr = *iadlist.begin(); debug(LOG_DEBUG, DEBUG_LOG, 0, "Video Interface Association found"); // get the control interface, and the list of interface descriptors // for the control interface, and claim it uint8_t ci = controlInterfaceNumber(); videocontrol = (*config)[ci]; debug(LOG_DEBUG, DEBUG_LOG, 0, "Control interface number: %d", ci); videocontrol->detachKernelDriver(); // we also need to know all the video control descriptors appended // to this InterfaceDescriptor. The VideoControlDescriptorFactory // does that. debug(LOG_DEBUG, DEBUG_LOG, 0, "parse the video control descriptors"); InterfaceDescriptorPtr controlinterface = (*videocontrol)[0]; VideoControlDescriptorFactory vcdf(device); videocontroldescriptors = vcdf.descriptors(controlinterface->extra()); std::cout << videocontroldescriptors[0]; // now claim get the various interface descriptors, i.e. the // alternate settings for an interface int interfacecount = iad().bInterfaceCount(); debug(LOG_DEBUG, DEBUG_LOG, 0, "interfaces in association: %d", interfacecount); // now parse the video streaming interfaces debug(LOG_DEBUG, DEBUG_LOG, 0, "parse streaming interface descriptors"); VideoStreamingDescriptorFactory vsf(device); for (int vsif = controlInterfaceNumber() + 1; vsif < controlInterfaceNumber() + iad().bInterfaceCount(); vsif++) { debug(LOG_DEBUG, DEBUG_LOG, 0, "analyzing video streaming interface %d", vsif); InterfacePtr interface = (*config)[vsif]; // only alternate setting 0 contains the formats InterfaceDescriptorPtr id = (*interface)[0]; std::string extra = id->extra(); debug(LOG_DEBUG, DEBUG_LOG, 0, "extra descriptors: %d bytes", extra.size()); USBDescriptorPtr vsd = vsf.descriptor(extra); debug(LOG_DEBUG, DEBUG_LOG, 0, "parse complete"); videostreaming.push_back(vsd); } debug(LOG_DEBUG, DEBUG_LOG, 0, "UVCCamera constructed"); }