WLG/threadfunc/thread_func.cpp

412 lines
13 KiB
C++
Raw Normal View History

2024-10-22 19:04:25 +08:00
#include "thread_func.hpp"
#include <map>
#include <time.h>
#include <math.h>
#include <string.h>
#include <cstdlib>
#include <linux/types.h>
#include <sys/sysinfo.h>
2024-10-23 09:22:06 +08:00
#include <dirent.h>
2024-10-22 19:04:25 +08:00
#include <boost/typeof/typeof.hpp>
2024-11-05 15:15:51 +08:00
#include <boost/filesystem.hpp>
2024-10-23 19:51:01 +08:00
#include <zlog.h>
2024-10-23 22:25:03 +08:00
#include <json/json.h>
#include "mqttclient/mqtt_client.h"
2024-10-23 09:22:06 +08:00
#include "uart/uart.hpp"
#include "common/common_func.hpp"
#include "wifi_5g/dial.h"
#include "wifi_5g/wpa_client.h"
2024-10-23 22:25:03 +08:00
#include "utility/tcp_cgi.hpp"
#include "utility/udp_scan.hpp"
#include "utility/search_dev.hpp"
#include "localserver/local_server.hpp"
2024-10-22 19:04:25 +08:00
2024-10-23 22:25:03 +08:00
extern zlog_category_t *zct;
extern zlog_category_t *zbt;
2024-10-22 19:04:25 +08:00
static std::string serverPort;
Dial dial;
2024-11-05 15:15:51 +08:00
static int clean_memory = 0;
2024-10-22 19:04:25 +08:00
void StartCgiServer() {
2024-10-24 20:54:29 +08:00
zlog_info(zbt, "start deal cgi");
2024-10-23 22:25:03 +08:00
2024-10-22 19:04:25 +08:00
while (1) {
2024-10-24 20:54:29 +08:00
TcpCgi::startCgiServer();
2024-10-22 19:04:25 +08:00
sleep(10);
}
}
void RunLED() {
while (1) {
gpio_set(GlobalConfig::GPIO_G.runLed, 1);
sleep(1);
gpio_set(GlobalConfig::GPIO_G.runLed, 0);
sleep(1);
}
}
void HeartRep() {
2024-11-11 20:51:40 +08:00
int count = 0;
2024-10-22 19:04:25 +08:00
while (1) {
Json::Value jsHeart;
Json::FastWriter fw;
jsHeart["dataNodeGatewayNo"] = GlobalConfig::MacAddr_G;
jsHeart["status"] = "online_V" + GlobalConfig::Version;
jsHeart["IP"] = GlobalConfig::IpAddr_G;
std::string strJson = fw.write(jsHeart);
int iRet = data_publish(strJson.c_str(), GlobalConfig::Topic_G.mPubHeart.c_str());
2024-10-24 20:54:29 +08:00
if (iRet != 0) {
2024-11-11 20:51:40 +08:00
zlog_warn(zct, "fail to send heart mqtt msg");
2024-10-24 20:54:29 +08:00
}
2024-11-11 20:51:40 +08:00
if (count == 10){
zlog_warn(zct, "heart = %s,iRet = %d", strJson.c_str(), iRet);
count = 0;
}else{
zlog_info(zct, "heart = %s,iRet = %d", strJson.c_str(), iRet);
}
2024-10-22 19:04:25 +08:00
if (iRet != 0) {
gpio_set(GlobalConfig::GPIO_G.errorLed, 1);
sleep(1);
gpio_set(GlobalConfig::GPIO_G.errorLed, 0);
sleep(1);
gpio_set(GlobalConfig::GPIO_G.errorLed, 1);
sleep(1);
gpio_set(GlobalConfig::GPIO_G.errorLed, 0);
sleep(1);
gpio_set(GlobalConfig::GPIO_G.errorLed, 1);
sleep(1);
GlobalConfig::serverStatus = 1;
} else {
GlobalConfig::serverStatus = 0;
gpio_set(GlobalConfig::GPIO_G.errorLed, 0);
}
2024-11-08 16:55:14 +08:00
sleep(30);
2024-11-11 20:51:40 +08:00
count ++;
2024-10-22 19:04:25 +08:00
}
}
void GetCSQ() {
#ifdef NR5G_MODULE
// 5G
int iRet = -1;
open5G:
iRet = dial.openPort("/dev/ttyUSB2");
if (iRet < 0) {
sleep(5);
goto open5G;
}
#ifdef NR5G_MEIGE
dial.closePort();
char szquectel[100] = {0x00};
std::string strAPN = ReadStrByOpt(SERVERCONFIG, "Server", "APN");
sprintf(szquectel, "/opt/quectel-CM/Meig-CM -s %s &", strAPN.c_str());
system(szquectel);
#else
dial.recvData();
#endif
#endif
#ifdef Q4G_MODULE
// 4G
int fd = -1;
open4G:
fd = config_uart("/dev/ttyUSB2", 115200);
if (fd < 0) {
sleep(5);
goto open4G;
}
char szbuffer[200] = {0x00};
int offSize = 0;
int timeoutflag = 0;
write_data(fd, "AT+QENG=\"servingcell\"\r\n", 27);
while (1) {
char buff[1024] = {0x00};
int ret = read_data(fd, buff, 1024, 10);
if (ret <= 0) {
timeoutflag++;
if (timeoutflag > 5) {
2024-12-02 20:11:58 +08:00
zlog_info(zbt,"timeoutflag = %d\n", timeoutflag);
2024-10-22 19:04:25 +08:00
timeoutflag = 0;
const char *str2 = "+QENG: ";
char csq[128] = {0};
char *pdata = strstr((char *)szbuffer, str2);
if (pdata) {
strncpy(csq, pdata + 7, sizeof(csq));
GlobalConfig::NetStatus = GetOneContent(csq, 1, ",");
2024-12-02 20:11:58 +08:00
std::string signal = GetOneContent(csq, 13, ",");
2024-10-22 19:04:25 +08:00
GlobalConfig::NetSignal = atoi(signal.c_str());
GlobalConfig::NetType = GetOneContent(csq, 2, ",");
2024-10-24 20:54:29 +08:00
zlog_info(zct, "NetStatus = %s,NetSignal = %d", GlobalConfig::NetStatus.c_str(), GlobalConfig::NetSignal);
2024-10-22 19:04:25 +08:00
}
memset(szbuffer, 0x00, sizeof(szbuffer));
offSize = 0;
write_data(fd, "AT+QENG=\"servingcell\"\r\n", 27);
}
usleep(10000);
} else if (ret > 0) {
2024-10-24 20:54:29 +08:00
zlog_info(zct, "ret = %d,buff = %s", ret, buff);
2024-10-22 19:04:25 +08:00
memcpy(szbuffer + offSize, buff, ret);
offSize = offSize + ret;
2024-10-24 20:54:29 +08:00
zlog_info(zct, "szbuffer = %s", szbuffer);
2024-10-22 19:04:25 +08:00
continue;
}
sleep(10);
}
#endif
}
2024-10-24 20:54:29 +08:00
2024-10-22 19:04:25 +08:00
void Dial5G() {
sleep(2);
dial5G:
if (dial.m_fd > 0) {
dial.dial5G();
} else {
sleep(5);
goto dial5G;
}
}
void UartStart() {
2024-10-24 20:54:29 +08:00
zlog_info(zbt, "zigAckrep = %d,zigAckreset = %d,zigReset = %d,errorLed = %d,power = %d", GlobalConfig::GPIO_G.zigAckrep, GlobalConfig::GPIO_G.zigAckreset, GlobalConfig::GPIO_G.zigReset, GlobalConfig::GPIO_G.errorLed, GlobalConfig::GPIO_G.power);
2024-10-22 19:04:25 +08:00
InitGpio(GlobalConfig::GPIO_G.zigAckrep, 0); // ACK
InitGpio(GlobalConfig::GPIO_G.zigAckreset, 1); // ACK reset
InitGpio(GlobalConfig::GPIO_G.zigReset, 1); // Zigbee reset
gpio_set(GlobalConfig::GPIO_G.zigAckreset, 1);
gpio_set(GlobalConfig::GPIO_G.zigReset, 1);
2024-10-24 20:54:29 +08:00
zlog_info(zbt, "GPIO Init");
2024-10-22 19:04:25 +08:00
InitGpio(GlobalConfig::GPIO_G.runLed, 1);
InitGpio(GlobalConfig::GPIO_G.errorLed, 1);
gpio_set(GlobalConfig::GPIO_G.runLed, 1);
gpio_set(GlobalConfig::GPIO_G.errorLed, 0);
InitGpio(GlobalConfig::GPIO_G.netResetNet0, 1);
gpio_set(GlobalConfig::GPIO_G.netResetNet0, 0);
2024-11-14 19:44:21 +08:00
2024-10-22 19:04:25 +08:00
GlobalConfig::Zigbee_G.Serial_Rate = 0x07;
GlobalConfig::Zigbee_G.Serial_DataB = 0x08;
GlobalConfig::Zigbee_G.Serial_StopB = 0x01;
uart_inst::instance().InitUart(B115200);
char buffer[1100] = {0x00};
sleep(1);
uart_inst::instance().UartRecv(uart_inst::instance().fd, 1, buffer);
sleep(1);
}
2024-10-24 20:54:29 +08:00
2024-10-22 19:04:25 +08:00
void InitModule() {
#ifdef NR5G_MODULE
InitGpio(GlobalConfig::GPIO_G.commPower, 1); // 4G,5G模组供电
gpio_set(GlobalConfig::GPIO_G.commPower, 1);
InitGpio(GlobalConfig::GPIO_G.vol3_8, 1); // 5G 高电平3.8V低电平3.3V
gpio_set(GlobalConfig::GPIO_G.vol3_8, 1);
InitGpio(GlobalConfig::GPIO_G.commRest, 1);
gpio_set(GlobalConfig::GPIO_G.commRest, 0); //高电平复位
2024-11-14 19:44:21 +08:00
2024-10-24 20:54:29 +08:00
#endif // NR5G_MODULE
2024-10-22 19:04:25 +08:00
#ifdef Q4G_MODULE
2024-11-14 19:44:21 +08:00
2024-11-28 09:16:56 +08:00
system("killall daemon_CM");
InitGpio(GlobalConfig::GPIO_G.commPower,1);//4G,5G模组供电
gpio_set(GlobalConfig::GPIO_G.commPower,1);
InitGpio(GlobalConfig::GPIO_G.commRest,1);
gpio_set(GlobalConfig::GPIO_G.commRest,0);//高电平复位
sleep(10);
char szquectel[100]={0x00};
std::string strAPN = ReadStrByOpt(SERVERCONFIG, "Server", "APN");
sprintf(szquectel,"/opt/quectel-CM/quectel-CM -s %s &",strAPN.c_str());
system(szquectel);
sleep(2);
system("/opt/Cidn/daemon_CM &");
2024-10-24 20:54:29 +08:00
#endif // Q4G_MODULE
2024-10-22 19:04:25 +08:00
#ifdef WIFI_MODULE
2024-10-24 20:54:29 +08:00
zlog_info(zbt, "Init WiFi!");
2024-10-22 19:04:25 +08:00
InitGpio(GlobalConfig::GPIO_G.wifiReset, 1); // WiFi模组复位1复位0取消复位
gpio_set(GlobalConfig::GPIO_G.wifiReset, 0);
InitGpio(GlobalConfig::GPIO_G.wifiPower, 1); // WiFi模组上电
gpio_set(GlobalConfig::GPIO_G.wifiPower, 1);
sleep(10);
wifi::WPAClient wpa;
wpa.ReconnectWiFi();
system("/usr/sbin/wpa_supplicant -Dnl80211 -iwlan0 -c/etc/wpa_supplicant.conf &");
system("udhcpc -b -i wlan0 &");
2024-10-24 20:54:29 +08:00
#endif // WIFI_MODULE
2024-10-22 19:04:25 +08:00
}
2024-10-24 20:54:29 +08:00
2024-10-22 19:04:25 +08:00
void TestUart() {
uart_inst::instance().InitTestUart(B115200);
uart_inst::instance().ReadTestUart();
}
void UartStartWave() { uart_inst::instance().DealWaveThread(); }
void StartUdpSys() { udp_sys::instance().StartConnectSysUdp(); }
2024-10-24 20:54:29 +08:00
2024-10-22 19:04:25 +08:00
void WatchDog() {
int fd = OpenWatchDog();
while (1) {
WriteWatchDog(fd);
sleep(50);
}
close(fd);
}
2024-10-24 20:54:29 +08:00
2024-10-22 19:04:25 +08:00
void StartMqttClient() {
2024-10-24 20:54:29 +08:00
zlog_info(zct, "start mqtt \n");
2024-10-22 19:04:25 +08:00
std::string runinfo = "MQTT通信模块启动";
while (1) {
if (GlobalConfig::ServerIP.length() > 0) {
std::string strEqupNo = GlobalConfig::MacAddr_G;
std::string strVersion = GlobalConfig::Version;
2024-10-25 09:35:37 +08:00
std::string salt;
2024-10-22 19:04:25 +08:00
start_client(strEqupNo.c_str(), GlobalConfig::MacAddr_G.c_str(), GlobalConfig::ServerIP.c_str(), strVersion.c_str(), "11111111", salt);
2024-10-24 20:36:27 +08:00
zlog_error(zct, "fail to connect server");
2024-10-22 19:04:25 +08:00
}
2024-10-24 20:36:27 +08:00
sleep(10);
2024-10-22 19:04:25 +08:00
}
}
void SearchThread() {
std::string runinfo = "设备搜索模块启动";
while (GlobalConfig::QuitFlag_G) {
if (GlobalConfig::IpAddr_G.length() > 0 && 0 != GlobalConfig::IpAddr_G.compare("0.0.0.0")) {
2024-10-23 22:25:03 +08:00
zlog_info(zct, "%s\n", runinfo.c_str());
2024-10-22 19:04:25 +08:00
boost::asio::io_service io_service;
SearchDev *searchDevObj = new SearchDev(io_service);
searchDevObj->MultiCastRecv();
io_service.run();
delete searchDevObj;
}
sleep(5);
2024-10-23 22:25:03 +08:00
zlog_info(zct, "SearchThread restart.");
2024-10-22 19:04:25 +08:00
}
}
void RecvUpdateFile() {
boost::asio::io_service iosev;
boost::asio::ip::tcp::acceptor acceptor(iosev, boost::asio::ip::tcp::endpoint(boost::asio::ip::tcp::v4(), 7304));
for (;;) {
boost::asio::ip::tcp::socket socket(iosev);
acceptor.accept(socket);
boost::system::error_code ec;
if (ec) {
2024-10-24 16:01:21 +08:00
zlog_error(zct, "%s\n", boost::system::system_error(ec).what());
2024-10-22 19:04:25 +08:00
}
FILE *fp;
char buffer[1024];
size_t len = 0;
2024-10-23 22:25:03 +08:00
size_t write_len;
2024-10-22 19:04:25 +08:00
bzero(buffer, 1024);
fp = fopen("/tmp/upgrade.tar.gz", "w");
if (NULL == fp) {
2024-10-24 20:54:29 +08:00
zlog_error(zbt, "File:/tmp/upgrade.tar.gz Can Not Open");
return;
2024-10-22 19:04:25 +08:00
}
2024-10-24 20:54:29 +08:00
2024-10-24 16:01:21 +08:00
while ((len = socket.read_some(boost::asio::buffer(buffer), ec))) {
2024-10-22 19:04:25 +08:00
write_len = fwrite(buffer, sizeof(char), len, fp);
if (write_len < len) {
2024-10-23 22:25:03 +08:00
zlog_info(zct, "File:test Write Failed!");
2024-10-22 19:04:25 +08:00
break;
}
bzero(buffer, 1024);
}
2024-10-24 20:54:29 +08:00
zlog_info(zbt, "Receive File From Server Finished!");
2024-10-22 19:04:25 +08:00
fclose(fp);
Json::Value jsData;
Json::FastWriter fw;
jsData["cmd"] = "03";
jsData["updatefilename"] = "updatefile";
std::string str = fw.write(jsData);
2024-10-24 20:54:29 +08:00
zlog_warn(zbt, "==============upgrade start===============");
system("/etc/init.d/sysupgrade.sh");
2024-10-22 19:04:25 +08:00
}
}
2024-11-05 15:15:51 +08:00
bool InsufficientFreeMemory() {
long mem_free = -1;
char name1[20];
std::string strMemFree = GetFileContent("/proc/meminfo", 2);
sscanf(strMemFree.c_str(), "%s%ld", name1, &mem_free);
2024-11-05 15:50:22 +08:00
mem_free = mem_free / 1024;
2024-11-05 15:15:51 +08:00
if (mem_free < 80) {
2024-11-05 15:50:22 +08:00
zlog_warn(zct, "free memory: %ld MB", mem_free);
2024-11-05 15:15:51 +08:00
return true;
} else {
return false;
}
}
void CleanLogFile(std::string log_dir, size_t retain) {
std::vector<LogFileProperty> vec;
boost::filesystem::path directory = log_dir;
try {
if (boost::filesystem::exists(directory) && boost::filesystem::is_directory(directory)) {
for (auto&& file : boost::filesystem::directory_iterator(directory)) {
if (boost::filesystem::is_regular_file(file)) {
LogFileProperty file_prop;
std::cout<<"["<<file.path()<<"]"<<std::endl;
file_prop.name = file.path().string();
file_prop.time_stamp = boost::filesystem::last_write_time(file);
vec.push_back(file_prop);
}
}
if (vec.size() > 0) {
std::sort(vec.begin(), vec.end());
if (vec.size() <= retain) {
zlog_warn(zct, "[DiskSpaceCheck] there is no enough file to clean:%d", vec.size());
return;
}
int total = vec.size();
for (int i = retain; i < total; ++i) {
boost::filesystem::remove(vec[i].name);
zlog_warn(zct, "[DiskSpaceCheck] *** delete %s", vec[i].name.c_str());
}
}
}
} catch (const boost::filesystem::filesystem_error& ex) {
zlog_error(zct, " Error accessing directory: %s", ex.what());
}
}
void DiskSpaceCheck() {
std::string directory = "/opt/log";
2024-11-25 19:00:15 +08:00
std::string directory_data = "/opt/data";
2024-11-05 15:15:51 +08:00
while (1) {
2024-11-07 11:21:55 +08:00
boost::filesystem::space_info si = boost::filesystem::space("/opt");
2024-11-25 19:00:15 +08:00
if (si.free <= 512000000) {
2024-11-07 11:21:55 +08:00
zlog_warn(zct, "disk free space:%llu for /opt", si.free);
2024-11-25 19:00:15 +08:00
CleanLogFile(directory, 10);
CleanLogFile(directory_data, 100);
2024-11-05 15:15:51 +08:00
boost::filesystem::space_info si1 = boost::filesystem::space("/opt");
2024-11-25 19:00:15 +08:00
if (si1.free <= 512000000) {
2024-11-05 15:15:51 +08:00
zlog_warn(zct, "[DiskSpaceCheck] can not release enough space and clean more log file");
CleanLogFile(directory, 5);
}
}
if (clean_memory == 10) { // 10*30 = 300秒清理一次内存
clean_memory = 0;
if (InsufficientFreeMemory()) {
system("sync");
sleep(10);
system("echo 3 > /proc/sys/vm/drop_caches");
if (InsufficientFreeMemory()) {
zlog_error(zct, "can not release more space, so reboot");
system("sync");
sleep(3);
system("reboot");
}
}
} else {
clean_memory++;
}
sleep(30);
}
}