添加广播方式升级
This commit is contained in:
@@ -5,16 +5,25 @@ void prot_m4::init()
|
||||
{
|
||||
if_ = interFaceFind("uart_m4");
|
||||
codec_ = codecFind("codec_m4");
|
||||
|
||||
if(if_==nullptr||codec_==nullptr){
|
||||
return;
|
||||
}
|
||||
if_->set_irq([=](myarray recv)
|
||||
{
|
||||
if(codec_->packCheck(recv_data)==true){
|
||||
int cmd,src,dst;
|
||||
myarray data=codec_->decode(src,dst,cmd,recv_data);
|
||||
if(exe_cb_fun(data)==false){
|
||||
qWarning("can not find cb fun with:\"%s\"",data.data());
|
||||
}
|
||||
recv_data.clear();
|
||||
recv_data+=recv;
|
||||
int pack_len=0;
|
||||
while(pack_len=codec_->packCheck(recv_data),pack_len>0){
|
||||
int cmd,src,dst;
|
||||
myarray data=codec_->decode(src,dst,cmd,recv_data);
|
||||
recv_data.remove(0,pack_len);
|
||||
if(wait>0) wait--;
|
||||
if(exe_cb_fun(data)==false){
|
||||
qWarning("can not find cb fun with:\"%s\"",data.data());
|
||||
}
|
||||
if(send_list.size()>0){
|
||||
if_->write(send_list.takeFirst());
|
||||
wait+=2;
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -24,7 +33,12 @@ void prot_m4::send_data_slot(myarray data)
|
||||
if ((if_ != nullptr) && (codec_ != nullptr))
|
||||
{
|
||||
myarray send = codec_->encode(0, 0, 0, data);
|
||||
if_->write(send);
|
||||
send_list.append(send);
|
||||
if(wait==0){
|
||||
wait+=2;
|
||||
qDebug("send m4:%s",data.data());
|
||||
if_->write(send_list.takeFirst());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -33,13 +47,16 @@ bool prot_m4::exe_cb_fun(myarray data)
|
||||
int left;
|
||||
for (int i = 0; i < funs.size(); i++)
|
||||
{
|
||||
left = funs[i].cmd.size();
|
||||
// 这里size包含结尾符,要去掉
|
||||
left = funs[i].cmd.size()-1;
|
||||
if (data.left(left) == funs[i].cmd)
|
||||
{
|
||||
if (funs[i].fun != nullptr)
|
||||
{
|
||||
funs[i].fun(data.mid(left));
|
||||
return true;
|
||||
for(int j=0;j<funs[i].funs.size();j++){
|
||||
prot_m4_cb fun=funs[i].funs[j];
|
||||
if(fun!=nullptr){
|
||||
fun(data.mid(left));
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -65,12 +82,21 @@ bool prot_m4::set_irq_fun(prot_m4_cb fun, myarray data)
|
||||
left = funs[i].cmd.size();
|
||||
if (data.left(left) == funs[i].cmd)
|
||||
{
|
||||
return false;
|
||||
for(int j=0;j<funs[i].funs.size();j++){
|
||||
prot_m4_cb temp=funs[i].funs[j];
|
||||
if(fun.target<void(*)(myarray data)>()==temp.target<void(*)(myarray data)>()){
|
||||
qDebug("this function pointer was exited.");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
qDebug("add function pointer success.");
|
||||
funs[i].funs.append(fun);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
HandleM4_def m4_cmd;
|
||||
m4_cmd.cmd = data;
|
||||
m4_cmd.fun = fun;
|
||||
m4_cmd.funs.append(fun);
|
||||
funs.append(m4_cmd);
|
||||
return true;
|
||||
}
|
||||
@@ -83,8 +109,24 @@ bool prot_m4::del_irq_fun(prot_m4_cb fun, myarray data)
|
||||
left = funs[i].cmd.size();
|
||||
if (data.left(left) == funs[i].cmd)
|
||||
{
|
||||
funs.removeAt(i);
|
||||
return true;
|
||||
if(fun==nullptr){
|
||||
qDebug("del the same string cb.");
|
||||
funs.removeAt(i);
|
||||
return true;
|
||||
}else{
|
||||
for(int j=0;j<funs[i].funs.size();j++){
|
||||
prot_m4_cb temp=funs[i].funs[j];
|
||||
if(fun.target<void(*)(myarray data)>()==temp.target<void(*)(myarray data)>()){
|
||||
qDebug("del the same function pointer.");
|
||||
funs[i].funs.removeAt(j);
|
||||
if(funs[i].funs.size()==0){
|
||||
funs.removeAt(i);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
|
@@ -16,14 +16,14 @@ typedef std::function<void(myarray data)> prot_m4_cb;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
prot_m4_cb fun;
|
||||
QList<prot_m4_cb> funs;
|
||||
myarray cmd;
|
||||
} HandleM4_def;
|
||||
|
||||
class prot_m4 : public QObject
|
||||
{
|
||||
public:
|
||||
prot_m4() { if_ = nullptr; }
|
||||
prot_m4() { if_ = nullptr;wait=0; }
|
||||
~prot_m4() {}
|
||||
void init();
|
||||
bool set_irq_fun(prot_m4_cb fun, myarray data);
|
||||
@@ -40,6 +40,8 @@ protected:
|
||||
Codec *codec_;
|
||||
QThread thread;
|
||||
myarray recv_data;
|
||||
int wait;
|
||||
QList<myarray> send_list;
|
||||
};
|
||||
|
||||
prot_m4 *protM4();
|
||||
|
@@ -25,30 +25,35 @@ HandlePc *handlePcFind(int cmd)
|
||||
|
||||
void ProtPc::init()
|
||||
{
|
||||
if_ = interFaceFind("tcp");
|
||||
if_ = interFaceFind("uart_host");
|
||||
codec_ = codecFind("codec_ym");
|
||||
if(if_==nullptr||codec_==nullptr){
|
||||
return;
|
||||
}
|
||||
|
||||
if_->set_irq([=](myarray recv)
|
||||
{
|
||||
recv_data+=recv;
|
||||
if(codec_->packCheck(recv_data)==true){
|
||||
int cmd,src,dst;
|
||||
myarray data=codec_->decode(src,dst,cmd,recv_data);
|
||||
if(handle_!=nullptr){
|
||||
if(handle_->busy==0){
|
||||
disconnect(handle_,&HandlePc::send_data_signal,this,&ProtPc::send_data_slot);
|
||||
delete handle_;
|
||||
}else{
|
||||
qWarning("prot_pc is busy.");
|
||||
return;
|
||||
}
|
||||
int pack_len=0;
|
||||
while(pack_len=codec_->packCheck(recv_data),pack_len>0){
|
||||
int cmd,src,dst;
|
||||
qDebug("host recv:%s",recv_data.toHex(' ').data());
|
||||
myarray data=codec_->decode(src,dst,cmd,recv_data);
|
||||
recv_data.remove(0,pack_len);
|
||||
if(handle_!=nullptr){
|
||||
if(handle_->busy==0){
|
||||
disconnect(handle_,&HandlePc::send_data_signal,this,&ProtPc::send_data_slot);
|
||||
delete handle_;
|
||||
}else{
|
||||
qWarning("prot_pc is busy.");
|
||||
return;
|
||||
}
|
||||
handle_=handlePcFind(cmd);
|
||||
if(handle_!=nullptr){
|
||||
connect(handle_,&HandlePc::send_data_signal,this,&ProtPc::send_data_slot);
|
||||
handle_->dolater(cmd,data);
|
||||
}
|
||||
recv_data.clear();
|
||||
}
|
||||
handle_=handlePcFind(cmd);
|
||||
if(handle_!=nullptr){
|
||||
connect(handle_,&HandlePc::send_data_signal,this,&ProtPc::send_data_slot);
|
||||
handle_->dolater(cmd,data);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
@@ -80,7 +80,7 @@ typedef struct
|
||||
} handlepc_def;
|
||||
|
||||
#define protpc_export(cmd_, fun_) \
|
||||
__attribute__((used)) static handlepc_def _handlepc_##name_ __attribute__((section("protpc"))) = { \
|
||||
__attribute__((used)) static handlepc_def _handlepc_##cmd_ __attribute__((section("protpc"))) = { \
|
||||
.cmd = cmd_, \
|
||||
.handle_get_fun = fun_, \
|
||||
}
|
||||
|
@@ -6,26 +6,36 @@ void prot_slave::init()
|
||||
if_ = interFaceFind("can");
|
||||
codec_ = codecFind("codec_slave");
|
||||
mycfg *cfg_ = syscfg();
|
||||
if(if_==nullptr||codec_==nullptr){
|
||||
return;
|
||||
}
|
||||
for (int i = 0; i < cfg_->slave_num; i++)
|
||||
{
|
||||
slaves.append(nullptr);
|
||||
}
|
||||
if_->set_irq([=](myarray recv)
|
||||
{
|
||||
if(codec_->packCheck(recv)==true){
|
||||
int cmd,src,dst;
|
||||
HandleSlave *handle=nullptr;
|
||||
myarray data=codec_->decode(src,dst,cmd,recv);
|
||||
if((src>slaves.size())||(src<=0)){
|
||||
qWarning("slave addr err:%d",src);
|
||||
int pack_len=0;
|
||||
if(pack_len=codec_->packCheck(recv),pack_len>0){
|
||||
int cmd,src,dst;
|
||||
HandleSlave *handle=nullptr;
|
||||
myarray data=codec_->decode(src,dst,cmd,recv);
|
||||
if((src>slaves.size())||(src<=0)){
|
||||
qWarning("slave addr err:%d",src);
|
||||
}else{
|
||||
if((broadcast_!=nullptr)&&(broadcast_->busy)){
|
||||
broadcast_->addr_response|=1<<(src-1);
|
||||
if(broadcast_->check_response()==true)
|
||||
broadcast_->dolater(cmd,data);
|
||||
}else{
|
||||
handle=slaves[src-1];
|
||||
if(handle!=nullptr){
|
||||
handle->dolater(cmd,data);
|
||||
}else{
|
||||
qWarning("slave addr=%d not have handle.",src);
|
||||
}
|
||||
handle=slaves[src-1];
|
||||
if(handle!=nullptr){
|
||||
handle->dolater(cmd,data);
|
||||
}else{
|
||||
qWarning("slave addr=%d not have handle.",src);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -51,17 +61,38 @@ bool prot_slave::set_slave_handle(int addr, HandleSlave *handle)
|
||||
delete temp;
|
||||
}
|
||||
}
|
||||
handle->addr=addr;
|
||||
connect(handle, &HandleSlave::send_data_signal, this, &prot_slave::send_data_slot);
|
||||
slaves.replace(addr - 1, handle);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool prot_slave::set_boardcast_handle(QList<int> addrs,HandleBoardCast *handle)
|
||||
{
|
||||
if (broadcast_ != nullptr)
|
||||
{
|
||||
if (broadcast_->busy != 0)
|
||||
{
|
||||
delete handle;
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
delete broadcast_;
|
||||
}
|
||||
}
|
||||
broadcast_=handle;
|
||||
broadcast_->trun_list_to_bit(addrs);
|
||||
connect(handle, &HandleBoardCast::send_data_signal, this, &prot_slave::send_data_slot);
|
||||
return true;
|
||||
}
|
||||
|
||||
void prot_slave::send_data_slot(int addr, int cmd, myarray data)
|
||||
{
|
||||
if ((if_ != nullptr) && (codec_ != nullptr))
|
||||
{
|
||||
myarray send = codec_->encode(0, addr, cmd, data);
|
||||
if_->write(send);
|
||||
if_->write(addr,send);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -71,7 +102,7 @@ prot_slave *protSlave()
|
||||
if (g_protslave == nullptr)
|
||||
{
|
||||
g_protslave = new prot_slave();
|
||||
// g_protslave->init();
|
||||
g_protslave->init();
|
||||
}
|
||||
return g_protslave;
|
||||
}
|
||||
|
@@ -19,29 +19,43 @@ public:
|
||||
addr = 0;
|
||||
cmd=0;
|
||||
timer_=nullptr;
|
||||
timer_retry_=nullptr;
|
||||
times_retry=0;
|
||||
}
|
||||
virtual ~HandleSlave() {
|
||||
if(timer_!=nullptr){
|
||||
delete timer_;
|
||||
}
|
||||
if(timer_retry_!=nullptr){
|
||||
delete timer_retry_;
|
||||
}
|
||||
}
|
||||
public:
|
||||
virtual int start(myarray data) = 0;
|
||||
virtual int dolater(int cmd, myarray data) = 0;
|
||||
virtual void timeout()=0;
|
||||
virtual void timeout(){timer_->stop();};
|
||||
int busy;
|
||||
int addr;
|
||||
int cmd;
|
||||
public:
|
||||
int send_data(int cmd,myarray data){
|
||||
emit send_data_signal(addr,cmd,data);
|
||||
protected:
|
||||
// 发送数据到从机
|
||||
int send_data(int cmd,myarray data,int times){
|
||||
this->cmd=cmd;
|
||||
this->data_send=data;
|
||||
this->times_retry=times;
|
||||
if(timer_retry_==nullptr){
|
||||
timer_retry_=new QTimer();
|
||||
connect(timer_,&QTimer::timeout,this,&HandleSlave::timeout_retry);
|
||||
}
|
||||
timer_retry_->start(60);
|
||||
return 0;
|
||||
}
|
||||
// 发送操作结束信号
|
||||
int end(int ack,myarray data){
|
||||
emit end_signal(addr,ack,data);
|
||||
return 0;
|
||||
}
|
||||
protected:
|
||||
// 开始超时计时器,此计时器用于整个操作的超时
|
||||
void timeout_start(int ms){
|
||||
if(timer_==nullptr){
|
||||
timer_=new QTimer();
|
||||
@@ -49,18 +63,158 @@ protected:
|
||||
}
|
||||
timer_->start(ms);
|
||||
}
|
||||
// 停止超时计时器,此方法同时停止重发计时器
|
||||
void timeout_stop(){
|
||||
if(timer_!=nullptr){
|
||||
timer_->stop();
|
||||
}
|
||||
timeout_stop_retry();
|
||||
}
|
||||
// 停止数据回复超时重试计时器
|
||||
void timeout_stop_retry(){
|
||||
if(timer_retry_!=nullptr){
|
||||
timer_retry_->stop();
|
||||
}
|
||||
times_retry=0;
|
||||
}
|
||||
private:
|
||||
// 重试回调
|
||||
void timeout_retry(){
|
||||
if(times_retry>0){
|
||||
times_retry--;
|
||||
emit send_data_signal(addr,cmd,data_send);
|
||||
}else{
|
||||
timer_retry_->stop();
|
||||
}
|
||||
}
|
||||
private:
|
||||
QTimer *timer_;
|
||||
QTimer *timer_retry_;
|
||||
int times_retry;
|
||||
myarray data_send;
|
||||
signals:
|
||||
void send_data_signal(int addr, int cmd, myarray data);
|
||||
void end_signal(int addr,int ack,myarray data);
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
class HandleBoardCast : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
HandleBoardCast() {
|
||||
busy = 0;
|
||||
addr = 0;
|
||||
cmd=0;
|
||||
timer_=nullptr;
|
||||
timer_retry_=nullptr;
|
||||
times_retry=0;
|
||||
addr_response=0;
|
||||
}
|
||||
virtual ~HandleBoardCast() {
|
||||
if(timer_!=nullptr){
|
||||
delete timer_;
|
||||
}
|
||||
if(timer_retry_!=nullptr){
|
||||
delete timer_retry_;
|
||||
}
|
||||
}
|
||||
public:
|
||||
virtual int start(myarray data) = 0;
|
||||
virtual int dolater(int cmd, myarray data) = 0;
|
||||
virtual void timeout(){timer_->stop();};
|
||||
int busy;
|
||||
int addr;
|
||||
int addr_response;
|
||||
int cmd;
|
||||
public:
|
||||
// 判断是否所有从机都返回
|
||||
bool check_response(){
|
||||
return (addr^addr_response)==0?true:false;
|
||||
}
|
||||
// 把地址列表转化为bit
|
||||
void trun_list_to_bit(QList<int> addrs){
|
||||
addr=0;
|
||||
foreach(int adr,addrs){
|
||||
addr|=1<<(adr-1);
|
||||
}
|
||||
}
|
||||
protected:
|
||||
// 发送数据到从机
|
||||
int send_data(int cmd,myarray data,int times){
|
||||
this->cmd=cmd;
|
||||
this->data_send=data;
|
||||
this->times_retry=times;
|
||||
if(timer_retry_==nullptr){
|
||||
timer_retry_=new QTimer();
|
||||
connect(timer_,&QTimer::timeout,this,&HandleBoardCast::timeout_retry);
|
||||
}
|
||||
timer_retry_->start(300);
|
||||
return 0;
|
||||
}
|
||||
// 发送操作结束信号
|
||||
int end(int ack,myarray data){
|
||||
emit end_signal(0x1f,ack,data);
|
||||
return 0;
|
||||
}
|
||||
// 开始超时计时器,此计时器用于整个操作的超时
|
||||
void timeout_start(int ms){
|
||||
if(timer_==nullptr){
|
||||
timer_=new QTimer();
|
||||
connect(timer_,&QTimer::timeout,this,&HandleBoardCast::timeout);
|
||||
}
|
||||
timer_->start(ms);
|
||||
}
|
||||
// 停止超时计时器,此方法同时停止重发计时器
|
||||
void timeout_stop(){
|
||||
if(timer_!=nullptr){
|
||||
timer_->stop();
|
||||
}
|
||||
timeout_stop_retry();
|
||||
}
|
||||
// 停止数据回复超时重试计时器
|
||||
void timeout_stop_retry(){
|
||||
if(timer_retry_!=nullptr){
|
||||
timer_retry_->stop();
|
||||
}
|
||||
times_retry=0;
|
||||
}
|
||||
private:
|
||||
// 重试回调
|
||||
void timeout_retry(){
|
||||
if(times_retry>0){
|
||||
times_retry--;
|
||||
myarray s;
|
||||
int addr_retry=addr^addr_response;
|
||||
// 这里重发只重发没有收到回应的从机
|
||||
s.append(addr_retry&0xff);
|
||||
s.append((addr_retry>>8)&0xff);
|
||||
s.append((addr_retry>>16)&0xff);
|
||||
s.append(data_send);
|
||||
emit send_data_signal(0x1f,cmd,s);
|
||||
}else{
|
||||
timer_retry_->stop();
|
||||
}
|
||||
}
|
||||
private:
|
||||
QTimer *timer_;
|
||||
QTimer *timer_retry_;
|
||||
int times_retry;
|
||||
myarray data_send;
|
||||
signals:
|
||||
void send_data_signal(int addr, int cmd, myarray data);
|
||||
void end_signal(int addr,int ack,myarray data);
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
class prot_slave : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
@@ -69,10 +223,12 @@ public:
|
||||
{
|
||||
if_ = nullptr;
|
||||
codec_ = nullptr;
|
||||
broadcast_=nullptr;
|
||||
}
|
||||
~prot_slave() {}
|
||||
void init();
|
||||
bool set_slave_handle(int addr, HandleSlave *handle);
|
||||
bool set_boardcast_handle(QList<int> addrs,HandleBoardCast *handle);
|
||||
protected slots:
|
||||
void send_data_slot(int addr, int cmd, myarray data);
|
||||
|
||||
@@ -80,6 +236,7 @@ protected:
|
||||
InterFace *if_;
|
||||
Codec *codec_;
|
||||
QList<HandleSlave *> slaves;
|
||||
HandleBoardCast *broadcast_;
|
||||
};
|
||||
|
||||
prot_slave *protSlave();
|
||||
|
Reference in New Issue
Block a user