parent
cb374c3235
commit
2c56b028c2
|
@ -1267,12 +1267,11 @@ TW_INT16 CTWAINDS_FreeImage::closeDS()
|
|||
if (dsState_Open != m_CurrentState)
|
||||
{
|
||||
setConditionCode(TWCC_SEQERROR);
|
||||
//FileTools::write_log("1.txt", "~CTWAINDS_FreeImage closeDS dsState_Open != m_CurrentState");
|
||||
return TWRC_FAILURE;
|
||||
}
|
||||
|
||||
|
||||
memset(&m_App, 0, sizeof(m_App));
|
||||
//FileTools::write_log("D:/1.txt"," Close DS ");
|
||||
XdPrint(" CloseDS !\n");
|
||||
return TWRC_SUCCESS;
|
||||
}
|
||||
|
@ -1654,7 +1653,6 @@ TW_INT16 CTWAINDS_FreeImage::endXfer(pTW_PENDINGXFERS _pXfers)
|
|||
if (rs)
|
||||
{
|
||||
m_Xfers.Count = 0;
|
||||
XdPrint("m_Scanner.isImageQueueEmpty() \n");
|
||||
}
|
||||
|
||||
//if (m_bCanceled)
|
||||
|
@ -1690,7 +1688,6 @@ TW_INT16 CTWAINDS_FreeImage::endXfer(pTW_PENDINGXFERS _pXfers)
|
|||
if (_pXfers == 0)
|
||||
{
|
||||
|
||||
//FileTools::write_log("D:/1.txt"," (_pXfers: m_Xfers.Count==0");
|
||||
setConditionCode(TWCC_BADVALUE);
|
||||
// Did everyting but return the currect count.
|
||||
return TWRC_CHECKSTATUS;
|
||||
|
@ -1702,11 +1699,7 @@ TW_INT16 CTWAINDS_FreeImage::endXfer(pTW_PENDINGXFERS _pXfers)
|
|||
}
|
||||
else
|
||||
{
|
||||
if (bIndicators)
|
||||
{
|
||||
//FileTools::write_log("D:/1.txt"," (bIndicators: HIDDEN");
|
||||
m_pGUI->UpdateProgress(false, '0', 0, "0");
|
||||
}
|
||||
m_pGUI->DestroyIndicators();
|
||||
}
|
||||
return twrc;
|
||||
}
|
||||
|
@ -1773,7 +1766,6 @@ bool CTWAINDS_FreeImage::UpdateCapsFromConfig(CONFIGPARAMS pConfig)
|
|||
CTWAINContainerFix32 *pfCap = 0;
|
||||
CTWAINContainerFix32Range *pfRCap = 0;
|
||||
DWORD index = -1;
|
||||
//FileTools::write_log("D:/1.txt",)
|
||||
if (0 == (pnCap = dynamic_cast<CTWAINContainerInt*>(findCapability(ICAP_PIXELTYPE))))
|
||||
{
|
||||
cerr << "Could not get ICAP_PIXELTYPE" << endl;
|
||||
|
@ -2792,16 +2784,14 @@ bool CTWAINDS_FreeImage::StartScanning(bool showUI)
|
|||
setConditionCode(TWCC_BADVALUE);
|
||||
return false;
|
||||
}
|
||||
if (bIndicators)
|
||||
{
|
||||
m_pGUI->UpdateProgress(true, '0', 0, "0");
|
||||
}
|
||||
|
||||
m_pGUI->ShowIndicators();
|
||||
bool ret = m_Scanner.acquireImage();
|
||||
if (bIndicators)
|
||||
{
|
||||
if (!ret)
|
||||
{
|
||||
m_pGUI->UpdateProgress(false, '0', 0, "0");
|
||||
m_pGUI->DestroyIndicators();
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
|
|
|
@ -0,0 +1,505 @@
|
|||
#include "stdafx.h"
|
||||
#include "GDevice.h"
|
||||
#include "IUsb.h"
|
||||
#include <cstdio>
|
||||
#include <iostream>
|
||||
#include <algorithm>
|
||||
#include <set>
|
||||
#include <string.h>
|
||||
#include <fstream>
|
||||
#include <iterator>
|
||||
#include <sstream>
|
||||
#include "StopWatch.h"
|
||||
#include "device_common.h"
|
||||
#ifndef WIN32
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
|
||||
|
||||
#define DSP_CODE_ADDR 0
|
||||
#define USER_ADDR 0x4000
|
||||
|
||||
using namespace std;
|
||||
|
||||
GDevice::GDevice(std::shared_ptr<IUsb> usb)
|
||||
{
|
||||
m_bScan = false;
|
||||
m_bListen = false;
|
||||
m_usb = usb;
|
||||
event_call = NULL;
|
||||
image_call = NULL;
|
||||
m_imagecall_userdata = NULL;
|
||||
m_eventcall_userdata = NULL;
|
||||
m_threadInt = NULL;
|
||||
m_threadrecv = NULL;
|
||||
}
|
||||
|
||||
GDevice::~GDevice()
|
||||
{
|
||||
close();
|
||||
}
|
||||
|
||||
bool GDevice::open()
|
||||
{
|
||||
if (is_open())
|
||||
return true;
|
||||
|
||||
if (m_usb && m_usb->open()) {
|
||||
m_usb->set_timeout(1000);
|
||||
init_cam();
|
||||
m_bListen = true;
|
||||
m_bScan = true;
|
||||
|
||||
if (m_threadInt) {
|
||||
m_bListen = false;
|
||||
m_threadInt->join();
|
||||
}
|
||||
|
||||
if (m_threadrecv) {
|
||||
m_bScan = false;
|
||||
m_threadrecv->join();
|
||||
}
|
||||
m_bListen = true;
|
||||
m_bScan = true;
|
||||
m_threadInt = std::shared_ptr<std::thread>(new std::thread(&GDevice::Int_main, this));
|
||||
m_threadrecv = std::shared_ptr<std::thread>(new std::thread(&GDevice::recv_main, this));
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void GDevice::close()
|
||||
{
|
||||
if (m_usb.get() && m_usb->is_open()) {
|
||||
m_usb->set_timeout(100);
|
||||
stop();
|
||||
|
||||
if (m_threadInt && m_threadInt->joinable()) {
|
||||
m_bListen = false;
|
||||
this_thread::sleep_for(std::chrono::milliseconds(100));
|
||||
m_threadInt->join();
|
||||
m_threadInt = NULL;
|
||||
}
|
||||
|
||||
if (m_threadrecv && m_threadrecv->joinable()) {
|
||||
m_bScan = false;
|
||||
image_indexs.ShutDown();
|
||||
m_threadrecv->join();
|
||||
m_threadrecv = NULL;
|
||||
}
|
||||
m_usb->close();
|
||||
}
|
||||
}
|
||||
|
||||
bool GDevice::is_open()
|
||||
{
|
||||
if (m_usb.get())
|
||||
return m_usb->is_open();
|
||||
return false;
|
||||
}
|
||||
|
||||
bool GDevice::start(image_callback callfunc, void* userdata)
|
||||
{
|
||||
if (is_run())
|
||||
return false;
|
||||
|
||||
image_call = callfunc;
|
||||
m_imagecall_userdata = userdata;
|
||||
MotorSetting ms;
|
||||
ms.value = read_reg(MOTOR_BOARD, 0x00);
|
||||
ms.scan_enable = 0;
|
||||
write_reg(MOTOR_BOARD, 0x00, ms.value);
|
||||
ms.scan_enable = 1;
|
||||
write_reg(MOTOR_BOARD, 0x00, ms.value);
|
||||
return true;
|
||||
}
|
||||
|
||||
void GDevice::set_event_call(event_callback callfunc, void* userdata)
|
||||
{
|
||||
m_eventcall_userdata = userdata;
|
||||
event_call = callfunc;
|
||||
}
|
||||
|
||||
void GDevice::stop()
|
||||
{
|
||||
|
||||
set_option(Cam_Options::scanner_stop_motor, 0);
|
||||
}
|
||||
|
||||
int GDevice::is_run()
|
||||
{
|
||||
return image_indexs.Size() != 0;
|
||||
}
|
||||
|
||||
void GDevice::reset()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
static std::string read_all_from(std::string path)
|
||||
{
|
||||
int t;
|
||||
FILE* file = fopen(path.c_str(), "rb");
|
||||
fseek(file, 0, SEEK_END);
|
||||
t = ftell(file);
|
||||
std::string buf(t, 0);
|
||||
fseek(file, 0, SEEK_SET);
|
||||
fread((void*)buf.c_str(), t, 1, file);
|
||||
fclose(file);
|
||||
return buf;
|
||||
}
|
||||
|
||||
void GDevice::write_dsp_fw(std::string path)
|
||||
{
|
||||
std::string buf = read_all_from(path);
|
||||
write_flash(DSP_CODE_ADDR, (void*)buf.c_str(), buf.size());
|
||||
}
|
||||
|
||||
void GDevice::write_pid(unsigned short pid)
|
||||
{
|
||||
write_flash(PID_ADDR, &pid, sizeof(pid));
|
||||
}
|
||||
|
||||
unsigned short GDevice::read_pid()
|
||||
{
|
||||
unsigned short pid;
|
||||
read_flash(PID_ADDR, &pid, sizeof(pid));
|
||||
return pid;
|
||||
}
|
||||
|
||||
|
||||
void GDevice::write_devname(std::string name)
|
||||
{
|
||||
if (name.size() > 64)
|
||||
return;
|
||||
|
||||
write_flash(DEVNAME_ADDR, (void*)name.c_str(), name.size());
|
||||
}
|
||||
|
||||
std::string GDevice::read_devname()
|
||||
{
|
||||
char devname[65] = {0};
|
||||
read_flash(DEVNAME_ADDR, devname, sizeof(devname) - 1);
|
||||
return devname;
|
||||
}
|
||||
|
||||
bool GDevice::write_flash(unsigned int addr, void* data, int size)
|
||||
{
|
||||
unsigned int writeAddr = addr;
|
||||
int writed = 0;
|
||||
int writing = 0;
|
||||
while (writed < size) {
|
||||
writing = min(crtlBufferSize, size - writed);
|
||||
writeAddr = addr + writed;
|
||||
{
|
||||
std::lock_guard<std::mutex> lck(m_mtxCtrl);
|
||||
m_usb->control_msg(to_device, flash_access, ((Reg2Short*)&writeAddr)->short2, ((Reg2Short*)&writeAddr)->short1, writing, (unsigned char*)data + writed);
|
||||
}
|
||||
writed += writing;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool GDevice::read_flash(unsigned int addr, void* data, int size)
|
||||
{
|
||||
unsigned int readAddr = addr;
|
||||
int readed = 0;
|
||||
int reading = 0;
|
||||
while (readed < size) {
|
||||
reading = min(crtlBufferSize, size - readed);
|
||||
readAddr = addr + readed;
|
||||
{
|
||||
std::lock_guard<std::mutex> lck(m_mtxCtrl);
|
||||
m_usb->control_msg(from_device, flash_access, ((Reg2Short*)&readAddr)->short2, ((Reg2Short*)&readAddr)->short1, reading, (unsigned char*)data + readed);
|
||||
}
|
||||
readed += reading;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
const int int_buffer_size = 1024;
|
||||
int index_count = 0;
|
||||
#include <windows.h>
|
||||
static void write_log(std::string fullname, std::string log)
|
||||
{
|
||||
std::string savepath;
|
||||
savepath = fullname;
|
||||
std::ofstream ofs(savepath, std::ios::app);
|
||||
|
||||
SYSTEMTIME sys;
|
||||
GetLocalTime(&sys);
|
||||
ofs << sys.wYear << "/" << sys.wMonth << "/" << sys.wDay << " " << sys.wHour << ":" << sys.wMinute << ":" << sys.wSecond << ":" << sys.wMilliseconds << " " << log << std::endl;
|
||||
}
|
||||
int image_index_c = 0;
|
||||
void GDevice::recv_main()
|
||||
{
|
||||
const double timeout_ratio = (1000.0 / (15.0 * 1024 * 1024)); //!< s / Mbyte
|
||||
int image_index = 0;
|
||||
int buffer_size = 0;
|
||||
int b_buffer_size = 0;
|
||||
int f_buffer_size = 0;
|
||||
unsigned char* bbuf = 0;
|
||||
unsigned char* fbuf = 0;
|
||||
unsigned char* buf;
|
||||
int buffer_reading = 0;
|
||||
int buffer_readed = 0;
|
||||
const int read_timeout = 5000;
|
||||
std::vector<unsigned char> image_data;
|
||||
StopWatch sw;
|
||||
while (m_bScan) {
|
||||
image_index = image_indexs.Take();
|
||||
if (!image_indexs.IsShutDown() && image_index >= 0)
|
||||
{
|
||||
buffer_reading = 0;
|
||||
buffer_readed = 0;
|
||||
buffer_size = frame_size(image_index);
|
||||
image_data.resize(buffer_size * 2 + int_buffer_size);
|
||||
buf = image_data.data() + int_buffer_size;
|
||||
|
||||
sw.reset();
|
||||
while (sw.elapsed_ms() < read_timeout) {
|
||||
while (DataOn() && sw.elapsed_ms() < read_timeout);
|
||||
read_frame(image_index, buffer_readed);
|
||||
buffer_reading = max(0, buffer_size - buffer_readed);
|
||||
buffer_reading = read_data(buf + buffer_readed, buffer_reading, (int)(buffer_reading * timeout_ratio));
|
||||
if (buffer_reading > 0)
|
||||
buffer_readed += buffer_reading;
|
||||
|
||||
if (buffer_readed >= buffer_size) {
|
||||
write_log("d:\\1.txt", std::to_string(image_index_c) + " time1 = " + std::to_string(sw.elapsed_ms()));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
image_index_c++;
|
||||
if (buffer_readed != buffer_size)
|
||||
{
|
||||
write_log("d:\\1.txt", std::to_string(image_index_c) + " error readed:" + std::to_string(buffer_readed) + " per read:" + std::to_string(buffer_size) + " time = " + std::to_string(sw.elapsed_ms()));
|
||||
}
|
||||
else {
|
||||
write_log("d:\\1.txt", std::to_string(image_index_c) + " get" + " time = " + std::to_string(sw.elapsed_ms()));
|
||||
}
|
||||
|
||||
b_buffer_size = 0;
|
||||
f_buffer_size = 0;
|
||||
bbuf = buf - int_buffer_size;
|
||||
fbuf = buf + buffer_size;
|
||||
for (int i = 0; i < (buffer_size / int_buffer_size); i++)
|
||||
{
|
||||
if (buf[(i + 1) * int_buffer_size - 1] == 0)
|
||||
{
|
||||
memcpy(bbuf + b_buffer_size, buf + i * int_buffer_size, int_buffer_size - 1);
|
||||
b_buffer_size += (int_buffer_size - 1);
|
||||
}
|
||||
else if (buf[(i + 1) * int_buffer_size - 1] == 255)
|
||||
{
|
||||
memcpy(fbuf + f_buffer_size, buf + i * int_buffer_size, int_buffer_size - 1);
|
||||
f_buffer_size += (int_buffer_size - 1);
|
||||
}
|
||||
}
|
||||
|
||||
FILE* pfile = fopen((("d:\\") + std::to_string(image_index_c)+"b.jpg").c_str(), "wb");
|
||||
fwrite(bbuf, 1, b_buffer_size, pfile);
|
||||
fclose(pfile);
|
||||
pfile = fopen((("d:\\") + std::to_string(image_index_c) + "f.jpg").c_str(), "wb");
|
||||
fwrite(fbuf, 1, f_buffer_size, pfile);
|
||||
fclose(pfile);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void GDevice::Int_main()
|
||||
{
|
||||
unsigned int int_buffer[4];
|
||||
int size = 0;
|
||||
while (m_bListen) {
|
||||
size = m_usb->read_int(int_buffer, sizeof(int_buffer));
|
||||
if (size >= 16)
|
||||
{
|
||||
if (int_buffer[2] != 0)
|
||||
{
|
||||
image_indexs.Put(int_buffer[1]);
|
||||
}
|
||||
if (((MotorStatus*)int_buffer)->motor_status == 1)
|
||||
{
|
||||
if (event_call) {
|
||||
event_call(0, m_eventcall_userdata);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void GDevice::init_cam()
|
||||
{
|
||||
}
|
||||
|
||||
int GDevice::read_data(void* data, int length, int timeout)
|
||||
{
|
||||
int readed = 0;
|
||||
int reading = 0;
|
||||
StopWatch sw;
|
||||
while (readed < length && sw.elapsed_ms() < timeout) {
|
||||
reading = max(0, min(length - readed, buffer_size));
|
||||
reading = m_usb->read_bulk((unsigned char*)data + readed, reading);
|
||||
if (reading > 0) {
|
||||
readed += reading;
|
||||
}
|
||||
}
|
||||
return readed;
|
||||
}
|
||||
|
||||
void GDevice::read_frame(int index, int offset)
|
||||
{
|
||||
write_reg(3, index, offset);
|
||||
}
|
||||
|
||||
int GDevice::frame_size(int index)
|
||||
{
|
||||
return read_reg(3, index);
|
||||
}
|
||||
|
||||
int GDevice::read_reg(int type, int addr)
|
||||
{
|
||||
int value;
|
||||
std::lock_guard<std::mutex> lck(m_mtxCtrl);
|
||||
m_usb->control_msg(from_device, regs_access, type, addr, sizeof(value), &value);
|
||||
return value;
|
||||
}
|
||||
|
||||
|
||||
void GDevice::write_reg(int type, int addr, int value)
|
||||
{
|
||||
std::lock_guard<std::mutex> lck(m_mtxCtrl);
|
||||
m_usb->control_msg(to_device, regs_access, type, addr, sizeof(value), &value);
|
||||
}
|
||||
|
||||
void GDevice::set_option(Cam_Options option, unsigned int value)
|
||||
{
|
||||
unsigned int val = 0;
|
||||
switch (option)
|
||||
{
|
||||
case scanner_config:
|
||||
write_reg(USERDEFINE, ModeParam, value);
|
||||
break;
|
||||
case scanner_scan_skrew:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->skew_enable = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
case scanner_stample_enable:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->staple_enable = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
case scanner_doublePape_enable:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->double_paper = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
case scanner_stop_motor:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->scan_enable = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
case scanner_error_clean:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->error_clean = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
case scanner_Init_Status:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->status_init = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
case scanner_IIC_Config:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->iic_config = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
case scanner_Speed_Config:
|
||||
val = read_reg(MOTOR_BOARD, 0x00);
|
||||
((MotorSetting*)& val)->speed_set_enable = value;
|
||||
write_reg(MOTOR_BOARD, 0x00, val);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
int GDevice::get_option(Cam_Options option)
|
||||
{
|
||||
int value = 0;
|
||||
switch (option)
|
||||
{
|
||||
case scanner_cover_status:
|
||||
value = read_reg(1, 0x01);
|
||||
value = ((MotorStatus*)& value)->open_machine;
|
||||
break;
|
||||
case scanner_pick_paper_stauts:
|
||||
value = read_reg(1, 0x01);
|
||||
value = ((MotorStatus*)& value)->pick_failed;
|
||||
break;
|
||||
case scanner_jam_stauts:
|
||||
value = read_reg(1, 0x01);
|
||||
value = ((MotorStatus*)& value)->stop_jam;
|
||||
break;
|
||||
case scanner_paper_count:
|
||||
value = read_reg(1, 0x02);
|
||||
value = ((MotorMode*)& value)->scan_num;
|
||||
break;
|
||||
case scanner_double_paper:
|
||||
value = read_reg(1, 0x01);
|
||||
value= ((MotorStatus*)& value)->double_paper;
|
||||
break;
|
||||
case scanner_staple_state:
|
||||
value = read_reg(1, 0x01);
|
||||
value = ((MotorStatus*)& value)->staple;
|
||||
break;
|
||||
case scanner_skrew_state:
|
||||
value = read_reg(1, 0x01);
|
||||
value = ((MotorStatus*)& value)->papertilted;
|
||||
break;
|
||||
case scanner_paper_have:
|
||||
value = read_reg(MOTOR_BOARD, 0x02);
|
||||
value = ((Motor_Mode*)& value)->feeding_paper_ready;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
std::vector<Cam_Options> GDevice::support_options()
|
||||
{
|
||||
std::set<Cam_Options> options;
|
||||
options.insert(Cam_Options::scanner_exposure_blue);
|
||||
options.insert(Cam_Options::scanner_exposure_gray);
|
||||
options.insert(Cam_Options::scanner_exposure_red);
|
||||
|
||||
return std::vector<Cam_Options>(options.begin(), options.end());
|
||||
}
|
||||
|
||||
void GDevice::pick_paper(void)
|
||||
{
|
||||
MotorSetting ms;
|
||||
ms.value = read_reg(MOTOR_BOARD, 0x00);
|
||||
ms.pick_paper = 0;
|
||||
write_reg(MOTOR_BOARD, 0x00, ms.value);
|
||||
ms.pick_paper = 1;
|
||||
write_reg(MOTOR_BOARD, 0x00, ms.value);
|
||||
}
|
||||
|
||||
void GDevice::trigger_scan(void)
|
||||
{
|
||||
ScanTriger st;
|
||||
st.value = 0;
|
||||
write_reg(MAIN_BOARD, 0x02, st.value);
|
||||
st.triger = 1;
|
||||
write_reg(MAIN_BOARD, 0x02, st.value);
|
||||
}
|
||||
|
||||
bool GDevice::DataOn()
|
||||
{
|
||||
return read_reg(0x02, 0x03);
|
||||
}
|
|
@ -0,0 +1,87 @@
|
|||
#pragma once
|
||||
#include "IGDevice.h"
|
||||
#include <memory>
|
||||
#include <thread>
|
||||
#include <mutex>
|
||||
#include "BlockingQueue.h"
|
||||
#include <string>
|
||||
|
||||
class IUsb;
|
||||
class GDevice : public IGDevice
|
||||
{
|
||||
public:
|
||||
GDevice(std::shared_ptr<IUsb> usb);
|
||||
virtual ~GDevice();
|
||||
// ͨ¹ý IGDevice ¼Ì³Ð
|
||||
virtual bool open() override;
|
||||
virtual void close() override;
|
||||
virtual bool is_open() override;
|
||||
bool start(image_callback callfunc, void* userdata);
|
||||
void set_event_call(event_callback event_callfunc, void* userdata);
|
||||
virtual void stop() override;
|
||||
virtual int is_run() override;
|
||||
virtual void reset() override;
|
||||
|
||||
void write_dsp_fw(std::string path);
|
||||
|
||||
void write_devname(std::string name);
|
||||
std::string read_devname();
|
||||
|
||||
void write_reg(int type, int addr, int value);
|
||||
int read_reg(int type, int addr);
|
||||
|
||||
bool write_flash(unsigned int addr, void* data, int size);
|
||||
bool read_flash(unsigned int addr, void* data, int size);
|
||||
|
||||
void trigger_scan(void);
|
||||
|
||||
void write_pid(unsigned short pid);
|
||||
unsigned short read_pid();
|
||||
|
||||
private:
|
||||
void recv_main();
|
||||
void Int_main();
|
||||
|
||||
void init_cam();
|
||||
|
||||
int read_data(void* data, int lenght, int timeout);
|
||||
void read_frame(int index, int offset);
|
||||
int frame_size(int index);
|
||||
|
||||
|
||||
|
||||
|
||||
void pick_paper(void);
|
||||
|
||||
bool DataOn();
|
||||
|
||||
std::shared_ptr<IUsb> m_usb;
|
||||
const int buffer_size = 1204 * 1024;
|
||||
const int crtlBufferSize = 512;
|
||||
volatile bool m_bScan;
|
||||
volatile bool m_bListen;
|
||||
|
||||
std::shared_ptr<std::thread> m_threadInt;
|
||||
std::shared_ptr<std::thread> m_threadrecv;
|
||||
std::mutex m_mtxInt;
|
||||
std::mutex m_mtxCtrl;
|
||||
image_callback image_call;
|
||||
event_callback event_call;
|
||||
const int to_device = 0x40;
|
||||
const int from_device = 0xc0;
|
||||
const int regs_access = 0x0c;
|
||||
const int flash_access = 0x04;
|
||||
|
||||
const int regs_req = 0x0c;
|
||||
|
||||
BlockingQueue<int> image_indexs;
|
||||
|
||||
void* m_imagecall_userdata;
|
||||
void* m_eventcall_userdata;
|
||||
|
||||
|
||||
// ͨ¹ý IGDevice ¼Ì³Ð
|
||||
virtual void set_option(Cam_Options option,unsigned int value) override;
|
||||
virtual int get_option(Cam_Options option) override;
|
||||
virtual std::vector<Cam_Options> support_options() override;
|
||||
};
|
|
@ -0,0 +1,19 @@
|
|||
#include "stdafx.h"
|
||||
#include "GDeviceLists.h"
|
||||
#include "UsbScanEx.h"
|
||||
#include "GDevice.h"
|
||||
|
||||
|
||||
std::list<std::shared_ptr<IGDevice>> HGDeviceLists::FindAll()
|
||||
{
|
||||
std::list<std::shared_ptr<IGDevice>> cameraLists;
|
||||
|
||||
// std::list<std::shared_ptr<IUsb>> usbs = CyUsbList::find_vid_pid(0x04b4, 0x1004);
|
||||
std::list<std::shared_ptr<IUsb>> usbs = UsbScan_List::find_vid_pid(0x064b, 0x7823);
|
||||
|
||||
|
||||
for (auto i = usbs.begin(); i != usbs.end(); i++)
|
||||
cameraLists.push_back(std::shared_ptr<IGDevice>(new GDevice(*i)));
|
||||
|
||||
return cameraLists;
|
||||
}
|
|
@ -0,0 +1,12 @@
|
|||
#pragma once
|
||||
#include <list>
|
||||
#include <memory>
|
||||
|
||||
|
||||
class IGDevice;
|
||||
|
||||
class HGDeviceLists
|
||||
{
|
||||
public:
|
||||
static std::list<std::shared_ptr<IGDevice>> FindAll();
|
||||
};
|
|
@ -0,0 +1,54 @@
|
|||
#pragma once
|
||||
#include <vector>
|
||||
|
||||
|
||||
typedef void(*image_callback)(void*, int, int, int, void*);
|
||||
typedef void(*event_callback)(int, void*);
|
||||
|
||||
enum Cam_Options {
|
||||
scanner_config, //!< color, gray
|
||||
scanner_exposure_gray,
|
||||
scanner_exposure_green,
|
||||
scanner_exposure_blue,
|
||||
scanner_exposure_red,
|
||||
scanner_status,
|
||||
scanner_ad_gain,
|
||||
scanner_ad_offset,
|
||||
scanner_cover_status, //是否关闭盖子
|
||||
scanner_pick_paper_stauts, //是否搓纸失败
|
||||
scanner_jam_stauts, //是否卡纸
|
||||
scanner_paper_count, //扫描计数值
|
||||
scanner_trigger_scan, //触发扫描
|
||||
scanner_staple_state, //有无订书钉
|
||||
scanner_skrew_state, //歪斜状态
|
||||
scanner_paper_have, //有无纸张
|
||||
scanner_double_paper, //双张检测
|
||||
scanner_scan_triger,//扫描状态,1停止扫描,0正在扫描
|
||||
scanner_scan_skrew, //歪斜检测开关,1开,0关
|
||||
scanner_stample_enable, //订书钉检测使能,0:default;1:订书钉检测使能
|
||||
scanner_doublePape_enable,//双张检测使能
|
||||
scanner_stop_motor, //停止电机
|
||||
scanner_error_clean ,//异常清除
|
||||
scanner_Init_Status, //状态初始化使能
|
||||
scanner_IIC_Config, //IIC配置使能
|
||||
scanner_Speed_Config //速度配置使能
|
||||
|
||||
};
|
||||
|
||||
class IGDevice
|
||||
{
|
||||
public:
|
||||
virtual ~IGDevice() {}
|
||||
virtual bool open() = 0;
|
||||
virtual void close() = 0;
|
||||
virtual bool is_open() = 0;
|
||||
virtual bool start(image_callback imagecall= NULL, void* userdata = NULL) = 0;
|
||||
virtual void stop() = 0;
|
||||
virtual int is_run() = 0;
|
||||
virtual void reset() = 0;
|
||||
virtual void set_event_call(event_callback event_callfunc, void* userdata) = 0;
|
||||
virtual void set_option(Cam_Options option, unsigned int value) = 0;
|
||||
virtual int get_option(Cam_Options option) = 0;
|
||||
virtual std::vector<Cam_Options> support_options() = 0;
|
||||
};
|
||||
|
|
@ -0,0 +1,15 @@
|
|||
#pragma once
|
||||
class IUsb
|
||||
{
|
||||
public:
|
||||
virtual ~IUsb() {}
|
||||
virtual bool open() = 0;
|
||||
virtual bool close() = 0;
|
||||
virtual bool is_open() = 0;
|
||||
virtual bool is_connected() = 0;
|
||||
virtual void set_timeout(int timeout) = 0;
|
||||
virtual int read_bulk(void* data, int len) = 0;
|
||||
virtual int write_bulk(void* data, int len) = 0;
|
||||
virtual int read_int(void* data, int len) = 0;
|
||||
virtual int control_msg(int rtype, int req, int value, int index, int len, void* data) = 0;
|
||||
};
|
BIN
IndicatorDlg.cpp
BIN
IndicatorDlg.cpp
Binary file not shown.
133
MFC_UI.cpp
133
MFC_UI.cpp
|
@ -7,13 +7,21 @@
|
|||
|
||||
extern ChugaotwaindsApp theApp;
|
||||
|
||||
void DeleteWnd(CDialog* pWnd)
|
||||
{
|
||||
if (pWnd && pWnd->GetSafeHwnd())
|
||||
{
|
||||
pWnd->DestroyWindow();
|
||||
delete pWnd;
|
||||
}
|
||||
}
|
||||
|
||||
MFC_UI::MFC_UI(CTWAINDS_FreeImage *pDS)
|
||||
: CTWAIN_UI(pDS)
|
||||
, m_pChildWnd(0, DeleteWnd)
|
||||
, m_pDlg(0, DeleteWnd)
|
||||
, m_pIndicator(0, DeleteWnd)
|
||||
{
|
||||
m_pDlg = NULL;
|
||||
m_pChildWnd = NULL;
|
||||
indicator = NULL;
|
||||
indicatorCreated = false;
|
||||
}
|
||||
|
||||
|
||||
|
@ -42,123 +50,47 @@ TW_INT16 MFC_UI::DisplayTWAINGUI(TW_USERINTERFACE Data, bool bSetup, bool bIndic
|
|||
|
||||
if (Data.hParent)
|
||||
{
|
||||
if (m_pChildWnd == NULL)
|
||||
{
|
||||
CDialog* dlg = new CDialog();
|
||||
dlg->Create(IDD_DIALOGBACK);
|
||||
m_pChildWnd = dlg;
|
||||
theApp.m_pMainWnd = m_pChildWnd;
|
||||
|
||||
//long ll = GetWindowLong(m_pChildWnd->GetSafeHwnd(), GWL_STYLE);
|
||||
//SetWindowLong(m_pChildWnd->GetSafeHwnd(), GWL_STYLE, WS_CHILD | ll);
|
||||
m_pChildWnd = std::unique_ptr<CDialog, void(*)(CDialog*)>(new CDialog(), DeleteWnd);
|
||||
m_pChildWnd->Create(IDD_DIALOGBACK, CWnd::FromHandle((HWND)Data.hParent));
|
||||
long ll = GetWindowLong(m_pChildWnd->GetSafeHwnd(), GWL_STYLE);
|
||||
SetWindowLong(m_pChildWnd->GetSafeHwnd(), GWL_STYLE, WS_CHILD | ll);
|
||||
SetParent(m_pChildWnd->GetSafeHwnd(), (HWND)Data.hParent);
|
||||
//dlg->ShowWindow(SW_SHOWNORMAL);
|
||||
}
|
||||
}
|
||||
|
||||
if (Data.ShowUI)
|
||||
{
|
||||
if (m_pDlg == NULL)
|
||||
{
|
||||
m_pDlg = new TwainUIDlg(this, m_pChildWnd);
|
||||
m_pDlg->Create(IDD_DIALOG_TWAINUI, m_pChildWnd);
|
||||
}
|
||||
if (!bSetup)
|
||||
{
|
||||
m_pDlg->SetDlgItemTextA(IDC_CONFIRM, _T("ɨÃè"));
|
||||
}
|
||||
else
|
||||
{
|
||||
m_pDlg->SetDlgItemTextA(IDC_CONFIRM, _T("È·¶¨"));
|
||||
}
|
||||
m_pDlg.reset(new TwainUIDlg(this, m_pChildWnd.get()));
|
||||
m_pDlg->Create(IDD_DIALOG_TWAINUI, m_pChildWnd.get());
|
||||
m_pDlg->SetDlgItemText(IDC_CONFIRM,bSetup ? _T("È·¶¨") : _T("ɨÃè"));
|
||||
|
||||
|
||||
if (m_pDlg)
|
||||
{
|
||||
if (m_pDlg) {
|
||||
m_pDlg->ShowWindow(SW_SHOWNORMAL);
|
||||
SetWindowPos(m_pDlg->m_hWnd, HWND_TOPMOST, 500, 500, 0, 0, SWP_NOSIZE | SWP_NOMOVE);
|
||||
}
|
||||
else
|
||||
{
|
||||
else {
|
||||
ret = TWRC_FAILURE;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (bIndicators)
|
||||
{
|
||||
if (indicator == NULL)
|
||||
{
|
||||
indicator = new IndicatorDlg(this, Data.ShowUI ? m_pDlg : m_pChildWnd);
|
||||
}
|
||||
showUI = Data.ShowUI;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
void MFC_UI::DestroyTWAINGUI()
|
||||
{
|
||||
m_pIndicator.reset();
|
||||
m_pDlg.reset();
|
||||
m_pChildWnd.reset();
|
||||
|
||||
CTWAIN_UI::DestroyTWAINGUI();
|
||||
if (indicator != NULL)
|
||||
{
|
||||
indicator->DestroyWindow();
|
||||
delete indicator;
|
||||
indicator = NULL;
|
||||
indicatorCreated = false;
|
||||
}
|
||||
|
||||
if (m_pDlg != NULL)
|
||||
{
|
||||
m_pDlg->DestroyWindow();
|
||||
delete m_pDlg;
|
||||
m_pDlg = NULL;
|
||||
}
|
||||
|
||||
if (m_pChildWnd != NULL)
|
||||
{
|
||||
m_pChildWnd->DestroyWindow();
|
||||
delete m_pChildWnd;
|
||||
m_pChildWnd = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void MFC_UI::UpdateProgress(bool bShow, unsigned char ucProgress, unsigned int unPageNo, string strProgressTitle)
|
||||
{
|
||||
if (indicator == NULL)
|
||||
{
|
||||
indicator = new IndicatorDlg(this, NULL);
|
||||
}
|
||||
|
||||
if (!indicatorCreated)
|
||||
{
|
||||
indicator->Create(IDD_DIALOG_INDICATOR, m_pChildWnd);//m_pChildWnd
|
||||
indicatorCreated = true;
|
||||
}
|
||||
|
||||
if (bShow)
|
||||
{
|
||||
indicator->ShowWindow(SW_SHOWNORMAL);
|
||||
}
|
||||
else
|
||||
{
|
||||
indicator->DestroyWindow();
|
||||
delete indicator;
|
||||
indicator = NULL;
|
||||
indicatorCreated = false;
|
||||
}
|
||||
//indicator->ShowWindow(bShow?SW_SHOWNORMAL:SW_HIDE);
|
||||
if (m_pDlg)
|
||||
{
|
||||
m_pDlg->EnableWindow(bShow ? FALSE : TRUE);
|
||||
}
|
||||
}
|
||||
|
||||
unsigned int MFC_UI::MyMessageBox(string strMessage, string strTitle, unsigned int unIconID)
|
||||
{
|
||||
//QMessageBox msgBox(QMessageBox::NoIcon, strTitle.c_str(), strMessage.c_str());
|
||||
if (m_pChildWnd != NULL)
|
||||
{
|
||||
return ::MessageBox(m_pChildWnd->m_hWnd, strMessage.c_str(), strTitle.c_str(), unIconID);
|
||||
|
@ -173,9 +105,22 @@ bool MFC_UI::processEvent(pTW_EVENT _pEvent)
|
|||
if (IsDialogMessage(m_pDlg->m_hWnd, (LPMSG)(((pTW_EVENT)_pEvent)->pEvent)))
|
||||
{
|
||||
m_pDlg->SendMessage(_pEvent->TWMessage);
|
||||
//XdPrint("_pEvent->TWMessage %d\n",_pEvent->TWMessage);
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
void MFC_UI::ShowIndicators()
|
||||
{
|
||||
if (m_bIndicators) {
|
||||
m_pIndicator.reset(new IndicatorDlg(this));
|
||||
m_pIndicator->Create(IDD_DIALOG_INDICATOR,m_pDlg ? m_pDlg.get() : m_pChildWnd.get());
|
||||
m_pIndicator->ShowWindow(SW_SHOWNORMAL);
|
||||
}
|
||||
}
|
||||
|
||||
void MFC_UI::DestroyIndicators()
|
||||
{
|
||||
m_pIndicator.reset();
|
||||
}
|
||||
|
|
13
MFC_UI.h
13
MFC_UI.h
|
@ -1,6 +1,7 @@
|
|||
#pragma once
|
||||
#include "CTWAINDS_FreeImage.h"
|
||||
#include "TWAIN_UI.h"
|
||||
#include <memory>
|
||||
class TwainUIDlg;
|
||||
class CWnd;
|
||||
class IndicatorDlg;
|
||||
|
@ -29,11 +30,13 @@ public:
|
|||
bool processEvent(pTW_EVENT _pEvent);
|
||||
|
||||
private:
|
||||
TwainUIDlg* m_pDlg;
|
||||
CWnd* m_pChildWnd;
|
||||
IndicatorDlg* indicator;
|
||||
bool indicatorCreated;
|
||||
bool showUI;
|
||||
std::unique_ptr<CDialog, void(*)(CDialog*)> m_pChildWnd;
|
||||
std::unique_ptr<CDialog, void(*)(CDialog*)> m_pDlg;
|
||||
std::unique_ptr<CDialog, void(*)(CDialog*)> m_pIndicator;
|
||||
ChugaotwaindsApp* m_app;
|
||||
|
||||
// 通过 CTWAIN_UI 继承
|
||||
virtual void ShowIndicators() override;
|
||||
virtual void DestroyIndicators() override;
|
||||
};
|
||||
|
||||
|
|
|
@ -0,0 +1,34 @@
|
|||
#pragma once
|
||||
#include <chrono>
|
||||
|
||||
class StopWatch
|
||||
{
|
||||
public:
|
||||
StopWatch() {
|
||||
_start = std::chrono::steady_clock::now();
|
||||
}
|
||||
|
||||
void reset() {
|
||||
_start = std::chrono::steady_clock::now();
|
||||
}
|
||||
|
||||
double elapsed_s() {
|
||||
return std::chrono::duration<double>(std::chrono::steady_clock::now() - _start).count();
|
||||
}
|
||||
|
||||
double elapsed_ms() {
|
||||
return std::chrono::duration<double, std::milli>(std::chrono::steady_clock::now() - _start).count();
|
||||
}
|
||||
|
||||
double elapsed_us() {
|
||||
return std::chrono::duration<double, std::micro>(std::chrono::steady_clock::now() - _start).count();
|
||||
}
|
||||
|
||||
double elapsed_ns() {
|
||||
return std::chrono::duration<double, std::nano>(std::chrono::steady_clock::now() - _start).count();
|
||||
}
|
||||
|
||||
private:
|
||||
std::chrono::steady_clock::time_point _start;
|
||||
};
|
||||
|
|
@ -194,6 +194,7 @@ void CTWAIN_UI::DestroyTWAINGUI()
|
|||
{
|
||||
m_bScanning=false;
|
||||
memset(&m_EnableDSdata,0,sizeof(TW_USERINTERFACE));
|
||||
|
||||
}
|
||||
void CTWAIN_UI::UpdateProgress(bool bShow, unsigned char ucProgress, unsigned int unPageNo, string strProgressTitle)
|
||||
{
|
||||
|
|
|
@ -73,6 +73,8 @@ public:
|
|||
* Close the user interface for TWAIN
|
||||
*/
|
||||
virtual void DestroyTWAINGUI();
|
||||
virtual void ShowIndicators() = 0;
|
||||
virtual void DestroyIndicators() = 0;
|
||||
virtual void UpdateProgress(bool bShow, unsigned char ucProgress, unsigned int unPageNo, string strProgressTitle);
|
||||
virtual void Scan();
|
||||
virtual void Cancel();
|
||||
|
|
BIN
TwainUIDlg.cpp
BIN
TwainUIDlg.cpp
Binary file not shown.
|
@ -0,0 +1,335 @@
|
|||
#include "stdafx.h"
|
||||
#include "UsbScanEx.h"
|
||||
#include <tchar.h>
|
||||
#include <winioctl.h>
|
||||
|
||||
UsbScanEx::UsbScanEx(int index)
|
||||
{
|
||||
m_h_dev = INVALID_HANDLE_VALUE;
|
||||
timeout = 100;
|
||||
m_h_index = index;
|
||||
memset(ov, 0, sizeof(ov));
|
||||
CTRL_IN_OUT = 3;
|
||||
for (int i = 0; i < (sizeof(ov) / sizeof(ov[0])); i++)
|
||||
ov[i].hEvent = CreateEvent(NULL, FALSE, FALSE, NULL);
|
||||
}
|
||||
|
||||
UsbScanEx::~UsbScanEx()
|
||||
{
|
||||
if (m_h_dev != INVALID_HANDLE_VALUE)
|
||||
close();
|
||||
|
||||
for (int i = 0; i < (sizeof(ov) / sizeof(ov[0])); i++)
|
||||
CloseHandle(ov[i].hEvent);
|
||||
}
|
||||
|
||||
bool UsbScanEx::open()
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
TCHAR szDevPath[MAX_PATH] = { 0 };
|
||||
DWORD cbRet = 0;
|
||||
|
||||
USBSCAN_TIMEOUT ut;
|
||||
ut.TimeoutEvent = 1;
|
||||
ut.TimeoutRead = 1;
|
||||
ut.TimeoutWrite = 1;
|
||||
|
||||
_stprintf(szDevPath, TEXT("\\\\.\\Usbscan%d"), m_h_index);
|
||||
m_h_dev = CreateFile(szDevPath,
|
||||
GENERIC_READ | GENERIC_WRITE,
|
||||
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
FILE_FLAG_OVERLAPPED,
|
||||
NULL);
|
||||
if (m_h_dev != INVALID_HANDLE_VALUE) {
|
||||
m_b_is_connected = TRUE;
|
||||
b_ret = DeviceIoControl(m_h_dev, (DWORD)IOCTL_GET_PIPE_CONFIGURATION,
|
||||
NULL, 0, &m_usbscan_config, sizeof(USBSCAN_PIPE_CONFIGURATION),
|
||||
&cbRet, NULL);
|
||||
if (b_ret && m_usbscan_config.NumberOfPipes > 0) {
|
||||
for (int by_i = 0x00; (ULONG)by_i < m_usbscan_config.NumberOfPipes; by_i++) {
|
||||
TCHAR szPipePath[MAX_PATH] = { 0 };
|
||||
_stprintf(szPipePath, TEXT("\\\\.\\Usbscan%d\\%d"), m_h_index, by_i);
|
||||
m_usb_pipes[by_i].pipe_info = m_usbscan_config.PipeInfo[by_i];
|
||||
m_usb_pipes[by_i].h_pipe = CreateFile(szPipePath,
|
||||
GENERIC_READ | GENERIC_WRITE,
|
||||
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
FILE_FLAG_OVERLAPPED,
|
||||
NULL);
|
||||
if (m_usbscan_config.PipeInfo[by_i].PipeType == USBSCAN_PIPE_INTERRUPT) {
|
||||
INT_IN = by_i;
|
||||
}
|
||||
else {
|
||||
if (m_usbscan_config.PipeInfo[by_i].EndpointAddress & 0x80) {
|
||||
BULK_IN = by_i;
|
||||
}
|
||||
else {
|
||||
BULK_OUT = by_i;
|
||||
}
|
||||
}
|
||||
b_ret = DeviceIoControl(m_usb_pipes[by_i].h_pipe, IOCTL_SET_TIMEOUT, &ut, sizeof(ut), NULL, 0, &cbRet, NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
CloseHandle(m_h_dev);
|
||||
m_h_dev = INVALID_HANDLE_VALUE;
|
||||
}
|
||||
return m_h_dev;
|
||||
}
|
||||
|
||||
bool UsbScanEx::close()
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
BYTE by_i = 0x00;
|
||||
|
||||
if (m_h_dev != INVALID_HANDLE_VALUE) {
|
||||
BOOL bState = FALSE;
|
||||
DWORD cbRet = 0;
|
||||
OVERLAPPED overlapped;
|
||||
PIPE_TYPE pipeType = ALL_PIPE;
|
||||
|
||||
memset(&overlapped, 0, sizeof(OVERLAPPED));
|
||||
overlapped.hEvent =
|
||||
CreateEvent(NULL, // pointer to security attributes
|
||||
FALSE, // automatic reset
|
||||
FALSE, // initialize to nosignaled
|
||||
NULL); // pointer to the event-object name
|
||||
bState =
|
||||
DeviceIoControl(m_h_dev,
|
||||
(DWORD)IOCTL_CANCEL_IO,
|
||||
(LPVOID)&pipeType,
|
||||
sizeof(PIPE_TYPE),
|
||||
NULL,
|
||||
0,
|
||||
&cbRet,
|
||||
&overlapped);
|
||||
WaitForSingleObject(overlapped.hEvent, 1000);
|
||||
CloseHandle(overlapped.hEvent);
|
||||
|
||||
for (by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++) {
|
||||
CancelIo(m_usb_pipes[by_i].h_pipe);
|
||||
CloseHandle(m_usb_pipes[by_i].h_pipe);
|
||||
m_usb_pipes[by_i].h_pipe = INVALID_HANDLE_VALUE;
|
||||
}
|
||||
|
||||
CancelIo(m_h_dev);
|
||||
b_ret = CloseHandle(m_h_dev);
|
||||
if (b_ret) {
|
||||
m_h_dev = INVALID_HANDLE_VALUE;
|
||||
b_ret = TRUE;
|
||||
}
|
||||
}
|
||||
m_b_is_connected = FALSE;
|
||||
return b_ret;
|
||||
}
|
||||
|
||||
void UsbScanEx::set_timeout(int timeout)
|
||||
{
|
||||
this->timeout = timeout;
|
||||
}
|
||||
|
||||
int UsbScanEx::read_bulk(void* data, int len)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
HANDLE h_pipe = m_usb_pipes[BULK_IN].h_pipe;
|
||||
unsigned long pdw_ret = len;
|
||||
LPOVERLAPPED lp_overlap = ov+BULK_IN;
|
||||
lp_overlap->Internal = 0;
|
||||
lp_overlap->InternalHigh = 0;
|
||||
lp_overlap->Offset = 0;
|
||||
lp_overlap->OffsetHigh = 0;
|
||||
lp_overlap->Pointer = 0;
|
||||
|
||||
if (m_h_dev != NULL) {
|
||||
b_ret = ReadFile(h_pipe, data, len, &pdw_ret, lp_overlap);
|
||||
|
||||
if (b_ret) {
|
||||
return pdw_ret;
|
||||
}
|
||||
else {
|
||||
switch (GetLastError())
|
||||
{
|
||||
case ERROR_IO_PENDING:
|
||||
GetOverlappedResult(h_pipe, lp_overlap, &pdw_ret, TRUE);
|
||||
return pdw_ret;
|
||||
|
||||
case ERROR_FILE_NOT_FOUND:
|
||||
m_b_is_connected = false;
|
||||
break;
|
||||
default:
|
||||
int a = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int UsbScanEx::write_bulk(void* data, int len)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
HANDLE h_pipe = m_usb_pipes[BULK_OUT].h_pipe;
|
||||
void* p_data = data;
|
||||
unsigned long dw_size = len;
|
||||
|
||||
LPOVERLAPPED lp_overlap = ov + BULK_OUT;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return TRUE;
|
||||
|
||||
b_ret = WriteFile(h_pipe, p_data, dw_size, &dw_size, lp_overlap);
|
||||
if (b_ret) {
|
||||
return dw_size;
|
||||
}
|
||||
else {
|
||||
switch (GetLastError())
|
||||
{
|
||||
case ERROR_IO_PENDING:
|
||||
GetOverlappedResult(h_pipe, lp_overlap, &dw_size, TRUE);
|
||||
return dw_size;
|
||||
|
||||
case ERROR_FILE_NOT_FOUND:
|
||||
m_b_is_connected = false;
|
||||
break;
|
||||
default:
|
||||
int a = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int UsbScanEx::control_msg(int rtype, int req, int value, int index, int len, void* data)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
_IO_BLOCK_EX irp;
|
||||
DWORD dw_ret;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return TRUE;
|
||||
irp.uOffset = value;
|
||||
irp.uLength = len;
|
||||
irp.uIndex = index;
|
||||
irp.pbyData = (LPBYTE)data;
|
||||
irp.fTransferDirectionIn = (rtype >> 7);
|
||||
irp.bRequest = req;
|
||||
irp.bmRequestType = (rtype >> 5) & 0x03;
|
||||
|
||||
LPOVERLAPPED lp_overlap = ov + CTRL_IN_OUT;
|
||||
b_ret = DeviceIoControl(m_h_dev, IOCTL_SEND_USB_REQUEST, &irp, sizeof(irp), data, len, &dw_ret, lp_overlap);
|
||||
|
||||
if (!b_ret)
|
||||
b_ret = WaitForSingleObject(lp_overlap->hEvent, timeout) == WAIT_OBJECT_0;
|
||||
|
||||
return b_ret;
|
||||
}
|
||||
|
||||
bool UsbScanEx::is_open()
|
||||
{
|
||||
return m_h_dev != INVALID_HANDLE_VALUE;
|
||||
}
|
||||
|
||||
bool UsbScanEx::is_connected()
|
||||
{
|
||||
return is_open();//m_b_is_connected;
|
||||
}
|
||||
|
||||
int UsbScanEx::read_int(void* data, int len)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
DWORD dw_ret = 0L;
|
||||
HANDLE h_pipe = m_usb_pipes[INT_IN].h_pipe;
|
||||
LPOVERLAPPED lp_overlap = ov + INT_IN;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return FALSE;
|
||||
|
||||
b_ret = DeviceIoControl(h_pipe, (DWORD)IOCTL_WAIT_ON_DEVICE_EVENT, NULL, 0,
|
||||
data, len, &dw_ret, lp_overlap);
|
||||
|
||||
if (b_ret) {
|
||||
return dw_ret;
|
||||
}
|
||||
else {
|
||||
switch (GetLastError())
|
||||
{
|
||||
case ERROR_IO_PENDING:
|
||||
GetOverlappedResult(h_pipe, lp_overlap, &dw_ret, TRUE);
|
||||
return dw_ret;
|
||||
|
||||
case ERROR_FILE_NOT_FOUND:
|
||||
m_b_is_connected = false;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
UsbScan_List::~UsbScan_List()
|
||||
{
|
||||
}
|
||||
|
||||
std::list<std::shared_ptr<IUsb>> UsbScan_List::find_all()
|
||||
{
|
||||
auto devs = find_all_usb();
|
||||
std::list<std::shared_ptr<IUsb>> usbs;
|
||||
for (auto inter = devs.begin(); inter != devs.end(); inter++) {
|
||||
usbs.push_back(std::shared_ptr<IUsb>(new UsbScanEx(inter->index)));
|
||||
}
|
||||
return usbs;
|
||||
}
|
||||
|
||||
std::list<std::shared_ptr<IUsb>> UsbScan_List::find_vid_pid(int vid, int pid)
|
||||
{
|
||||
auto devs = find_all_usb();
|
||||
std::list<std::shared_ptr<IUsb>> usbs;
|
||||
for (auto inter = devs.begin(); inter != devs.end(); inter++) {
|
||||
if (inter->vid == vid && inter->pid == pid)
|
||||
usbs.push_back(std::shared_ptr<IUsb>(new UsbScanEx(inter->index)));
|
||||
}
|
||||
return usbs;
|
||||
}
|
||||
|
||||
std::list<usb_scan_dev_info> UsbScan_List::find_all_usb()
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
DWORD cbRet = 0;
|
||||
TCHAR szDevPath[MAX_PATH] = { 0 };
|
||||
DEVICE_DESCRIPTOR dev_desc;
|
||||
HANDLE h_dev;
|
||||
std::list<usb_scan_dev_info> usbs;
|
||||
usb_scan_dev_info dev_info;
|
||||
|
||||
for (int i = 0; i < 1024; i++) {
|
||||
|
||||
_stprintf(szDevPath, TEXT("\\\\.\\Usbscan%d"), i);
|
||||
h_dev = CreateFile(szDevPath,
|
||||
GENERIC_READ | GENERIC_WRITE,
|
||||
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
FILE_FLAG_OVERLAPPED,
|
||||
NULL);
|
||||
if (h_dev != INVALID_HANDLE_VALUE) {
|
||||
b_ret = DeviceIoControl(h_dev, (DWORD)IOCTL_GET_DEVICE_DESCRIPTOR,
|
||||
&dev_desc, sizeof(dev_desc), &dev_desc, sizeof(dev_desc),
|
||||
&cbRet, NULL);
|
||||
if (b_ret != 0) {
|
||||
dev_info.index = i;
|
||||
dev_info.vid = dev_desc.usVendorId;
|
||||
dev_info.pid = dev_desc.usProductId;
|
||||
usbs.push_back(dev_info);
|
||||
}
|
||||
CloseHandle(h_dev);
|
||||
}
|
||||
}
|
||||
|
||||
return usbs;
|
||||
}
|
|
@ -0,0 +1,76 @@
|
|||
#pragma once
|
||||
#include <Windows.h>
|
||||
#include <usbscan.h>
|
||||
#include <memory>
|
||||
#include <list>
|
||||
#include "IUsb.h"
|
||||
|
||||
|
||||
#pragma pack(1)
|
||||
struct tag_usb_pipe
|
||||
{
|
||||
HANDLE h_pipe;
|
||||
USBSCAN_PIPE_INFORMATION pipe_info;
|
||||
OVERLAPPED overlap;
|
||||
};
|
||||
typedef struct tag_usb_pipe usb_pipe_t, * pusb_pipe_t;
|
||||
#pragma pack()
|
||||
|
||||
typedef struct tag_usb_scan_dev_info
|
||||
{
|
||||
WORD vid;
|
||||
WORD pid;
|
||||
WORD index;
|
||||
}usb_scan_dev_info, * pusb_scan_dev_info;
|
||||
|
||||
typedef struct tag_usb_scan_dev
|
||||
{
|
||||
USHORT _NumberOfDevs;
|
||||
tag_usb_scan_dev_info dev_infos[1024];
|
||||
}usb_scan_dev, * pusb_scan_dev;
|
||||
|
||||
class UsbScanEx : public IUsb
|
||||
{
|
||||
public:
|
||||
UsbScanEx(int index);
|
||||
virtual ~UsbScanEx();
|
||||
// ͨ¹ý IUsb ¼Ì³Ð
|
||||
virtual bool open() override;
|
||||
virtual bool close() override;
|
||||
virtual void set_timeout(int timeout) override;
|
||||
virtual int read_bulk(void *data, int len) override;
|
||||
virtual int write_bulk(void *data, int len) override;
|
||||
virtual int control_msg(int rtype, int req, int value, int index, int len, void* data) override;
|
||||
virtual bool is_open() override;
|
||||
virtual bool is_connected() override;
|
||||
virtual int read_int(void* data, int len) override;
|
||||
|
||||
private:
|
||||
|
||||
int BULK_OUT;
|
||||
int BULK_IN;
|
||||
int INT_IN;
|
||||
int CTRL_IN_OUT;
|
||||
USBSCAN_PIPE_CONFIGURATION m_usbscan_config;
|
||||
usb_pipe_t m_usb_pipes[MAX_NUM_PIPES];
|
||||
HANDLE m_h_dev;
|
||||
bool m_b_is_connected;
|
||||
int m_h_index;
|
||||
int timeout;
|
||||
OVERLAPPED ov[4];
|
||||
};
|
||||
|
||||
|
||||
class UsbScan_List
|
||||
{
|
||||
public:
|
||||
~UsbScan_List();
|
||||
|
||||
static std::list<std::shared_ptr<IUsb>> find_all();
|
||||
static std::list<std::shared_ptr<IUsb>> find_vid_pid(int vid, int pid);
|
||||
|
||||
private:
|
||||
static std::list<usb_scan_dev_info> find_all_usb();
|
||||
UsbScan_List();
|
||||
UsbScan_List(uint16_t vendor_id, uint16_t product_id);
|
||||
};
|
|
@ -0,0 +1,147 @@
|
|||
#pragma once
|
||||
#define FLASH_ADDR_START (0x300000) //!<DSP 读取flash起始地址
|
||||
|
||||
#define CONT_ADDR (FLASH_ADDR_START) //!< 指向flash存储定义的首地址 4字节存储扫描总数 所属空间4字节
|
||||
#define PID_ADDR (CONT_ADDR+4) //!<CONT_ADDR向后偏移4字节 指向PID存储位置 2字节存储pid(unsigned short类型)
|
||||
#define VID_ADDR (PID_ADDR+2) //!<PID_ADDR向后偏移2字节 指向VID_ADDR首地址 2字节存储vid 所属空间大小2字节
|
||||
#define DEVNAME_ADDR (VID_ADDR+2) //!<VID_ADDR向后偏移2字节 指向DEVNAME_ADDR首地址 所属空间大小64字节
|
||||
#define SERIAL_ADDR (DEVNAME_ADDR+64) //!<DEVNAME_ADDR向后偏移64字节 指向序列号flash存储地址 所属空间大小12字节
|
||||
#define MOTORBOARD_CONFIG_ADDR (SERIAL_ADDR+12) //!<SERIAL_ADDR偏移12字节 指向 电机板flash存储数据头地址 所属空间3字节
|
||||
#define EXPOSURE_ADDR (MOTORBOARD_CONFIG_ADDR+3) //!<MOTORBOARD_CONFIG_ADDR偏移8字节 指向 电机板flash存储曝光数据头地址
|
||||
//!<所属空间8字节 存储空间 存储方式Gray(2)+B(2)+G(2)+R(2)
|
||||
#define AD_ADDR (EXPOSURE_ADDR+8) //!<EXPOSURE_ADDR
|
||||
#define FPGA_FLAT_ADDR (AD_ADDR+28) //!<所属空间918+612字节
|
||||
//flash size
|
||||
#define FLASH_200_COLOR (2448 * 8)
|
||||
#define FLASH_200_GRAY (2448)
|
||||
#define ARRAY_200 (612)
|
||||
#define ARRAY_300 (918)
|
||||
#define FLASH_300_COLOR (3672 * 8)
|
||||
#define FLASH_300_GRAY (3672)
|
||||
|
||||
|
||||
|
||||
typedef enum {
|
||||
Cmd_None,
|
||||
Cmd_Line_Count,
|
||||
Cmd_Mode_Freque,
|
||||
Cmd_Ad_Front,
|
||||
Cmd_Ad_Back,
|
||||
Cmd_Exposure_Back1,
|
||||
Cmd_Exposure_Back2,
|
||||
Cmd_Exposure_Front1,
|
||||
Cmd_Exposure_Front2,
|
||||
Cmd_Start,
|
||||
Cmd_Stop,
|
||||
Cmd_Status,
|
||||
Cmd_Width,
|
||||
Cmd_Sensor_Count_Channel,
|
||||
Cmd_Dma_Status,
|
||||
Cmd_Dma_Stransfer,
|
||||
Cmd_Dma_Size,
|
||||
Cmd_Num
|
||||
} FPGA_CMD;
|
||||
|
||||
typedef enum
|
||||
{
|
||||
MAIN_BOARD,
|
||||
MOTOR_BOARD,
|
||||
USERDEFINE,
|
||||
IMAGEREGS,
|
||||
BOARDFLAGNUM
|
||||
} BOARD_FLAG;
|
||||
|
||||
|
||||
typedef enum User_Define_Regs
|
||||
{
|
||||
ModeParam,
|
||||
WriteCorrectData,
|
||||
ReadCorrectData,
|
||||
BulkInOn
|
||||
} UserDefineRegs;
|
||||
|
||||
typedef union Motor_Setting {
|
||||
unsigned int value;
|
||||
struct {
|
||||
unsigned int scan_enable : 1;
|
||||
unsigned int dpi : 1;
|
||||
unsigned int paper : 1;
|
||||
unsigned int double_paper : 1;
|
||||
unsigned int staple_enable : 1;
|
||||
unsigned int error_clean : 1;
|
||||
unsigned int status_init : 1;
|
||||
unsigned int pick_paper : 1;
|
||||
unsigned int skew_enable : 1;
|
||||
unsigned int skew_parameter : 3;
|
||||
unsigned int key_staple_enable : 1;
|
||||
unsigned int iic_config_addr : 7;
|
||||
unsigned int iic_config : 1;
|
||||
unsigned int v_setting : 2;
|
||||
unsigned int speed_set_enable : 1;
|
||||
unsigned int papar_type : 4;
|
||||
unsigned int color_model : 1;
|
||||
unsigned int reserve : 3;
|
||||
};
|
||||
} MotorSetting;
|
||||
|
||||
typedef union Motor_Status {
|
||||
unsigned int value;
|
||||
struct {
|
||||
unsigned int scan_pulse : 1;
|
||||
unsigned int m1_paper_sin : 1;
|
||||
unsigned int open_machine : 1;
|
||||
unsigned int pick_failed : 1;
|
||||
unsigned int stop_jam : 1;
|
||||
unsigned int double_paper : 1;
|
||||
unsigned int staple : 1;
|
||||
unsigned int papertilted : 1;
|
||||
unsigned int count_pulse : 1;
|
||||
unsigned int scan_mode_change : 1;
|
||||
unsigned int motor_status : 1;
|
||||
unsigned int keep_last_paper : 1;
|
||||
};
|
||||
} MotorStatus;
|
||||
|
||||
typedef union Motor_Mode {
|
||||
unsigned int value;
|
||||
struct {
|
||||
unsigned int scan_num : 14;
|
||||
unsigned int scan_mode : 2;
|
||||
unsigned int feeding_paper_ready : 1;
|
||||
};
|
||||
} MotorMode;
|
||||
|
||||
typedef union Scan_Triger {
|
||||
unsigned int value;
|
||||
struct {
|
||||
unsigned int triger : 1;
|
||||
};
|
||||
} ScanTriger;
|
||||
|
||||
|
||||
typedef enum Color_Mode
|
||||
{
|
||||
Gray = 0,
|
||||
Color = 1
|
||||
}ColorMode;
|
||||
|
||||
typedef enum Burst_Mode
|
||||
{
|
||||
SingleInternalTrigger = 1,
|
||||
SingleExternalTrigger,
|
||||
ContinuousInternalTrigger,
|
||||
ContinuousExternalTrigger,
|
||||
}BurstMode;
|
||||
|
||||
typedef union Reg_2Short {
|
||||
int value;
|
||||
struct {
|
||||
unsigned short short1;
|
||||
unsigned short short2;
|
||||
};
|
||||
struct
|
||||
{
|
||||
unsigned short val[2];
|
||||
};
|
||||
} Reg2Short;
|
||||
|
79
gscn_drv.cpp
79
gscn_drv.cpp
|
@ -8,6 +8,7 @@
|
|||
#include "ImageApply.h"
|
||||
#include "hugaotwainds.h"
|
||||
#include "filetools.h"
|
||||
#include "UsbScanEx.h"
|
||||
|
||||
extern ChugaotwaindsApp theApp;
|
||||
|
||||
|
@ -34,14 +35,24 @@ GScn_Drv::~GScn_Drv()
|
|||
|
||||
void GScn_Drv::open(int vid, int pid)
|
||||
{
|
||||
usb_scan_dev devs = Devices(vid, pid);
|
||||
//usb_scan_dev devs = Devices(vid, pid);
|
||||
|
||||
if (devs._NumberOfDevs != 0)
|
||||
{
|
||||
m_usb.open(devs.dev_infos[0].index);//同时存在多个同种扫描设备时,默认选取第一个vid pid匹配的设备
|
||||
//if (devs._NumberOfDevs != 0)
|
||||
//{
|
||||
// m_usb.open(devs.dev_infos[0].index);//同时存在多个同种扫描设备时,默认选取第一个vid pid匹配的设备
|
||||
// GetFWVersion();
|
||||
// GetSerialNum();
|
||||
//}
|
||||
auto usbs = UsbScan_List::find_vid_pid(vid, pid);
|
||||
if (!usbs.empty()) {
|
||||
m_usb = *usbs.begin();
|
||||
m_usb->open();
|
||||
if (m_usb->is_open()) {
|
||||
GetFWVersion();
|
||||
GetSerialNum();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static void DoEvents()
|
||||
|
@ -121,7 +132,7 @@ void GScn_Drv::pushMat(JpegBuffer& data)
|
|||
|
||||
BOOL GScn_Drv::IsConnected()
|
||||
{
|
||||
return m_usb.is_connected();
|
||||
return m_usb->is_connected();
|
||||
}
|
||||
|
||||
|
||||
|
@ -129,9 +140,8 @@ cv::Mat GScn_Drv::Get_Img_Data(int bufferSize)
|
|||
{
|
||||
cv::Mat iData(1, bufferSize, CV_8UC1);
|
||||
USBCB usbcb = { GET_IMAGE,0,(UINT32)bufferSize };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb.Read_Data(iData.data, bufferSize, 2000, &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(usbcb));
|
||||
m_usb->read_bulk(iData.data, bufferSize);
|
||||
return iData;
|
||||
}
|
||||
|
||||
|
@ -187,7 +197,7 @@ DWORD GScn_Drv::usbmain()
|
|||
devState = DEV_ISRUNNING;
|
||||
while (devState == DEV_ISRUNNING)
|
||||
{
|
||||
if (!m_usb.is_connected())
|
||||
if (!m_usb->is_connected())
|
||||
{
|
||||
this_thread::sleep_for(chrono::milliseconds(200));
|
||||
continue;
|
||||
|
@ -260,13 +270,12 @@ DWORD GScn_Drv::usbmain()
|
|||
|
||||
void GScn_Drv::config_params(SFreeImage & params)
|
||||
{
|
||||
if (m_usb.is_connected())
|
||||
if (m_usb->is_connected())
|
||||
{
|
||||
hgConfigClass cfg(params);
|
||||
UINT32 cfgdata = cfg.GetData();
|
||||
USBCB usbcb = { CONFIGURED_DATA,cfgdata,0 };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(USBCB), &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(USBCB));
|
||||
setdecodepixtype(params.m_HardWareParams.PixType);
|
||||
m_pImages.setparam(params);
|
||||
}
|
||||
|
@ -275,12 +284,12 @@ void GScn_Drv::config_params(SFreeImage & params)
|
|||
///////////////////////////////////////////////////////////////////////////
|
||||
void GScn_Drv::Scanner_StartScan(UINT16 count)
|
||||
{
|
||||
if (m_usb.is_connected())
|
||||
if (m_usb->is_connected())
|
||||
{
|
||||
std::lock_guard<std::mutex> lck(m_imgLocker);
|
||||
DWORD transfer;
|
||||
USBCB usbcb = { START_COMMAND,(UINT32)count ,0 };
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(usbcb));
|
||||
run();
|
||||
m_pImages.SetScanningStatus(true);
|
||||
m_pImages.run();
|
||||
|
@ -291,16 +300,15 @@ void GScn_Drv::Scanner_StartScan(UINT16 count)
|
|||
std::string GScn_Drv::GetFWVersion()
|
||||
{
|
||||
XdPrint("GetFWVersion \n");
|
||||
if (m_usb.is_connected())
|
||||
if (m_usb->is_connected())
|
||||
{
|
||||
std::lock_guard<std::mutex> lck(m_imgLocker);
|
||||
if (fwVersion.empty())
|
||||
{
|
||||
fwVersion = " ";
|
||||
USBCB usbcb = { GET_FW_VERSION,8,0 };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb.Read_Data(&fwVersion[0], 8, 200, &transfer);
|
||||
m_usb->write_bulk( &usbcb, sizeof(usbcb));
|
||||
m_usb->read_bulk(&fwVersion[0], 8);
|
||||
}
|
||||
return fwVersion;
|
||||
}
|
||||
|
@ -310,16 +318,15 @@ std::string GScn_Drv::GetFWVersion()
|
|||
///////////////////////////////////////////////////////////////////////////
|
||||
std::string GScn_Drv::GetSerialNum()
|
||||
{
|
||||
if (m_usb.is_connected())
|
||||
if (m_usb->is_connected())
|
||||
{
|
||||
std::lock_guard<std::mutex> lck(m_imgLocker);
|
||||
if (SerialNum.empty())
|
||||
{
|
||||
SerialNum = " ";
|
||||
USBCB usbcb = { GET_SERIAL,12,0 };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb.Read_Data(&SerialNum[0], 12, 200, &transfer);
|
||||
m_usb->write_bulk( &usbcb, sizeof(usbcb));
|
||||
m_usb->read_bulk(&SerialNum[0], 12);
|
||||
}
|
||||
return SerialNum;
|
||||
}
|
||||
|
@ -329,16 +336,15 @@ std::string GScn_Drv::GetSerialNum()
|
|||
///////////////////////////////////////////////////////////////////////////
|
||||
USBCB GScn_Drv::Get_Scanner_Status()
|
||||
{
|
||||
if (!m_usb.is_connected())
|
||||
if (!m_usb->is_connected())
|
||||
{
|
||||
|
||||
USBCB errorType = { NO_COMMAND ,PC_SCAN_BUSY_or_ERROR ,0 };
|
||||
return errorType;
|
||||
}
|
||||
USBCB usbcb = { GET_DSP_STATUS ,0,0 };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb.Read_Data(&usbcb, sizeof(usbcb), 200, &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(usbcb));
|
||||
m_usb->read_bulk(&usbcb, sizeof(usbcb));
|
||||
return usbcb;
|
||||
}
|
||||
|
||||
|
@ -353,28 +359,26 @@ bool GScn_Drv::is_scan()
|
|||
BOOL GScn_Drv::Get_Scanner_PaperOn()
|
||||
{
|
||||
XdPrint("Get_Scanner_PaperOn \n");
|
||||
if (!m_usb.is_connected())
|
||||
if (!m_usb->is_open())
|
||||
{
|
||||
return FALSE;
|
||||
}
|
||||
USBCB usbcb = { GET_PAPER_STATUS ,0,0 };
|
||||
DWORD transfer;
|
||||
std::lock_guard<std::mutex> lck(m_imgLocker);
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb.bulk_in(0x00, &usbcb, sizeof(usbcb), 200, &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(usbcb));
|
||||
m_usb->read_bulk( &usbcb, sizeof(usbcb));
|
||||
return usbcb.u32_Data != 0;
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
void GScn_Drv::Pop_Image()
|
||||
{
|
||||
if (!m_usb.is_connected())
|
||||
if (!m_usb->is_open())
|
||||
{
|
||||
return;
|
||||
}
|
||||
USBCB usbcb = { POP_IMAGE ,0,0 };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(usbcb));
|
||||
}
|
||||
|
||||
void GScn_Drv::trim(std::string &s)
|
||||
|
@ -392,25 +396,24 @@ void GScn_Drv::trim(std::string &s)
|
|||
///////////////////////////////////////////////////////////////////////////
|
||||
void GScn_Drv::Stop_scan()
|
||||
{
|
||||
if (!m_usb.is_connected())
|
||||
if (!m_usb->is_connected())
|
||||
{
|
||||
return;
|
||||
}
|
||||
std::lock_guard<std::mutex> lck(m_imgLocker);
|
||||
USBCB usbcb = { STOP ,0,0 };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(usbcb));
|
||||
}
|
||||
|
||||
void GScn_Drv::ResetScanner()
|
||||
{
|
||||
if (!m_usb.is_connected())
|
||||
if (!m_usb->is_connected())
|
||||
return;
|
||||
|
||||
std::lock_guard<std::mutex> lck(m_imgLocker);
|
||||
USBCB usbcb = { INIT_HARDWARE_SYS ,0,0 };
|
||||
DWORD transfer;
|
||||
m_usb.bulk_out(0x00, &usbcb, sizeof(usbcb), &transfer);
|
||||
m_usb->write_bulk(&usbcb, sizeof(usbcb));
|
||||
}
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////
|
||||
|
|
35
gscn_drv.h
35
gscn_drv.h
|
@ -1,5 +1,4 @@
|
|||
#pragma once
|
||||
#include "scn_usb.h"
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
#include <string>
|
||||
|
@ -37,11 +36,38 @@ class
|
|||
DiscardBlank;
|
||||
class CImageApply;
|
||||
|
||||
class GScn_Drv
|
||||
class IGScan
|
||||
{
|
||||
public:
|
||||
virtual ~IGScan()=0 {};
|
||||
|
||||
virtual void open(int vid, int pid) = 0;;
|
||||
virtual int aquire_image(cv::Mat& image) = 0;
|
||||
virtual BOOL IsConnected() = 0;
|
||||
virtual std::string GetFWVersion() = 0;
|
||||
virtual std::string GetSerialNum() = 0;
|
||||
virtual bool is_scan() = 0;
|
||||
virtual BOOL Get_Scanner_PaperOn() = 0;
|
||||
virtual void config_params(SFreeImage& params) = 0;
|
||||
virtual void Scanner_StartScan(UINT16 count) = 0;
|
||||
virtual void Stop_scan() = 0;
|
||||
virtual void ResetScanner() =0;
|
||||
virtual bool Get_IsImageQueueEmpty() = 0;
|
||||
virtual void reset() = 0;
|
||||
|
||||
virtual void setdecodepixtype(int twpixtype)= 0;
|
||||
virtual UINT32 get_ErrorCode() = 0;
|
||||
virtual void Set_ErrorCode(UINT32 value) = 0;
|
||||
};
|
||||
|
||||
|
||||
class IUsb;
|
||||
|
||||
class GScn_Drv : IGScan
|
||||
{
|
||||
public:
|
||||
GScn_Drv();
|
||||
~GScn_Drv();
|
||||
virtual ~GScn_Drv();
|
||||
|
||||
void open(int vid, int pid);
|
||||
int aquire_image(cv::Mat& image);
|
||||
|
@ -72,7 +98,8 @@ private:
|
|||
DWORD usbmain();
|
||||
void Pop_Image();
|
||||
void trim(std::string &s);
|
||||
cscn_usb m_usb;
|
||||
// cscn_usb m_usb;
|
||||
std::shared_ptr<IUsb> m_usb;
|
||||
HANDLE m_h_usb_thread;
|
||||
DWORD m_dw_ctrl_thread_id;
|
||||
volatile int devState;
|
||||
|
|
BIN
hugaotwainds.aps
BIN
hugaotwainds.aps
Binary file not shown.
|
@ -23,20 +23,20 @@
|
|||
<ProjectGuid>{F928F998-CD13-478E-8D23-5943C2B108F5}</ProjectGuid>
|
||||
<Keyword>MFCDLLProj</Keyword>
|
||||
<RootNamespace>hugaotwainds</RootNamespace>
|
||||
<WindowsTargetPlatformVersion>10.0.17763.0</WindowsTargetPlatformVersion>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
<UseOfMfc>Dynamic</UseOfMfc>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
<UseOfMfc>Dynamic</UseOfMfc>
|
||||
|
@ -44,14 +44,14 @@
|
|||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
<UseOfMfc>Dynamic</UseOfMfc>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<CharacterSet>MultiByte</CharacterSet>
|
||||
<UseOfMfc>Dynamic</UseOfMfc>
|
||||
|
@ -139,7 +139,7 @@
|
|||
<WarningLevel>Level3</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>_WINDOWS;_DEBUG;_USRDLL;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<AdditionalIncludeDirectories>C:\local\boost_1_69_0;.\pub\external\include;.\pub\ddk;.\pub\opencv\include;.\pub\json;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalIncludeDirectories>.\pub\external\include;.\pub\ddk;.\opencv\include;.\pub\json;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
|
@ -227,6 +227,8 @@
|
|||
<ClCompile Include="CTwainMutex.cpp" />
|
||||
<ClCompile Include="DSMInterface.cpp" />
|
||||
<ClCompile Include="FeederPaper.cpp" />
|
||||
<ClCompile Include="GDevice.cpp" />
|
||||
<ClCompile Include="GDeviceLists.cpp" />
|
||||
<ClCompile Include="gscn_drv.cpp" />
|
||||
<ClCompile Include="hugaotwainds.cpp" />
|
||||
<ClCompile Include="ImageAdjustColors.cpp" />
|
||||
|
@ -252,7 +254,6 @@
|
|||
<ClCompile Include="PublicFunc.cpp" />
|
||||
<ClCompile Include="SaveConfigDlg.cpp" />
|
||||
<ClCompile Include="scn_config.cpp" />
|
||||
<ClCompile Include="scn_usb.cpp" />
|
||||
<ClCompile Include="stdafx.cpp">
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">Create</PrecompiledHeader>
|
||||
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">Create</PrecompiledHeader>
|
||||
|
@ -271,6 +272,7 @@
|
|||
<ClCompile Include="TwainString.cpp" />
|
||||
<ClCompile Include="TwainUIDlg.cpp" />
|
||||
<ClCompile Include="TWAIN_UI.cpp" />
|
||||
<ClCompile Include="UsbScanEx.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="HUAGO-LOGO-for UI.bmp" />
|
||||
|
@ -295,8 +297,11 @@
|
|||
<ClInclude Include="DSMInterface.h" />
|
||||
<ClInclude Include="FeederPaper.h" />
|
||||
<ClInclude Include="filetools.h" />
|
||||
<ClInclude Include="GDevice.h" />
|
||||
<ClInclude Include="GDeviceLists.h" />
|
||||
<ClInclude Include="gscn_drv.h" />
|
||||
<ClInclude Include="hugaotwainds.h" />
|
||||
<ClInclude Include="IGDevice.h" />
|
||||
<ClInclude Include="ImageAdjustColors.h" />
|
||||
<ClInclude Include="ImageApply.h" />
|
||||
<ClInclude Include="ImageApplyCrop.h" />
|
||||
|
@ -313,6 +318,7 @@
|
|||
<ClInclude Include="ImageTranferMat.h" />
|
||||
<ClInclude Include="ImageTransfer.h" />
|
||||
<ClInclude Include="IndicatorDlg.h" />
|
||||
<ClInclude Include="IUsb.h" />
|
||||
<ClInclude Include="JpegBuffer.h" />
|
||||
<ClInclude Include="jpeglib.h" />
|
||||
<ClInclude Include="JsonConfig.h" />
|
||||
|
@ -324,8 +330,8 @@
|
|||
<ClInclude Include="Resource.h" />
|
||||
<ClInclude Include="SaveConfigDlg.h" />
|
||||
<ClInclude Include="scn_config.h" />
|
||||
<ClInclude Include="scn_usb.h" />
|
||||
<ClInclude Include="stdafx.h" />
|
||||
<ClInclude Include="StopWatch.h" />
|
||||
<ClInclude Include="SupperScanImageMTF.h" />
|
||||
<ClInclude Include="targetver.h" />
|
||||
<ClInclude Include="TextDirection.h" />
|
||||
|
@ -340,6 +346,7 @@
|
|||
<ClInclude Include="TwainString.h" />
|
||||
<ClInclude Include="TwainUIDlg.h" />
|
||||
<ClInclude Include="TWAIN_UI.h" />
|
||||
<ClInclude Include="UsbScanEx.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="hugaotwainds.rc" />
|
||||
|
|
|
@ -90,9 +90,6 @@
|
|||
<ClCompile Include="scn_config.cpp">
|
||||
<Filter>USB通信</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="scn_usb.cpp">
|
||||
<Filter>USB通信</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="TwainUIDlg.cpp">
|
||||
<Filter>UI</Filter>
|
||||
</ClCompile>
|
||||
|
@ -189,6 +186,15 @@
|
|||
<ClCompile Include="ImageTranferBW.cpp">
|
||||
<Filter>代码文件</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="GDevice.cpp">
|
||||
<Filter>代码文件</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="GDeviceLists.cpp">
|
||||
<Filter>代码文件</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="UsbScanEx.cpp">
|
||||
<Filter>代码文件</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="hugaotwainds.def">
|
||||
|
@ -271,9 +277,6 @@
|
|||
<ClInclude Include="scn_config.h">
|
||||
<Filter>USB通信</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="scn_usb.h">
|
||||
<Filter>USB通信</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="BasicSetting.h">
|
||||
<Filter>UI</Filter>
|
||||
</ClInclude>
|
||||
|
@ -388,6 +391,24 @@
|
|||
<ClInclude Include="ImageTransfer.h">
|
||||
<Filter>头文件</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="GDevice.h">
|
||||
<Filter>头文件</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="GDeviceLists.h">
|
||||
<Filter>头文件</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="IGDevice.h">
|
||||
<Filter>头文件</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="IUsb.h">
|
||||
<Filter>头文件</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="StopWatch.h">
|
||||
<Filter>头文件</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="UsbScanEx.h">
|
||||
<Filter>头文件</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="hugaotwainds.rc">
|
||||
|
|
455
scn_usb.cpp
455
scn_usb.cpp
|
@ -1,455 +0,0 @@
|
|||
#include "stdafx.h"
|
||||
#include <stdio.h>
|
||||
#include <tchar.h>
|
||||
#include "scn_usb.h"
|
||||
#include "winioctl.h"
|
||||
#include "PublicFunc.h"
|
||||
#include "filetools.h"
|
||||
|
||||
//CUSBHotPlugged usb;
|
||||
cscn_usb::cscn_usb(void)
|
||||
{
|
||||
m_h_dev = INVALID_HANDLE_VALUE;
|
||||
m_usbscan_config = { 0 };
|
||||
m_w_serial_no = 0;
|
||||
}
|
||||
|
||||
cscn_usb::~cscn_usb(void)
|
||||
{
|
||||
close();
|
||||
//FileTools::write_log("1.txt", "~cscn_usb");
|
||||
}
|
||||
|
||||
void cscn_usb::init(WORD w_vid, WORD w_pid)
|
||||
{
|
||||
m_h_dev = INVALID_HANDLE_VALUE;
|
||||
w_vid = w_vid;
|
||||
w_pid = w_pid;
|
||||
m_w_serial_no = 0;
|
||||
}
|
||||
|
||||
HANDLE cscn_usb::open(WORD index)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
TCHAR szDevPath[MAX_PATH] = { 0 };
|
||||
INT i = 0, j = 0;
|
||||
DEVICE_DESCRIPTOR dev_desc;
|
||||
DWORD cbRet = 0;
|
||||
|
||||
|
||||
_stprintf(szDevPath, TEXT("\\\\.\\Usbscan%d"), index);
|
||||
m_h_dev = CreateFile(szDevPath,
|
||||
GENERIC_READ | GENERIC_WRITE,
|
||||
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
FILE_FLAG_OVERLAPPED,
|
||||
NULL);
|
||||
if (m_h_dev != INVALID_HANDLE_VALUE)
|
||||
{
|
||||
m_b_is_connected = TRUE;
|
||||
b_ret = DeviceIoControl(m_h_dev, (DWORD)IOCTL_GET_DEVICE_DESCRIPTOR,
|
||||
&dev_desc, sizeof(dev_desc), &dev_desc, sizeof(dev_desc),
|
||||
&cbRet, NULL);
|
||||
|
||||
if (b_ret)
|
||||
{
|
||||
m_w_vid = dev_desc.usVendorId;
|
||||
m_w_pid = dev_desc.usProductId;
|
||||
m_w_serial_no = index;
|
||||
b_ret = DeviceIoControl(m_h_dev, (DWORD)IOCTL_GET_PIPE_CONFIGURATION,
|
||||
NULL, 0, &m_usbscan_config, sizeof(USBSCAN_PIPE_CONFIGURATION),
|
||||
&cbRet, NULL);
|
||||
if (b_ret && m_usbscan_config.NumberOfPipes > 0)
|
||||
{
|
||||
for (int by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++)
|
||||
{
|
||||
TCHAR szPipePath[MAX_PATH] = { 0 };
|
||||
_stprintf(szPipePath, TEXT("\\\\.\\Usbscan%d\\%d"), index, by_i);
|
||||
m_usb_pipes[by_i].pipe_info = m_usbscan_config.PipeInfo[by_i];
|
||||
m_usb_pipes[by_i].h_pipe = CreateFile(szPipePath,
|
||||
GENERIC_READ | GENERIC_WRITE,
|
||||
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
FILE_FLAG_OVERLAPPED,
|
||||
NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
CloseHandle(m_h_dev);
|
||||
m_h_dev = INVALID_HANDLE_VALUE;
|
||||
}
|
||||
}
|
||||
|
||||
return m_h_dev;
|
||||
}
|
||||
|
||||
BOOL cscn_usb::close(void)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
BYTE by_i = 0x00;
|
||||
|
||||
if (m_h_dev != INVALID_HANDLE_VALUE)
|
||||
{
|
||||
|
||||
BOOL bState = FALSE;
|
||||
DWORD cbRet = 0;
|
||||
OVERLAPPED overlapped;
|
||||
PIPE_TYPE pipeType = ALL_PIPE;
|
||||
|
||||
memset(&overlapped, 0, sizeof(OVERLAPPED));
|
||||
overlapped.hEvent =
|
||||
CreateEvent(NULL, // pointer to security attributes
|
||||
FALSE, // automatic reset
|
||||
FALSE, // initialize to nosignaled
|
||||
NULL); // pointer to the event-object name
|
||||
bState =
|
||||
DeviceIoControl(m_h_dev,
|
||||
(DWORD)IOCTL_CANCEL_IO,
|
||||
(LPVOID)&pipeType,
|
||||
sizeof(PIPE_TYPE),
|
||||
NULL,
|
||||
0,
|
||||
&cbRet,
|
||||
&overlapped);
|
||||
WaitForSingleObject(overlapped.hEvent, 1000);
|
||||
CloseHandle(overlapped.hEvent);
|
||||
|
||||
for (by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++)
|
||||
{
|
||||
CancelIo(m_usb_pipes[by_i].h_pipe); //++@2012-06-08
|
||||
CloseHandle(m_usb_pipes[by_i].h_pipe);
|
||||
m_usb_pipes[by_i].h_pipe = INVALID_HANDLE_VALUE;
|
||||
}
|
||||
|
||||
CancelIo(m_h_dev); //++@2012-06-08
|
||||
b_ret = CloseHandle(m_h_dev);
|
||||
if (b_ret)
|
||||
{
|
||||
m_h_dev = INVALID_HANDLE_VALUE;
|
||||
b_ret = TRUE;
|
||||
}
|
||||
}
|
||||
m_b_is_connected = FALSE;
|
||||
return b_ret;
|
||||
}
|
||||
|
||||
BOOL cscn_usb::control_in(BYTE by_pipe_addr, WORD w_value, WORD w_index, PVOID p_data, DWORD dw_size, PDWORD pdw_read, LPOVERLAPPED lp_overlap)
|
||||
{
|
||||
IO_BLOCK irp;
|
||||
DWORD dw_ret;
|
||||
HANDLE h_pipe = INVALID_HANDLE_VALUE;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return TRUE;
|
||||
irp.uOffset = w_value;
|
||||
irp.uLength = dw_size;
|
||||
irp.uIndex = w_index;
|
||||
irp.pbyData = (LPBYTE)p_data;
|
||||
|
||||
if (by_pipe_addr == 0x00)
|
||||
h_pipe = m_h_dev;
|
||||
else
|
||||
{
|
||||
BYTE by_i = 0x00;
|
||||
for (by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++)
|
||||
{
|
||||
if (m_usb_pipes[by_i].pipe_info.EndpointAddress == by_pipe_addr)
|
||||
h_pipe = m_usb_pipes[by_i].h_pipe;
|
||||
}
|
||||
}
|
||||
return DeviceIoControl(h_pipe, IOCTL_READ_REGISTERS, &irp, sizeof(IO_BLOCK), p_data, 64, &dw_ret, lp_overlap);
|
||||
}
|
||||
|
||||
BOOL cscn_usb::control_out(BYTE by_pipe_addr, WORD w_value, WORD w_index, PVOID p_data, DWORD dw_size, PDWORD pdw_write, LPOVERLAPPED lp_overlap)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
IO_BLOCK irp;
|
||||
DWORD dw_ret;
|
||||
HANDLE h_pipe = INVALID_HANDLE_VALUE;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return TRUE;
|
||||
irp.uOffset = w_value;
|
||||
irp.uLength = dw_size;
|
||||
irp.uIndex = w_index;
|
||||
irp.pbyData = (LPBYTE)p_data;
|
||||
if (by_pipe_addr == 0x00)
|
||||
h_pipe = m_h_dev;
|
||||
else
|
||||
{
|
||||
BYTE by_i = 0x00;
|
||||
for (by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++)
|
||||
{
|
||||
if (m_usb_pipes[by_i].pipe_info.EndpointAddress == by_pipe_addr)
|
||||
h_pipe = m_usb_pipes[by_i].h_pipe;
|
||||
}
|
||||
}
|
||||
b_ret = DeviceIoControl(h_pipe, IOCTL_WRITE_REGISTERS, &irp, sizeof(IO_BLOCK), NULL, 0L, &dw_ret, lp_overlap);
|
||||
if (!b_ret)
|
||||
{
|
||||
if (ERROR_FILE_NOT_FOUND == GetLastError())
|
||||
m_b_is_connected = FALSE;
|
||||
}
|
||||
return b_ret;
|
||||
}
|
||||
|
||||
BOOL cscn_usb::interrupt_in(BYTE by_pipe_addr, PBYTE pby_data, BYTE by_len, PBYTE pby_read, LPOVERLAPPED lp_overlap)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
IO_BLOCK irp = { 0 };
|
||||
DWORD dw_ret = 0L;
|
||||
HANDLE h_pipe = INVALID_HANDLE_VALUE;
|
||||
BYTE by_i = 0x00;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return FALSE;
|
||||
|
||||
for (by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++)
|
||||
{
|
||||
if (m_usb_pipes[by_i].pipe_info.EndpointAddress == by_pipe_addr)
|
||||
h_pipe = m_usb_pipes[by_i].h_pipe;
|
||||
}
|
||||
b_ret = DeviceIoControl(h_pipe, (DWORD)IOCTL_WAIT_ON_DEVICE_EVENT,
|
||||
NULL, 0, pby_data, by_len, &dw_ret, lp_overlap);
|
||||
if (!b_ret)
|
||||
{
|
||||
if (ERROR_FILE_NOT_FOUND == GetLastError())
|
||||
m_b_is_connected = FALSE;
|
||||
}
|
||||
if (lp_overlap != NULL)
|
||||
{
|
||||
DWORD dw_trans = 0x0L;
|
||||
b_ret = WaitForSingleObject(lp_overlap->hEvent, 50) == WAIT_OBJECT_0;
|
||||
if (b_ret)
|
||||
{
|
||||
b_ret = GetOverlappedResult(h_pipe, lp_overlap, &dw_trans, FALSE);
|
||||
if (b_ret)
|
||||
{
|
||||
if (pby_read != NULL)
|
||||
*pby_read = dw_trans & 0xff;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ERROR_FILE_NOT_FOUND == GetLastError())
|
||||
m_b_is_connected = FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (pby_read != NULL)
|
||||
*pby_read = dw_ret & 0xff;
|
||||
}
|
||||
|
||||
return b_ret;
|
||||
}
|
||||
|
||||
BOOL cscn_usb::bulk_in(BYTE by_pipe_addr, PVOID p_data, DWORD dw_size,DWORD timeout, PDWORD pdw_ret)
|
||||
{
|
||||
HANDLE h_pipe = INVALID_HANDLE_VALUE;
|
||||
BOOL b_ret = FALSE;
|
||||
|
||||
OVERLAPPED oa;
|
||||
memset(&oa, 0, sizeof(oa));
|
||||
oa.hEvent = CreateEvent(0, TRUE, FALSE, NULL);
|
||||
LPOVERLAPPED lp_overlap = &oa;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return TRUE;
|
||||
if (by_pipe_addr == 0x00)
|
||||
h_pipe = m_h_dev;
|
||||
else
|
||||
{
|
||||
BYTE by_i = 0x00;
|
||||
for (by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++)
|
||||
{
|
||||
if (m_usb_pipes[by_i].pipe_info.EndpointAddress == by_pipe_addr)
|
||||
h_pipe = m_usb_pipes[by_i].h_pipe;
|
||||
}
|
||||
}
|
||||
b_ret = ReadFile(h_pipe, p_data, dw_size, pdw_ret, lp_overlap);
|
||||
if (lp_overlap != NULL)
|
||||
{
|
||||
DWORD dw_trans = 0x0L;;
|
||||
b_ret = WaitForSingleObject(lp_overlap->hEvent, timeout) == WAIT_OBJECT_0;
|
||||
if (b_ret)
|
||||
{
|
||||
b_ret = GetOverlappedResult(h_pipe, lp_overlap, &dw_trans, FALSE);
|
||||
if (b_ret)
|
||||
{
|
||||
if (pdw_ret != NULL)
|
||||
*pdw_ret = dw_trans;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ERROR_FILE_NOT_FOUND == GetLastError())
|
||||
m_b_is_connected = FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
return b_ret;
|
||||
CloseHandle(lp_overlap->hEvent);
|
||||
return b_ret;
|
||||
}
|
||||
//overlap do not use current
|
||||
BOOL cscn_usb::bulk_out(BYTE by_pipe_addr, PVOID p_data, DWORD dw_size, PDWORD pdw_ret)
|
||||
{
|
||||
BOOL b_ret = FALSE;
|
||||
HANDLE h_pipe = INVALID_HANDLE_VALUE;
|
||||
|
||||
OVERLAPPED oa;
|
||||
memset(&oa, 0, sizeof(oa));
|
||||
oa.hEvent = CreateEvent(0, TRUE, FALSE, NULL);
|
||||
LPOVERLAPPED lp_overlap = &oa;
|
||||
|
||||
if (m_h_dev == INVALID_HANDLE_VALUE)
|
||||
return TRUE;
|
||||
if (by_pipe_addr == 0x00)
|
||||
h_pipe = m_h_dev;
|
||||
else
|
||||
{
|
||||
BYTE by_i = 0x00;
|
||||
for (by_i = 0x00; by_i < m_usbscan_config.NumberOfPipes; by_i++)
|
||||
{
|
||||
if (m_usb_pipes[by_i].pipe_info.EndpointAddress == by_pipe_addr)
|
||||
h_pipe = m_usb_pipes[by_i].h_pipe;
|
||||
}
|
||||
}
|
||||
|
||||
b_ret = WriteFile(h_pipe, p_data, dw_size, pdw_ret, lp_overlap);
|
||||
if (!b_ret)
|
||||
{
|
||||
DWORD dw_trans = 0x0L;
|
||||
b_ret = WaitForSingleObject(lp_overlap->hEvent, 1000) == WAIT_OBJECT_0;
|
||||
if (b_ret)
|
||||
{
|
||||
b_ret = GetOverlappedResult(h_pipe, lp_overlap, &dw_trans, FALSE);
|
||||
if (b_ret)
|
||||
{
|
||||
if (pdw_ret != NULL)
|
||||
*pdw_ret = dw_trans;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (ERROR_FILE_NOT_FOUND == GetLastError())
|
||||
m_b_is_connected = FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
CloseHandle(lp_overlap->hEvent);
|
||||
return b_ret;
|
||||
|
||||
}
|
||||
|
||||
BOOL cscn_usb::Read_Data(PVOID p_data, DWORD length, DWORD timeout, PDWORD pdw_ret)
|
||||
{
|
||||
//HANDLE h_pipe = INVALID_HANDLE_VALUE;
|
||||
BOOL b_ret = FALSE;
|
||||
OVERLAPPED oa;
|
||||
memset(&oa, 0, sizeof(oa));
|
||||
oa.hEvent = CreateEvent(0, TRUE, FALSE, NULL);
|
||||
|
||||
LPOVERLAPPED lp_overlap = &oa;
|
||||
|
||||
if (m_h_dev != NULL)
|
||||
{
|
||||
b_ret = ReadFile(m_h_dev, p_data, length, pdw_ret, lp_overlap);
|
||||
DWORD dw_trans = 0x0L;
|
||||
b_ret = WaitForSingleObject(lp_overlap->hEvent, timeout) == WAIT_OBJECT_0;
|
||||
if (b_ret)
|
||||
{
|
||||
b_ret = GetOverlappedResult(m_h_dev, lp_overlap, &dw_trans, FALSE);
|
||||
if (b_ret)
|
||||
{
|
||||
if (pdw_ret != NULL)
|
||||
{
|
||||
*pdw_ret = dw_trans;
|
||||
}
|
||||
CloseHandle(lp_overlap->hEvent);
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
CloseHandle(lp_overlap->hEvent);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
BOOL cscn_usb::is_connected(void)
|
||||
{
|
||||
return m_b_is_connected;
|
||||
}
|
||||
|
||||
usb_scan_dev Devices()
|
||||
{
|
||||
usb_scan_dev devs;
|
||||
memset(&devs, 0, sizeof(devs));
|
||||
BOOL b_ret = FALSE;
|
||||
TCHAR szDevPath[MAX_PATH] = { 0 };
|
||||
DEVICE_DESCRIPTOR dev_desc;
|
||||
DWORD cbRet = 0;
|
||||
HANDLE h_dev;
|
||||
for (int i = 0; i < 1024; i++)
|
||||
{
|
||||
_stprintf(szDevPath, TEXT("\\\\.\\Usbscan%d"), i);
|
||||
h_dev = CreateFile(szDevPath,
|
||||
GENERIC_READ | GENERIC_WRITE,
|
||||
FILE_SHARE_READ | FILE_SHARE_WRITE,
|
||||
NULL,
|
||||
OPEN_EXISTING,
|
||||
FILE_FLAG_OVERLAPPED,
|
||||
NULL);
|
||||
|
||||
if (h_dev != INVALID_HANDLE_VALUE)
|
||||
{
|
||||
b_ret = DeviceIoControl(h_dev, (DWORD)IOCTL_GET_DEVICE_DESCRIPTOR,
|
||||
&dev_desc, sizeof(dev_desc), &dev_desc, sizeof(dev_desc),
|
||||
&cbRet, NULL);
|
||||
if (b_ret)
|
||||
{
|
||||
devs.dev_infos[devs._NumberOfDevs].index = i;
|
||||
devs.dev_infos[devs._NumberOfDevs].vid = dev_desc.usVendorId;
|
||||
devs.dev_infos[devs._NumberOfDevs].pid = dev_desc.usProductId;
|
||||
devs._NumberOfDevs++;
|
||||
}
|
||||
CloseHandle(h_dev);
|
||||
h_dev = INVALID_HANDLE_VALUE;
|
||||
}
|
||||
}
|
||||
|
||||
return devs;
|
||||
}
|
||||
usb_scan_dev Devices(WORD w_vid)
|
||||
{
|
||||
usb_scan_dev all_dev = Devices();
|
||||
usb_scan_dev devs;
|
||||
memset(&devs, 0, sizeof(devs));
|
||||
for (int i = 0; i < all_dev._NumberOfDevs; i++)
|
||||
{
|
||||
if (all_dev.dev_infos[i].vid == w_vid)
|
||||
{
|
||||
devs.dev_infos[devs._NumberOfDevs] = all_dev.dev_infos[i];
|
||||
devs._NumberOfDevs++;
|
||||
}
|
||||
}
|
||||
return devs;
|
||||
}
|
||||
usb_scan_dev Devices(WORD w_vid, WORD w_pid)
|
||||
{
|
||||
usb_scan_dev all_dev = Devices();
|
||||
usb_scan_dev devs;
|
||||
memset(&devs, 0, sizeof(devs));
|
||||
for (int i = 0; i < all_dev._NumberOfDevs; i++)
|
||||
{
|
||||
if (all_dev.dev_infos[i].vid == w_vid && all_dev.dev_infos[i].pid == w_pid)
|
||||
{
|
||||
devs.dev_infos[devs._NumberOfDevs] = all_dev.dev_infos[i];
|
||||
devs._NumberOfDevs++;
|
||||
}
|
||||
}
|
||||
return devs;
|
||||
}
|
66
scn_usb.h
66
scn_usb.h
|
@ -1,66 +0,0 @@
|
|||
#ifndef SCN_USB_H_HEADER_INCLUDED_B2BF228E
|
||||
#define SCN_USB_H_HEADER_INCLUDED_B2BF228E
|
||||
#include <Windows.h>
|
||||
#include <usbscan.h>
|
||||
|
||||
#pragma pack(1)
|
||||
struct tag_usb_pipe
|
||||
{
|
||||
HANDLE h_pipe;
|
||||
USBSCAN_PIPE_INFORMATION pipe_info;
|
||||
OVERLAPPED overlap;
|
||||
};
|
||||
typedef struct tag_usb_pipe usb_pipe_t, *pusb_pipe_t;
|
||||
#pragma pack()
|
||||
|
||||
typedef struct tag_usb_scan_dev_info
|
||||
{
|
||||
WORD vid;
|
||||
WORD pid;
|
||||
WORD index;
|
||||
}usb_scan_dev_info, *pusb_scan_dev_info;
|
||||
|
||||
typedef struct tag_usb_scan_dev
|
||||
{
|
||||
USHORT _NumberOfDevs;
|
||||
tag_usb_scan_dev_info dev_infos[1024];
|
||||
}usb_scan_dev, *pusb_scan_dev;
|
||||
|
||||
//##ModelId=4D40D3230138
|
||||
class cscn_usb
|
||||
{
|
||||
public:
|
||||
|
||||
USBSCAN_PIPE_CONFIGURATION m_usbscan_config;
|
||||
usb_pipe_t m_usb_pipes[MAX_NUM_PIPES];
|
||||
HANDLE m_h_dev;
|
||||
void init(WORD w_vid, WORD w_pid);
|
||||
BOOL control_in (BYTE by_pipe_addr, WORD w_value, WORD w_index, PVOID p_data, DWORD dw_size, PDWORD pdw_read, LPOVERLAPPED lp_overlap);
|
||||
BOOL control_out (BYTE by_pipe_addr, WORD w_value, WORD w_index, PVOID p_data, DWORD dw_size, PDWORD pdw_write, LPOVERLAPPED lp_overlap);
|
||||
BOOL interrupt_in(BYTE by_pipe_addr, PBYTE pby_data, BYTE by_len, PBYTE pby_read, LPOVERLAPPED lp_overlap);
|
||||
BOOL bulk_in (BYTE by_pipe_addr, PVOID p_data, DWORD dw_size, DWORD timeout,PDWORD pdw_ret);
|
||||
BOOL bulk_out(BYTE by_pipe_addr, PVOID p_data, DWORD dw_size, PDWORD pdw_ret);
|
||||
HANDLE open(WORD index);
|
||||
BOOL Read_Data(PVOID p_data, DWORD length, DWORD timeout, PDWORD pdw_ret);
|
||||
BOOL close(void);
|
||||
cscn_usb(void);
|
||||
~cscn_usb(void);
|
||||
BOOL is_connected(void);
|
||||
|
||||
private:
|
||||
BOOL m_b_is_connected;
|
||||
//##ModelId=4D41B612027E
|
||||
WORD m_w_vid;
|
||||
//##ModelId=4D41B62200F7
|
||||
WORD m_w_pid;
|
||||
//##ModelId=4D41B63103A7
|
||||
WORD m_w_serial_no;
|
||||
|
||||
};
|
||||
|
||||
|
||||
usb_scan_dev Devices();
|
||||
usb_scan_dev Devices(WORD w_vid);
|
||||
usb_scan_dev Devices(WORD w_vid, WORD w_pid);
|
||||
|
||||
#endif /* SCN_USB_H_HEADER_INCLUDED_B2BF228E */
|
Loading…
Reference in New Issue