改进热插拔重连判断机制
This commit is contained in:
parent
e4d5933b7f
commit
627b026b87
|
@ -168,36 +168,28 @@ void hg_scanner_mgr::on_hgscanner_pnp(usb_event ev, libusb_device* device, int v
|
||||||
if (index != -1)
|
if (index != -1)
|
||||||
{
|
{
|
||||||
bool add = true;
|
bool add = true;
|
||||||
for (size_t i = 0; i < online_devices_.size(); ++i)
|
size_t i = 0;
|
||||||
|
for (; i < online_devices_.size(); ++i)
|
||||||
{
|
{
|
||||||
if (online_devices_[i].dev == device)
|
if (online_devices_[i].dev == device) // 此处假定同一台设备重新连接后,设备对象“device”保持不变;如果假设不成立,会导致设备重连消息不能正常接收,绑定到该设备的scanner对象得不到释放
|
||||||
{
|
{
|
||||||
online_devices_[i].ind = index;
|
online_devices_[i].ind = index;
|
||||||
add = false;
|
add = false;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
else if (online_devices_[i].scanner && !online_devices_[i].scanner->is_online()
|
}
|
||||||
&& online_devices_[i].scanner->get_pid() == pid && online_devices_[i].scanner->get_vid() == vid)
|
if (add) // 处理对象“device”改变的情景
|
||||||
|
{
|
||||||
|
i = 0;
|
||||||
|
for (auto& v : online_devices_)
|
||||||
{
|
{
|
||||||
usb_io* io = NULL;
|
if (v.ind == index &&
|
||||||
|
(v.scanner == NULL || !v.scanner->is_online()))
|
||||||
name = online_devices_[i].display_name;
|
|
||||||
type = g_supporting_devices[index].type;
|
|
||||||
online_devices_[i].dev = device;
|
|
||||||
h = online_devices_[i].scanner;
|
|
||||||
if (pid == 0x300 || pid == 0x400)
|
|
||||||
std::this_thread::sleep_for(std::chrono::milliseconds(1000));
|
|
||||||
len = usb_manager::instance()->open(device, &io);
|
|
||||||
if (len == SCANNER_ERR_OK)
|
|
||||||
{
|
{
|
||||||
VLOG_MINI_3(LOG_LEVEL_WARNING, "[%04x:%04x]%s re-connected.\n", pid, vid, online_devices_[i].display_name.c_str());
|
add = false;
|
||||||
online_devices_[i].scanner->reset_io(io);
|
break;
|
||||||
de.openned = SANE_TRUE;
|
|
||||||
}
|
}
|
||||||
if (io)
|
i++;
|
||||||
io->release();
|
|
||||||
add = false;
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -216,10 +208,35 @@ void hg_scanner_mgr::on_hgscanner_pnp(usb_event ev, libusb_device* device, int v
|
||||||
sprintf(buf, " - %u", same_ind_++);
|
sprintf(buf, " - %u", same_ind_++);
|
||||||
ols.display_name += buf;
|
ols.display_name += buf;
|
||||||
}
|
}
|
||||||
|
libusb_ref_device(ols.dev); // ref to the device of queue online_devices_
|
||||||
online_devices_.push_back(ols);
|
online_devices_.push_back(ols);
|
||||||
name = ols.display_name;
|
name = ols.display_name;
|
||||||
type = g_supporting_devices[ols.ind].type;
|
type = g_supporting_devices[ols.ind].type;
|
||||||
}
|
}
|
||||||
|
else if (online_devices_[i].scanner && !online_devices_[i].scanner->is_online())
|
||||||
|
{
|
||||||
|
usb_io* io = NULL;
|
||||||
|
|
||||||
|
name = online_devices_[i].display_name;
|
||||||
|
type = g_supporting_devices[index].type;
|
||||||
|
if (online_devices_[i].dev)
|
||||||
|
libusb_unref_device(online_devices_[i].dev);
|
||||||
|
online_devices_[i].dev = device;
|
||||||
|
libusb_ref_device(online_devices_[i].dev);
|
||||||
|
h = online_devices_[i].scanner;
|
||||||
|
if (pid == 0x300 || pid == 0x400)
|
||||||
|
std::this_thread::sleep_for(std::chrono::milliseconds(1000));
|
||||||
|
len = usb_manager::instance()->open(device, &io);
|
||||||
|
if (len == SCANNER_ERR_OK)
|
||||||
|
{
|
||||||
|
VLOG_MINI_3(LOG_LEVEL_WARNING, "[%04x:%04x]%s re-connected.\n", pid, vid, online_devices_[i].display_name.c_str());
|
||||||
|
online_devices_[i].scanner->reset_io(io);
|
||||||
|
de.openned = SANE_TRUE;
|
||||||
|
}
|
||||||
|
if (io)
|
||||||
|
io->release();
|
||||||
|
add = false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (ev == USB_EVENT_DEVICE_LEFT)
|
else if (ev == USB_EVENT_DEVICE_LEFT)
|
||||||
|
@ -235,7 +252,10 @@ void hg_scanner_mgr::on_hgscanner_pnp(usb_event ev, libusb_device* device, int v
|
||||||
if (it->scanner)
|
if (it->scanner)
|
||||||
it->scanner->io_disconnected();
|
it->scanner->io_disconnected();
|
||||||
else
|
else
|
||||||
|
{
|
||||||
|
libusb_unref_device(it->dev); // unref the device of queue online_devices_
|
||||||
online_devices_.erase(it);
|
online_devices_.erase(it);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -72,7 +72,7 @@ int LIBUSB_CALL usb_manager::usb_pnp_callback(libusb_context* ctx, libusb_device
|
||||||
usb_manager* obj = (usb_manager*)monitor;
|
usb_manager* obj = (usb_manager*)monitor;
|
||||||
|
|
||||||
// if (event == LIBUSB_HOTPLUG_EVENT_DEVICE_ARRIVED)
|
// if (event == LIBUSB_HOTPLUG_EVENT_DEVICE_ARRIVED)
|
||||||
libusb_ref_device(device);
|
libusb_ref_device(device); // keep the object until handle it
|
||||||
//else if(event == LIBUSB_HOTPLUG_EVENT_DEVICE_LEFT)
|
//else if(event == LIBUSB_HOTPLUG_EVENT_DEVICE_LEFT)
|
||||||
// libusb_unref_device(device);
|
// libusb_unref_device(device);
|
||||||
|
|
||||||
|
@ -236,8 +236,7 @@ void usb_manager::notify_usb_event(PNPDEV& pd, bool* retry)
|
||||||
retry = &re_try;
|
retry = &re_try;
|
||||||
usb_cb_(ev, pd.dev, ud.vid, ud.pid, HIBYTE(ud.ver), LOBYTE(ud.ver) / 0x10, retry, usb_cb_param_);
|
usb_cb_(ev, pd.dev, ud.vid, ud.pid, HIBYTE(ud.ver), LOBYTE(ud.ver) / 0x10, retry, usb_cb_param_);
|
||||||
}
|
}
|
||||||
if(LIBUSB_HOTPLUG_EVENT_DEVICE_LEFT == pd.event)
|
libusb_unref_device(pd.dev); // response for libusb_ref_device in usb_manager::usb_pnp_callback
|
||||||
libusb_unref_device(pd.dev);
|
|
||||||
}
|
}
|
||||||
void usb_manager::thread_trigger_usb_event()
|
void usb_manager::thread_trigger_usb_event()
|
||||||
{
|
{
|
||||||
|
|
|
@ -59,7 +59,7 @@ namespace local_utility
|
||||||
RETURN_MATCH_ERROR(SCANNER_ERR_IO, SANE_STATUS_IO_ERROR);
|
RETURN_MATCH_ERROR(SCANNER_ERR_IO, SANE_STATUS_IO_ERROR);
|
||||||
RETURN_MATCH_ERROR(SCANNER_ERR_TIMEOUT, SANE_STATUS_IO_ERROR);
|
RETURN_MATCH_ERROR(SCANNER_ERR_TIMEOUT, SANE_STATUS_IO_ERROR);
|
||||||
|
|
||||||
RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_NOT_FOUND, SANE_STATUS_NO_DOCS);
|
// RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_NOT_FOUND, SANE_STATUS_NO_DOCS);
|
||||||
RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_NOT_SUPPORT, SANE_STATUS_UNSUPPORTED);
|
RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_NOT_SUPPORT, SANE_STATUS_UNSUPPORTED);
|
||||||
RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_BUSY, SANE_STATUS_DEVICE_BUSY);
|
RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_BUSY, SANE_STATUS_DEVICE_BUSY);
|
||||||
RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_COVER_OPENNED, SANE_STATUS_COVER_OPEN);
|
RETURN_MATCH_ERROR(SCANNER_ERR_DEVICE_COVER_OPENNED, SANE_STATUS_COVER_OPEN);
|
||||||
|
|
Loading…
Reference in New Issue