物联协议在0905上测试通过
This commit is contained in:
parent
466cdae9ad
commit
a1c72b8774
|
@ -0,0 +1,154 @@
|
|||
#include "LinkBoard.h"
|
||||
|
||||
#include "Drivers\W5500.h"
|
||||
#include "Drivers\Esp8266\Esp8266.h"
|
||||
|
||||
LinkBoard::LinkBoard()
|
||||
{
|
||||
Client = nullptr;
|
||||
|
||||
Data = nullptr;
|
||||
Size = 0;
|
||||
}
|
||||
|
||||
void* LinkBoard::InitData(void* data, int size)
|
||||
{
|
||||
// 启动信息
|
||||
auto hot = &HotConfig::Current();
|
||||
hot->Times++;
|
||||
|
||||
data = hot->Next();
|
||||
if (hot->Times == 1)
|
||||
{
|
||||
Buffer ds(data, size);
|
||||
ds.Clear();
|
||||
ds[0] = size;
|
||||
}
|
||||
|
||||
Data = data;
|
||||
Size = size;
|
||||
|
||||
#if DEBUG
|
||||
debug_printf("数据区[%d]:", hot->Times);
|
||||
Buffer(Data, Size).Show(true);
|
||||
#endif
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
// 写入数据区并上报
|
||||
void LinkBoard::Write(uint offset, byte data)
|
||||
{
|
||||
auto client = Client;
|
||||
if (!client) return;
|
||||
|
||||
client->Store.Write(offset, data);
|
||||
client->ReportAsync(offset, 1);
|
||||
}
|
||||
|
||||
/******************************** Link ********************************/
|
||||
|
||||
void LinkBoard::InitClient()
|
||||
{
|
||||
if (Client) return;
|
||||
|
||||
// 初始化配置区
|
||||
InitConfig();
|
||||
|
||||
// 初始化令牌网
|
||||
auto tk = LinkConfig::Create("tcp://192.168.0.3:2233");
|
||||
|
||||
// 创建客户端
|
||||
auto tc = LinkClient::CreateFast(Buffer(Data, Size));
|
||||
tc->Cfg = tk;
|
||||
tc->MaxNotActive = 8 * 60 * 1000;
|
||||
|
||||
Client = tc;
|
||||
}
|
||||
|
||||
void LinkBoard::Register(uint offset, IDataPort& dp)
|
||||
{
|
||||
if (!Client) return;
|
||||
|
||||
auto& ds = Client->Store;
|
||||
ds.Register(offset, dp);
|
||||
}
|
||||
|
||||
void LinkBoard::Register(uint offset, uint size, Handler hook)
|
||||
{
|
||||
if (!Client) return;
|
||||
|
||||
auto& ds = Client->Store;
|
||||
ds.Register(offset, size, hook);
|
||||
}
|
||||
|
||||
void LinkBoard::OnLongPress(InputPort* port, bool down)
|
||||
{
|
||||
if (down) return;
|
||||
|
||||
debug_printf("Press P%c%d Time=%d ms\r\n", _PIN_NAME(port->_Pin), port->PressTime);
|
||||
|
||||
auto client = Client;
|
||||
if (!client) return;
|
||||
|
||||
ushort time = port->PressTime;
|
||||
if (time >= 5000 && time < 10000)
|
||||
{
|
||||
client->Reset("按键重置");
|
||||
}
|
||||
else if (time >= 3000)
|
||||
{
|
||||
client->Reboot("按键重启");
|
||||
Sys.Reboot(1000);
|
||||
}
|
||||
}
|
||||
|
||||
NetworkInterface* LinkBoard::Create5500()
|
||||
{
|
||||
debug_printf("\r\nW5500::Create \r\n");
|
||||
|
||||
auto net = new W5500(Net.Spi, Net.Irq, Net.Reset);
|
||||
if (!net->Open())
|
||||
{
|
||||
delete net;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
net->SetLed(*Leds[0]);
|
||||
net->EnableDNS();
|
||||
net->EnableDHCP();
|
||||
|
||||
return net;
|
||||
}
|
||||
|
||||
NetworkInterface* LinkBoard::Create8266()
|
||||
{
|
||||
debug_printf("\r\nEsp8266::Create \r\n");
|
||||
|
||||
auto esp = new Esp8266();
|
||||
esp->Init(Esp.Com, Esp.Baudrate);
|
||||
esp->Set(Esp.Power, Esp.Reset, Esp.LowPower);
|
||||
|
||||
// 初次需要指定模式 否则为 Wire
|
||||
bool join = esp->SSID && *esp->SSID;
|
||||
if (!join)
|
||||
{
|
||||
*esp->SSID = "WSWL";
|
||||
*esp->Pass = "12345678";
|
||||
|
||||
esp->Mode = NetworkType::STA_AP;
|
||||
esp->WorkMode = NetworkType::STA_AP;
|
||||
}
|
||||
|
||||
if (!esp->Open())
|
||||
{
|
||||
delete esp;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
esp->SetLed(*Leds[1]);
|
||||
//Client->Register("SetWiFi", &Esp8266::SetWiFi, esp);
|
||||
//Client->Register("GetWiFi", &Esp8266::GetWiFi, esp);
|
||||
|
||||
return esp;
|
||||
}
|
|
@ -0,0 +1,48 @@
|
|||
#ifndef _LinkBoard_H_
|
||||
#define _LinkBoard_H_
|
||||
|
||||
#include "Net\Socket.h"
|
||||
|
||||
#include "Device\Spi.h"
|
||||
#include "Device\SerialPort.h"
|
||||
|
||||
#include "BaseBoard.h"
|
||||
|
||||
#include "Link\LinkClient.h"
|
||||
|
||||
// 物联协议板级包基类
|
||||
class LinkBoard : public BaseBoard
|
||||
{
|
||||
public:
|
||||
LinkClient* Client; // 物联客户端
|
||||
|
||||
LinkBoard();
|
||||
|
||||
// 设置数据区
|
||||
void* InitData(void* data, int size);
|
||||
// 写入数据区并上报
|
||||
void Write(uint offset, byte data);
|
||||
|
||||
typedef bool(*Handler)(uint offset, uint size, bool write);
|
||||
void Register(uint offset, uint size, Handler hook);
|
||||
void Register(uint offset, IDataPort& dp);
|
||||
|
||||
void OnLongPress(InputPort* port, bool down);
|
||||
void Restore();
|
||||
|
||||
void InitClient();
|
||||
|
||||
SpiConfig Net;
|
||||
SerialConfig Esp;
|
||||
|
||||
// 打开以太网W5500
|
||||
NetworkInterface* Create5500();
|
||||
// 打开Esp8266,作为主控或者纯AP
|
||||
NetworkInterface* Create8266();
|
||||
|
||||
private:
|
||||
void* Data;
|
||||
int Size;
|
||||
};
|
||||
|
||||
#endif
|
|
@ -28,6 +28,10 @@ LinkClient::LinkClient()
|
|||
Delay = 0;
|
||||
MaxNotActive = 0;
|
||||
|
||||
_task = 0;
|
||||
ReportStart = 0;
|
||||
ReportLength = 0;
|
||||
|
||||
assert(!Current, "只能有一个物联客户端实例");
|
||||
Current = this;
|
||||
}
|
||||
|
@ -123,6 +127,8 @@ void LinkClient::LoopTask()
|
|||
Ping();
|
||||
break;
|
||||
}
|
||||
|
||||
CheckReport();
|
||||
}
|
||||
|
||||
uint LinkClient::Dispatch(ITransport* port, Buffer& bs, void* param, void* param2)
|
||||
|
@ -397,6 +403,31 @@ void LinkClient::OnPing(LinkMessage& msg)
|
|||
if (serverTime > 1000) ((TTime&)Time).SetTime(serverTime);
|
||||
}
|
||||
|
||||
void LinkClient::Reset(const String& reason)
|
||||
{
|
||||
Json js;
|
||||
js.Add("time", DateTime::Now().TotalSeconds());
|
||||
js.Add("reason", reason);
|
||||
|
||||
Invoke("Reset", js);
|
||||
|
||||
debug_printf("设备500ms后重置\r\n");
|
||||
|
||||
Sys.Sleep(500);
|
||||
|
||||
Config::Current->RemoveAll();
|
||||
Sys.Reboot();
|
||||
}
|
||||
|
||||
void LinkClient::Reboot(const String& reason)
|
||||
{
|
||||
Json js;
|
||||
js.Add("time", DateTime::Now().TotalSeconds());
|
||||
js.Add("reason", reason);
|
||||
|
||||
Invoke("Reboot", js);
|
||||
}
|
||||
|
||||
void LinkClient::OnRead(LinkMessage& msg)
|
||||
{
|
||||
TS("LinkClient::OnRead");
|
||||
|
@ -441,3 +472,72 @@ void LinkClient::OnWrite(LinkMessage& msg)
|
|||
|
||||
Reply(js["action"].AsString(), msg.Seq, 0, rs);
|
||||
}
|
||||
|
||||
void LinkClient::Write(int start, const Buffer& bs)
|
||||
{
|
||||
Json js;
|
||||
js.Add("start", start);
|
||||
js.Add("data", bs.ToHex());
|
||||
|
||||
Invoke("Write", js);
|
||||
}
|
||||
|
||||
void LinkClient::Write(int start, byte dat)
|
||||
{
|
||||
Write(start, Buffer(&dat, 1));
|
||||
}
|
||||
|
||||
void LinkClient::ReportAsync(int start, uint length)
|
||||
{
|
||||
if (start<0 || start + (int)length > Store.Data.Length())
|
||||
{
|
||||
debug_printf("布置异步上报数据失败\r\n");
|
||||
debug_printf("start=%d len:%d data.len:%d\r\n", start, length, Store.Data.Length());
|
||||
return;
|
||||
}
|
||||
|
||||
ReportStart = start;
|
||||
ReportLength = length;
|
||||
|
||||
// 延迟上报,期间有其它上报任务到来将会覆盖
|
||||
Sys.SetTask(_task, true, 20);
|
||||
}
|
||||
|
||||
bool LinkClient::CheckReport()
|
||||
{
|
||||
TS("LinkClient::CheckReport");
|
||||
|
||||
auto offset = ReportStart;
|
||||
int len = ReportLength;
|
||||
|
||||
if (offset < 0) return false;
|
||||
|
||||
// 检查索引,否则数组越界
|
||||
auto& bs = Store.Data;
|
||||
if (bs.Length() >= offset + len) Write(offset, Buffer(&bs[offset], len));
|
||||
|
||||
ReportStart = -1;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// 快速建立客户端,注册默认Api
|
||||
LinkClient* LinkClient::CreateFast(const Buffer& store)
|
||||
{
|
||||
auto tc = new LinkClient();
|
||||
|
||||
/*// 重启
|
||||
tc->Register("Gateway/Restart", &LinkClient::InvokeRestart, tc);
|
||||
// 重置
|
||||
tc->Register("Gateway/Reset", &LinkClient::InvokeReset, tc);
|
||||
// 设置远程地址
|
||||
tc->Register("Gateway/SetRemote", &LinkClient::InvokeSetRemote, tc);
|
||||
// 获取远程配置信息
|
||||
tc->Register("Gateway/GetRemote", &LinkClient::InvokeGetRemote, tc);
|
||||
// 获取所有Invoke命令
|
||||
tc->Register("Api/All", &LinkClient::InvokeGetAllApi, tc);*/
|
||||
|
||||
if (store.Length()) tc->Store.Data.Set(store.GetBuffer(), store.Length());
|
||||
|
||||
return tc;
|
||||
}
|
||||
|
|
|
@ -3,6 +3,9 @@
|
|||
|
||||
#include "Kernel\Sys.h"
|
||||
|
||||
#include "Net\ITransport.h"
|
||||
#include "Net\Socket.h"
|
||||
|
||||
#include "Message\DataStore.h"
|
||||
#include "Message\Json.h"
|
||||
|
||||
|
@ -38,6 +41,16 @@ public:
|
|||
bool Invoke(const String& action, const Json& args);
|
||||
bool Reply(const String& action, int seq, int code, const Json& result);
|
||||
|
||||
void Read(int start, int size);
|
||||
void Write(int start, const Buffer& bs);
|
||||
void Write(int start, byte dat);
|
||||
|
||||
// 异步上传并等待响应,返回实际上传字节数
|
||||
int WriteAsync(int start, const Buffer& bs, int msTimeout);
|
||||
|
||||
// 必须满足 start > 0 才可以。
|
||||
void ReportAsync(int start, uint length = 1);
|
||||
|
||||
// 收到功能消息时触发
|
||||
//MessageHandler Received;
|
||||
void* Param;
|
||||
|
@ -48,6 +61,13 @@ public:
|
|||
// 心跳,用于保持与对方的活动状态
|
||||
void Ping();
|
||||
|
||||
// 重置并上报
|
||||
void Reset(const String& reason);
|
||||
void Reboot(const String& reason);
|
||||
|
||||
// 快速建立客户端,注册默认Api
|
||||
static LinkClient* CreateFast(const Buffer& store);
|
||||
|
||||
static LinkClient* Current;
|
||||
|
||||
private:
|
||||
|
@ -62,9 +82,12 @@ private:
|
|||
|
||||
private:
|
||||
uint _task;
|
||||
int ReportStart; // 下次上报偏移,-1不动
|
||||
byte ReportLength; // 下次上报数据长度
|
||||
|
||||
void LoopTask();
|
||||
void CheckNet();
|
||||
bool CheckReport();
|
||||
|
||||
static uint Dispatch(ITransport* port, Buffer& bs, void* param, void* param2);
|
||||
};
|
||||
|
|
|
@ -38,6 +38,7 @@
|
|||
<ClCompile Include="..\Board\IOK026X.cpp" />
|
||||
<ClCompile Include="..\Board\IOK027X.cpp" />
|
||||
<ClCompile Include="..\Board\IOK0612.cpp" />
|
||||
<ClCompile Include="..\Board\LinkBoard.cpp" />
|
||||
<ClCompile Include="..\Board\NH3_0317.cpp" />
|
||||
<ClCompile Include="..\Board\Pandora.cpp" />
|
||||
<ClCompile Include="..\Board\TokenBoard.cpp" />
|
||||
|
|
|
@ -593,5 +593,8 @@
|
|||
<ClCompile Include="..\Link\LinkConfig.cpp">
|
||||
<Filter>Link</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\Board\LinkBoard.cpp">
|
||||
<Filter>Board</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
</Project>
|
Loading…
Reference in New Issue