code_device/hgdriver/hgdev/scanner_manager.cpp

798 lines
31 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "scanner_manager.h"
#include "../wrapper/hg_log.h"
#include <iostream>
#include <string.h>
#include "raw_src.h"
#include "char_const.h"
#if !defined(WIN32) && !defined(_WIN64)
#endif
// kinds of scanners ...
#define SCAN_PTR(ptr) ((hg_scanner*)ptr)
#include "hg_scanner_200.h"
#include "hg_scanner_239.h"
#include "hg_scanner_300.h"
#include "hg_scanner_400.h"
#include "hg_scanner_302.h"
#include "hg_scanner_402.h"
/// <summary>
/// supporting devices :
///
#define TO_STR(s) #s
#define PID_AND_NAME(p, n) 0x##p, std::string(n) + " - " + TO_STR(p)
#define GET_LANG(str,b) from_default_language(str,b)
static struct
{
uint16_t vid; // vendor ID
uint16_t pid; // product ID
std::string name; // product name
std::string type; // product type
std::string rsc; // USB resource, version-addr. e.g. "USB2.0-1"
hg_scanner* (* create_scanner)(const char*, usb_io*, scanner_handle*);
}
g_supporting_devices[] = {
#ifdef OEM_LISICHENG
{0x31c9, PID_AND_NAME(8200, SCANNER_NAME_LSC_G42S), "G42S", "", &hg_scanner_mgr::create_scanner_g300}
, {0x31c9, PID_AND_NAME(8420, SCANNER_NAME_LSC_G42S), "G42S", "", &hg_scanner_mgr::create_scanner_g300}
, {0x31c9, PID_AND_NAME(8429, SCANNER_NAME_LSC_G42S), "G42S", "", &hg_scanner_mgr::create_scanner_empty}
, {0x31c9, PID_AND_NAME(8520, SCANNER_NAME_LSC_G52S), "G52S", "", &hg_scanner_mgr::create_scanner_g400}
, {0x31c9, PID_AND_NAME(8529, SCANNER_NAME_LSC_G52S), "G52S", "", &hg_scanner_mgr::create_scanner_g239}
, {0x31c9, PID_AND_NAME(8620, SCANNER_NAME_LSC_G62S), "G62S", "", &hg_scanner_mgr::create_scanner_g100}
, {0x31c9, PID_AND_NAME(8629, SCANNER_NAME_LSC_G62S), "G62S", "", &hg_scanner_mgr::create_scanner_g239}
, {0x31c9, PID_AND_NAME(8730, SCANNER_NAME_LSC_G73S), "G73S", "", &hg_scanner_mgr::create_scanner_g100}
, {0x31c9, PID_AND_NAME(8739, SCANNER_NAME_LSC_G73S), "G73S", "", &hg_scanner_mgr::create_scanner_g239}
#elif defined(OEM_HANWANG)
{0x2903, 0x1000, SCANNER_NAME_HW_1000, SCANNER_NAME_HW_1000, "", &hg_scanner_mgr::create_scanner_g300} // "HW-1060A"
, {0x2903, 0x1002, SCANNER_NAME_HW_1002, SCANNER_NAME_HW_1002, "", &hg_scanner_mgr::create_scanner_g302} // "HW-1060A"
, {0x2903, 0x7000, SCANNER_NAME_HW_7000, SCANNER_NAME_HW_7000, "", &hg_scanner_mgr::create_scanner_g400} // "HW-74x0WA"
, {0x2903, 0x7002, SCANNER_NAME_HW_7002, SCANNER_NAME_HW_7002, "", &hg_scanner_mgr::create_scanner_g402} // "HW-7002"
, {0x2903, 0x7039, SCANNER_NAME_HW_7039, SCANNER_NAME_HW_7039, "", &hg_scanner_mgr::create_scanner_g239} // "HW-7039F"
, {0x2903, 0x8000, SCANNER_NAME_HW_8000, SCANNER_NAME_HW_8000, "", &hg_scanner_mgr::create_scanner_g239} // "HW-8090F"
, {0x2903, 0x9000, SCANNER_NAME_HW_9000, SCANNER_NAME_HW_9000, "", &hg_scanner_mgr::create_scanner_g239} // "HW-9110E"
#elif defined(OEM_CANGTIAN)
{0x3308, 0x6006, SCANNER_NAME_CT_9020, SCANNER_NAME_CT_9020, "", &hg_scanner_mgr::create_scanner_g239}
, {0x3308, 0x6005, SCANNER_NAME_CT_4520, SCANNER_NAME_CT_4520, "", &hg_scanner_mgr::create_scanner_g300}
, {0x3308, 0x0238, SCANNER_NAME_CT_138, SCANNER_NAME_CT_138, "", &hg_scanner_mgr::create_scanner_g239}
, {0x3308, 0x0138, SCANNER_NAME_CT_238, SCANNER_NAME_CT_238, "", &hg_scanner_mgr::create_scanner_g239}
#elif defined(OEM_ZHONGJING)
{0X05DA, 0x9220, SCANNER_NAME_ZJ_6500, "S6500", "",& hg_scanner_mgr::create_scanner_g439}
#else
{0x3072, PID_AND_NAME(100, SCANNER_NAME_HG_G100), "G100", "", &hg_scanner_mgr::create_scanner_g100}
, {0x3072, PID_AND_NAME(139, SCANNER_NAME_HG_G100), "G100", "", &hg_scanner_mgr::create_scanner_g239}
, {0x3072, PID_AND_NAME(200, SCANNER_NAME_HG_G200), "G200", "", &hg_scanner_mgr::create_scanner_g100}
, {0x3072, PID_AND_NAME(239, SCANNER_NAME_HG_G200), "G200", "", &hg_scanner_mgr::create_scanner_g239}
, {0x3072, PID_AND_NAME(300, SCANNER_NAME_HG_G300), "G300", "", &hg_scanner_mgr::create_scanner_g300}
, {0x3072, PID_AND_NAME(302, SCANNER_NAME_HG_G300), "G300", "", &hg_scanner_mgr::create_scanner_g302}
, {0x3072, PID_AND_NAME(339, SCANNER_NAME_HG_G300), "G300", "", &hg_scanner_mgr::create_scanner_empty}
, {0x3072, PID_AND_NAME(400, SCANNER_NAME_HG_G400), "G400", "", &hg_scanner_mgr::create_scanner_g400}
, {0x3072, PID_AND_NAME(402, SCANNER_NAME_HG_G400), "G400", "", &hg_scanner_mgr::create_scanner_g402}
, {0x3072, PID_AND_NAME(439, SCANNER_NAME_HG_G400), "G400", "", &hg_scanner_mgr::create_scanner_g439}
, {0x064B, PID_AND_NAME(7823,SCANNER_NAME_HG_G200), "G200", "", &hg_scanner_mgr::create_scanner_g100}
#endif
};
bool islang = false;
//static std::string g_vendor = GET_LANG(COMPANY_NAME, &islang);
#define BRAND_LOGO_SIZE 8 * 1024
#define MOVE_TO_NEXT_STR(str) str += strlen(str) + 1
/// </summary>
hg_scanner_mgr* hg_scanner_mgr::inst_ = NULL;
sane_callback hg_scanner_mgr::event_callback_ = NULL;
bool hg_scanner_mgr::async_io_enabled_ = false;
int hg_scanner_mgr::ver_major_ = 1;
int hg_scanner_mgr::ver_minor_ = 0;
int hg_scanner_mgr::ver_build_ = 0;
int hg_scanner_mgr::ver_patch_ = 1;
std::string hg_scanner_mgr::pe_path_("");
std::string hg_scanner_mgr::pe_name_("");
bool hg_scanner_mgr::read_over_with_eof_ = true;
uint32_t hg_scanner_mgr::unique_img_id_ = 0;;
std::mutex hg_scanner_mgr::mutex_img_id;
hg_scanner_mgr::hg_scanner_mgr() : same_ind_(1)
{
usb_manager::instance()->register_hotplug(&hg_scanner_mgr::usb_event_handle, this);
}
hg_scanner_mgr::~hg_scanner_mgr()
{
usb_manager::clear();
}
int hg_scanner_mgr::ui_default_callback(scanner_handle h, int ev, void* data, unsigned int* len, void* param)
{
// if (!hg_scanner_mgr::async_io_enabled_ &&
// ev == SANE_EVENT_IS_MEMORY_ENOUGH)
// {
// struct sysinfo si;
// if(sysinfo(&si) == 0)
// return si.freeram * si.mem_unit > *len + 200 * 1024 * 1024 ? SCANNER_ERR_OK : SCANNER_ERR_INSUFFICIENT_MEMORY;
// return SCANNER_ERR_OK;
// }
if (hg_scanner_mgr::event_callback_)
return hg_scanner_mgr::event_callback_(h, ev, data, len, param);
return SCANNER_ERR_OK;
}
hg_scanner_mgr* hg_scanner_mgr::instance(sane_callback cb)
{
if (!hg_scanner_mgr::inst_)
{
hg_scanner_mgr::event_callback_ = cb;
if (cb)
hg_scanner_mgr::async_io_enabled_ = cb(NULL, SANE_EVENT_SUPPORT_ASYNC_IO, NULL, NULL, NULL) == 0;
hg_scanner_mgr::unique_img_id_ = (uint32_t)INT_MAX + 1;
hg_scanner_mgr::inst_ = new hg_scanner_mgr();
VLOG_MINI_1(LOG_LEVEL_DEBUG_INFO, "async image transferring is %s\n", hg_scanner_mgr::async_io_enabled_ ? "enabled" : "disabled");
}
return hg_scanner_mgr::inst_;
}
void hg_scanner_mgr::clear(void)
{
if (hg_scanner_mgr::inst_)
{
{
std::lock_guard<std::mutex> lock(hg_scanner_mgr::inst_->mutex_dev_);
hg_scanner_mgr::event_callback_ = nullptr;
}
delete hg_scanner_mgr::inst_;
hg_scanner_mgr::inst_ = NULL;
}
}
void hg_scanner_mgr::set_version(int hh, int hl, int lh, int ll)
{
hg_scanner_mgr::ver_major_ = hh;
hg_scanner_mgr::ver_minor_ = hl;
hg_scanner_mgr::ver_build_ = lh;
hg_scanner_mgr::ver_patch_ = ll;
}
void hg_scanner_mgr::set_exe_name(const char* path, const char* name)
{
hg_scanner_mgr::pe_path_ = path ? path : "";
hg_scanner_mgr::pe_name_ = name ? name : "";
std::string str = hg_log::get_scanimage_ver();
bool is_scanimg =false;
is_scanimg = str >= "1.0.29" ? true : false;
VLOG_MINI_2(LOG_LEVEL_ALL, "imgascan ver is: %s is_scanimg is:%d\n", str.c_str(),is_scanimg);
if (name && *name)
{
// int ret = system("scanimage -V");
std::string eof(hg_log::ini_get("read_eof", name));
if (eof.empty())
{
if(is_scanimg)
hg_scanner_mgr::read_over_with_eof_ = STRICMP(name, "simple-scan") != 0;
else
hg_scanner_mgr::read_over_with_eof_ = STRICMP(name, "simple-scan") != 0 && (!is_scanimg? (STRICMP(name, "scanimage") != 0) : 1);
}
else
hg_scanner_mgr::read_over_with_eof_ = eof != "0";
}
else
{
std::string eof(hg_log::ini_get("read_eof", "first"));
if (eof.empty())
hg_scanner_mgr::read_over_with_eof_ = true;
else
hg_scanner_mgr::read_over_with_eof_ = eof != "0";
}
VLOG_MINI_1(LOG_LEVEL_ALL, "read image data end with EOF: %s\n", hg_scanner_mgr::read_over_with_eof_ ? "true" : "false");
}
std::string hg_scanner_mgr::get_pe_name(std::string* path)
{
if (path)
*path = hg_scanner_mgr::pe_path_;
return hg_scanner_mgr::pe_name_;
}
uint32_t hg_scanner_mgr::unique_id(int type)
{
if (type == UNIQUE_ID_IMG)
{
std::lock_guard<std::mutex> lock(hg_scanner_mgr::mutex_img_id);
return hg_scanner_mgr::unique_img_id_++;
}
return -1;
}
hg_scanner* hg_scanner_mgr::create_scanner_empty(const char* name, usb_io* io, scanner_handle* h)
{
if (h)
*h = nullptr;
return nullptr;
}
hg_scanner* hg_scanner_mgr::create_scanner_g100(const char* name, usb_io* io, scanner_handle* h)
{
hg_scanner_200* s = new hg_scanner_200(name, 0x100, io);
if (h)
*h = s;
return dynamic_cast<hg_scanner*>(s);
}
hg_scanner* hg_scanner_mgr::create_scanner_g239(const char* name, usb_io* io, scanner_handle* h)
{
hg_scanner_239* s = new hg_scanner_239(name, 0x239, io);
if (h)
*h = s;
return dynamic_cast<hg_scanner*>(s);
}
hg_scanner* hg_scanner_mgr::create_scanner_g300(const char* name, usb_io* io, scanner_handle* h)
{
hg_scanner_300* s = new hg_scanner_300(name, 0x300, io);
if (h)
*h = s;
return dynamic_cast<hg_scanner*>(s);
}
hg_scanner* hg_scanner_mgr::create_scanner_g400(const char* name, usb_io* io, scanner_handle* h)
{
hg_scanner_300* s = new hg_scanner_300(name, 0x400, io);
if (h)
*h = s;
return dynamic_cast<hg_scanner*>(s);
}
hg_scanner* hg_scanner_mgr::create_scanner_g302(const char* name, usb_io* io, scanner_handle* h)
{
hg_scanner_302* s = new hg_scanner_302(name, 0x402, io); // image_process needs PID 402, we should add 302 ...
if (h)
*h = s;
return dynamic_cast<hg_scanner*>(s);
}
hg_scanner* hg_scanner_mgr::create_scanner_g402(const char* name, usb_io* io, scanner_handle* h)
{
hg_scanner_302* s = new hg_scanner_302(name, 0x402, io);
if (h)
*h = s;
return dynamic_cast<hg_scanner*>(s);
}
hg_scanner* hg_scanner_mgr::create_scanner_g439(const char* name, usb_io* io, scanner_handle* h)
{
hg_scanner_239* s = new hg_scanner_239(name, 0x439, io);
if (h)
*h = s;
return dynamic_cast<hg_scanner*>(s);
}
void hg_scanner_mgr::usb_event_handle(usb_event ev, libusb_device* device, int vid, int pid, int usb_ver_h, int usb_ver_l, bool* retry, void* user) // usb_ver_h.usb_ver_l
{
hg_scanner_mgr* obj = (hg_scanner_mgr*)user;
obj->on_hgscanner_pnp(ev, device, vid, pid, usb_ver_h, usb_ver_l, retry);
}
void hg_scanner_mgr::on_hgscanner_pnp(usb_event ev, libusb_device* device, int vid, int pid, int usb_ver_h, int usb_ver_l, bool* retry)
{
char model[40],
vendor[40];
SANE_Device_Ex de;
int ev_ui = 0;
scanner_handle h = NULL;
unsigned int len = sizeof(de);
std::string name(""), type("");
std::lock_guard<std::mutex> lock(mutex_dev_);
sprintf(model, "%x", pid);
sprintf(vendor, "%x", vid);
de.model = model;
de.name = NULL;
de.type = NULL;
de.vendor = vendor;
de.openned = SANE_FALSE;
if (ev == USB_EVENT_DEVICE_ARRIVED)
{
int index = -1;
for (int i = 0; i < _countof(g_supporting_devices); ++i)
{
if (g_supporting_devices[i].vid == vid && g_supporting_devices[i].pid == pid)
{
index = i;
ev_ui = SANE_EVENT_DEVICE_ARRIVED;
name = g_supporting_devices[i].name.c_str();
type = g_supporting_devices[i].type.c_str();
break;
}
}
if (index != -1)
{
bool add = true;
size_t i = 0;
for (; i < online_devices_.size(); ++i)
{
if (online_devices_[i].dev == device) // 此处假定同一台设备重新连接后设备对象“device”保持不变如果假设不成立会导致设备重连消息不能正常接收绑定到该设备的scanner对象得不到释放
{
online_devices_[i].ind = index;
add = false;
break;
}
}
if (add) // 处理对象“device”改变的情景
{
i = 0;
for (auto& v : online_devices_)
{
if (v.ind == index &&
(v.scanner && !v.scanner->is_online()))
{
add = false;
break;
}
i++;
}
}
if (add)
{
OLSCANNER ols;
ols.dev = device;
ols.ind = index;
ols.scanner = NULL;
ols.display_name = g_supporting_devices[ols.ind].name;
if (std::find(online_devices_.begin(), online_devices_.end(), ols.ind) != online_devices_.end())
{
char buf[40];
sprintf(buf, " - %u", same_ind_++);
ols.display_name += buf;
}
libusb_ref_device(ols.dev); // ref to the device of queue online_devices_
online_devices_.push_back(ols);
name = ols.display_name;
VLOG_MINI_1(LOG_LEVEL_DEBUG_INFO, "%s connected.\n", name.c_str());
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);
VLOG_MINI_3(LOG_LEVEL_WARNING, "[%04x:%04x]%s re-connected.\n", pid, vid, online_devices_[i].display_name.c_str());
if (len == SCANNER_ERR_OK)
{
online_devices_[i].scanner->reset_io(io);
de.openned = SANE_TRUE;
}
if (io)
io->release();
add = false;
}
}
}
else if (ev == USB_EVENT_DEVICE_LEFT)
{
std::vector<OLSCANNER>::iterator it = std::find(online_devices_.begin(), online_devices_.end(), device);
if (it != online_devices_.end())
{
ev_ui = SANE_EVENT_DEVICE_LEFT;
name = it->display_name;
type = g_supporting_devices[it->ind].type;
h = it->scanner;
VLOG_MINI_1(LOG_LEVEL_DEBUG_INFO, "%s Dis-connected.\n", name.c_str());
if (it->scanner)
it->scanner->io_disconnected();
else
{
libusb_unref_device(it->dev); // unref the device of queue online_devices_
online_devices_.erase(it);
}
}
}
if (ev_ui)
{
de.name = name.c_str();
de.type = type.c_str();
hg_scanner_mgr::ui_default_callback(h, ev_ui, &de, &len, NULL);
}
}
void hg_scanner_mgr::get_online_devices(std::vector<OLSCANNER>& devs)
{
std::lock_guard<std::mutex> lock(mutex_dev_);
devs = online_devices_;
}
void hg_scanner_mgr::set_appendix_info_for_about(SANE_About* about, char*& ptr, int& count, const char* key, const char* info, const char* url)
{
#ifdef BRAND_DISPLAY_ALL_EXPAND
if (!info || *info == 0)
info = GET_LANG(BRAND_COMMUNICATION_FAIL,&islang);
#endif
if (info && strlen(info))
{
about->appendix[count].key = ptr;
strcpy(ptr, key);
MOVE_TO_NEXT_STR(ptr);
about->appendix[count].content = ptr;
strcpy(ptr, info);
MOVE_TO_NEXT_STR(ptr);
if (url)
{
about->appendix[count++].url = ptr;
strcpy(ptr, url);
MOVE_TO_NEXT_STR(ptr);
}
else
count++;
}
}
scanner_err hg_scanner_mgr::get_about_info(scanner_handle h, void* data, unsigned* len)
{
hg_scanner* scanner = (hg_scanner*)h;
unsigned bytes = sizeof(SANE_About) + 40;
SANE_About tmp;
bytes += sizeof(g_logo);
bytes += strlen(GET_LANG(BRAND_APP_NAME,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_TITLE_VERSION,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_TITLE_COPYRIGHT,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_COPYRIGHT,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_TITE_MANUFACTOR,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_TITLE_URL,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_COMPANY_URL,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_URL_COMPANY_URL,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_TITLE_TEL,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_COMPANY_TEL,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_TITLE_ADDRESS,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_COMPANY_ADDRESS,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_TITLE_GPS,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_COMPANY_GPS,&islang)) + 8;
bytes += strlen(GET_LANG(BRAND_URL_GPS,&islang)) + 8;
// bytes += 5 * sizeof(tmp.appendix[0]);
#ifndef BRAND_DISPLAY_ALL_EXPAND
if (scanner)
#endif
{
bytes += sizeof(tmp.appendix[0]) + BRAND_INFO_MAX_LENGTH + 8 + strlen(GET_LANG(BRAND_TITLE_DEVICE_MODEL, &islang)) + 8;
bytes += sizeof(tmp.appendix[0]) + BRAND_INFO_MAX_LENGTH + 8 + strlen(GET_LANG(BRAND_TITLE_FIRM_VERSION,&islang)) + 8;
bytes += sizeof(tmp.appendix[0]) + BRAND_INFO_MAX_LENGTH + 8 + strlen(GET_LANG(BRAND_TITLE_SERIAL_NUM,&islang)) + 8;
bytes += sizeof(tmp.appendix[0]) + BRAND_INFO_MAX_LENGTH + 8 + strlen(GET_LANG(BRAND_TITLE_IP,&islang)) + 8;
bytes += sizeof(tmp.appendix[0]) + 28 + strlen(GET_LANG(BRAND_TITLE_ROLLER_COUNT,&islang)) + 8;
bytes += sizeof(tmp.appendix[0]) + 28 + strlen(GET_LANG(BRAND_TITLE_HISTORY_COUNT,&islang)) + 8;
bytes += sizeof(tmp.appendix[0]);
}
if (!data || *len < bytes)
{
*len = bytes;
return SCANNER_ERR_INSUFFICIENT_MEMORY;
}
// filling info to flat buffer ...
SANE_About* about = (SANE_About*)data;
std::string info("");
char* ptr = (char*)data + sizeof(SANE_About) + 9 * sizeof(about->appendix[0]);
about->title = ptr;
strcpy(ptr, GET_LANG(BRAND_APP_NAME,&islang));
MOVE_TO_NEXT_STR(ptr);
about->version = ptr;
sprintf(ptr, "%d.%d.%d.%d", hg_scanner_mgr::ver_major_, hg_scanner_mgr::ver_minor_, hg_scanner_mgr::ver_build_, hg_scanner_mgr::ver_patch_);
MOVE_TO_NEXT_STR(ptr);
about->copyright = ptr;
std::string s = GET_LANG(BRAND_COPYRIGHT, &islang);
strcpy(ptr, s.c_str());
MOVE_TO_NEXT_STR(ptr);
about->logo_bytes = sizeof(g_logo);;
about->logo = ptr;
memcpy(ptr, g_logo, about->logo_bytes);
ptr += about->logo_bytes + 1;
int count = 0, rolls = 0, ret = SCANNER_ERR_OK;
std::string g_vendor = GET_LANG(COMPANY_NAME, &islang);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITE_MANUFACTOR,&islang), g_vendor.c_str(), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_URL,&islang), GET_LANG(BRAND_COMPANY_URL,&islang), GET_LANG(BRAND_URL_COMPANY_URL,&islang));
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_TEL,&islang), GET_LANG(BRAND_COMPANY_TEL,&islang), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_ADDRESS,&islang), GET_LANG(BRAND_COMPANY_ADDRESS,&islang), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_GPS,&islang), GET_LANG(BRAND_COMPANY_GPS,&islang), GET_LANG(BRAND_URL_GPS,&islang));
if (scanner)
{
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_FIRM_VERSION,&islang), scanner->get_firmware_version().c_str(), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_SERIAL_NUM,&islang), scanner->get_serial_num().c_str(), NULL);
info = scanner->get_ip();
if (info.length() > 10)
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_IP,&islang), info.c_str(), NULL);
info.clear();
info = scanner->get_device_model();
if (!info.empty())
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_DEVICE_MODEL, &islang), info.c_str(), NULL);
ret = scanner->get_roller_num(rolls);
if (ret == SCANNER_ERR_OK)
{
char buf[40];
sprintf(buf, "%u", rolls);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_ROLLER_COUNT,&islang), buf, NULL);
}
#ifdef BRAND_DISPLAY_ALL_EXPAND
else
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_ROLLER_COUNT,&islang), rolls == -1 ? GET_LANG(BRAND_COMMUNICATION_FAIL,&islang) : GET_LANG(BRAND_DEVICE_NOT_SUPPORT,&islang), NULL);
#endif
ret = scanner->get_history_scan_count(rolls);
if (ret == SCANNER_ERR_OK)
{
char buf[40];
sprintf(buf, "%u", rolls);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_HISTORY_COUNT,&islang), buf, NULL);
}
#ifdef BRAND_DISPLAY_ALL_EXPAND
else
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_HISTORY_COUNT,&islang), rolls == -1 ? GET_LANG(BRAND_COMMUNICATION_FAIL,&islang) : GET_LANG(BRAND_DEVICE_NOT_SUPPORT,&islang), NULL);
#endif
}
#ifdef BRAND_DISPLAY_ALL_EXPAND
else
{
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_FIRM_VERSION,&islang), GET_LANG(BRAND_NO_DEVICE,&islang), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_SERIAL_NUM,&islang), GET_LANG(BRAND_NO_DEVICE,&islang), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_IP,&islang), GET_LANG(BRAND_NO_DEVICE,&islang), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_ROLLER_COUNT,&islang), GET_LANG(BRAND_NO_DEVICE,&islang), NULL);
set_appendix_info_for_about(about, ptr, count, GET_LANG(BRAND_TITLE_HISTORY_COUNT,&islang), GET_LANG(BRAND_NO_DEVICE,&islang), NULL);
}
#endif
about->appendix[count].key = NULL;
about->appendix[count].content = NULL;
about->appendix[count].url = NULL;
return SCANNER_ERR_OK;
}
scanner_err hg_scanner_mgr::hg_scanner_enum(ScannerInfo* scanner_list, long* count, bool local_only)
{
std::vector<OLSCANNER> devusbuf;
long size = *count;
scanner_err ret = SCANNER_ERR_OK;
std::string g_vendor = GET_LANG(COMPANY_NAME, &islang);
get_online_devices(devusbuf);
*count = devusbuf.size();
if (*count > size)
{
ret = SCANNER_ERR_INSUFFICIENT_MEMORY;
}
else
{
for (size_t i = 0; i < devusbuf.size(); i++)
{
scanner_list->vid = g_supporting_devices[devusbuf[i].ind].vid;
scanner_list->pid = g_supporting_devices[devusbuf[i].ind].pid;
strcpy(scanner_list->name, devusbuf[i].display_name.c_str());
strcpy(scanner_list->type, g_supporting_devices[devusbuf[i].ind].type.c_str());
sprintf(scanner_list->model, "%x", g_supporting_devices[devusbuf[i].ind].pid);
strcpy(scanner_list->vendor, g_vendor.c_str());
scanner_list++;
}
}
return ret;
}
scanner_err hg_scanner_mgr::hg_scanner_open(scanner_handle* h, const char* name, bool shared, const char* user, const char* pwd, const char* check, char* rsc)
{
std::vector<OLSCANNER> devs;
std::vector<OLSCANNER>::iterator it;
usb_io* io = NULL;
scanner_err ret = SCANNER_ERR_DEVICE_NOT_FOUND;
*h = NULL;
get_online_devices(devs);
it = std::find(devs.begin(), devs.end(), name);
if (it != devs.end())
{
std::string msg("");
ret = (scanner_err)usb_manager::instance()->open(it->dev, &io, &msg);
if (ret == SCANNER_ERR_OK)
{
hg_scanner* scanner = g_supporting_devices[it->ind].create_scanner(it->display_name.c_str(), io, h);
if (!scanner)
{
if (g_supporting_devices[it->ind].pid == 0x100 ||
g_supporting_devices[it->ind].pid == 0x200 ||
g_supporting_devices[it->ind].pid == 0x8620 ||
g_supporting_devices[it->ind].pid == 0x8730)
{
hg_scanner_200* s200 = new hg_scanner_200(it->display_name.c_str(), 0x100, io);
scanner = dynamic_cast<hg_scanner*>(s200);
*h = (scanner_handle)s200;
}
else if (g_supporting_devices[it->ind].pid == 0x239 ||
g_supporting_devices[it->ind].pid == 0x139 ||
g_supporting_devices[it->ind].pid == 0x8000 ||
g_supporting_devices[it->ind].pid == 0x9000 ||
g_supporting_devices[it->ind].pid == 0x8739 ||
g_supporting_devices[it->ind].pid == 0x8629 ||
g_supporting_devices[it->ind].pid == 0x0439 ||
g_supporting_devices[it->ind].pid == 0x7039 ||
g_supporting_devices[it->ind].pid == 0x8529)
{
hg_scanner_239* s239 = new hg_scanner_239(it->display_name.c_str(), 0x239, io);
scanner = dynamic_cast<hg_scanner*>(s239);
*h = (scanner_handle)s239;
}
else if (g_supporting_devices[it->ind].pid == 0x400 ||
g_supporting_devices[it->ind].pid == 0x7000 ||
g_supporting_devices[it->ind].pid == 0x8520)
{
hg_scanner_400* s400 = new hg_scanner_400(it->display_name.c_str(), 0x400, io);
scanner = dynamic_cast<hg_scanner*>(s400);
*h = (scanner_handle)s400;
}
else if (g_supporting_devices[it->ind].pid == 0x300 ||
g_supporting_devices[it->ind].pid == 0x1000 ||
g_supporting_devices[it->ind].pid == 0x8420)
{
hg_scanner_300* s300 = new hg_scanner_300(it->display_name.c_str(), 0x300, io);
scanner = dynamic_cast<hg_scanner*>(s300);
*h = (scanner_handle)s300;
}
}
if (scanner)
{
scanner->set_ui_callback(&hg_scanner_mgr::ui_default_callback, hg_scanner_mgr::async_io_enabled_);
scanner->set_read_over_with_no_data(hg_scanner_mgr::read_over_with_eof_);
}
std::lock_guard<std::mutex> lock(mutex_dev_);
std::vector<OLSCANNER>::iterator ptr = std::find(online_devices_.begin(), online_devices_.end(), name);
if (ptr != online_devices_.end())
ptr->scanner = (hg_scanner*)*h;
}
else if(msg.length())
hg_scanner_mgr::ui_default_callback(nullptr, SANE_EVENT_ERROR, (void*)msg.c_str(), (unsigned int*)&ret, nullptr);
if(io)
io->release();
}
return *h ? SCANNER_ERR_OK : ret;
}
scanner_err hg_scanner_mgr::hg_scanner_close(scanner_handle h, bool force)
{
{
std::lock_guard<std::mutex> lock(mutex_dev_);
for (size_t i = 0; i < online_devices_.size(); ++i)
{
if (online_devices_[i].scanner == h)
{
online_devices_[i].scanner = NULL;
break;
}
}
}
SCAN_PTR(h)->close(force);
delete SCAN_PTR(h);
return SCANNER_ERR_OK;
}
scanner_err hg_scanner_mgr::hg_scanner_get_parameter(scanner_handle h, const char* name, char* data, long* len, SANE_Int* id)
{
if (!len)
return SCANNER_ERR_INVALID_PARAMETER;
int l = *len,
err = SCAN_PTR(h)->get_setting(name, data, &l, id);
*len = l;
return (scanner_err)err;
}
scanner_err hg_scanner_mgr::hg_scanner_set_parameter(scanner_handle h, const char* name, void* data, long len)
{
return (scanner_err)SCAN_PTR(h)->set_setting(name, data, len);
}
scanner_err hg_scanner_mgr::hg_scanner_start(scanner_handle h, void* async_event, int num)
{
return (scanner_err)SCAN_PTR(h)->start();
}
scanner_err hg_scanner_mgr::hg_scanner_stop(scanner_handle h)
{
return (scanner_err)SCAN_PTR(h)->stop();
}
scanner_err hg_scanner_mgr::hg_scanner_get_img_info(scanner_handle h, SANE_Parameters* bmi, long len)
{
return (scanner_err)SCAN_PTR(h)->get_image_info(bmi);
}
scanner_err hg_scanner_mgr::hg_scanner_read_img_data(scanner_handle h, unsigned char* data, long* len)
{
if (!len)
return SCANNER_ERR_INVALID_PARAMETER;
int l = *len,
err = SCAN_PTR(h)->read_image_data(data, &l);
*len = l;
return (scanner_err)err;
}
scanner_err hg_scanner_mgr::hg_scanner_get_status(scanner_handle h, int setstutas)
{
return (scanner_err)SCAN_PTR(h)->status();
}
scanner_err hg_scanner_mgr::hg_scanner_reset(scanner_handle h)
{
return (scanner_err)SCAN_PTR(h)->reset();
}
scanner_err hg_scanner_mgr::hg_scanner_control(scanner_handle h, unsigned long code, void* data, unsigned* len)
{
//if (!len && code != IO_CTRL_CODE_TEST_SINGLE)
// return SCANNER_ERR_INVALID_PARAMETER;
if (code == IO_CTRL_CODE_ABOUT_INFO)
return get_about_info(h, data, len);
else if (code == IO_CTRL_CODE_GET_LOG_FILE && len && *len == LOG_FILE_DRIVER)
{
if (!data)
return SCANNER_ERR_INVALID_PARAMETER;
std::string f(hg_log::log_file_path());
if (f.empty())
*((char*)data) = 0;
else
strcpy((char*)data, f.c_str());
return SCANNER_ERR_OK;
}
else if (!h)
return SCANNER_ERR_INVALID_PARAMETER;
else
return (scanner_err)SCAN_PTR(h)->device_io_control(code, data, len);
}
void hg_scanner_mgr::on_language_changed(void)
{
std::lock_guard<std::mutex> lock(mutex_dev_);
for (auto& v: online_devices_)
{
if (v.scanner)
v.scanner->on_language_changed();
}
}