Files
ECAP_Server/module/Local_Server/Data_Source/Data_Source_Handler.cpp
T
2026-06-23 14:01:23 +08:00

265 lines
10 KiB
C++
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#include "Data_Source_Handler.h"
#include "Data_Source.h"
#include "Local_Server/server/Global.h"
using namespace Psc;
std::shared_ptr<Data_Source> ds(Data_Source_Handler* dsh) {
return dynamic_cast<Data_Source*>(dsh)->that();
}
std::shared_ptr<SSR::Msg> Data_Source_Handler::create_msg(
const std::string &packet) {
auto source = ds(this);
if (packet[0] != 0x1a)
{
std::cout << "first:" << mem2hex(packet) << std::endl;
return nullptr;
}
std::string error_len = source->key + " " + LOG_POS_SIMPLE + std::string(" ") + "mode_s_error_length";
if (packet.size() < 2) return nullptr;
auto mt = packet[1];
if (mt == SSR::Msg::AC)
{
if (packet.size() != SSR::Msg::AC_len)
{
SSR::mode_s_logger->c_debug(error_len, {},
std::to_string(mt) + " size:" + std::to_string(packet.size()) +
" hex:" + mem2hex(packet) + " should:" + std::to_string(SSR::Msg::AC_len));
mode_ac_statistic.add_length_error();
return nullptr;
}
mode_ac_statistic.add();
return std::make_shared<SSR::Mode_AC_Msg>(source, packet);
}
if (mt == SSR::Msg::S7)
{
if (packet.size() != SSR::Mode_S_Msg::S7_len)
{
SSR::mode_s_logger->c_debug(error_len, {},
std::to_string(mt) + " size:" + std::to_string(packet.size()) +
" hex:" + mem2hex(packet) + " should:" + std::to_string(SSR::Msg::S7_len));
mode_s_statistic.add_length_error("[length error] Msg::S7 handle_mode_s_source");
return nullptr;
}
return std::make_shared<SSR::Mode_S_Msg>(source, packet);
}
if (mt == SSR::Msg::S14)
{
if (packet.size() != SSR::Msg::S14_len)
{
SSR::mode_s_logger->c_debug(error_len, {},
std::to_string(mt) + " size:" + std::to_string(packet.size()) +
" hex:" + mem2hex(packet) + " should:" + std::to_string(SSR::Msg::S14_len));
mode_s_statistic.add_length_error("[length error] Msg::S14 handle_mode_s_source");
return nullptr;
}
return std::make_shared<SSR::Mode_S_Msg>(source, packet);
}
if (mt == SSR::Msg::Radarcape_status) {
return nullptr; // 不知道如何解析跳过
if (packet.size() != SSR::Msg::Radarcape_status_len)
{
SSR::mode_s_logger->c_debug(error_len, {},
std::to_string(mt) + " size:" + std::to_string(packet.size()) +
" hex:" + mem2hex(packet) + " should:" + std::to_string(SSR::Msg::Radarcape_status_len));
mode_s_statistic.add_length_error("[length error] Msg::Radarcape_status_len handle_mode_s_source");
return nullptr;
}
return std::make_shared<SSR::Msg>(source, packet);
}
if (mt == SSR::Msg::HULC_Status)
{
if (packet.size() != SSR::Msg::HULC_len)
{
// 找不到协议 size:23 hex:1A34195F0000001500B502FF06F423CE50000090000000 should:5
SSR::mode_s_logger->c_debug(error_len, {},
Psc::to_string(source->type) + " HULC size:" +
std::to_string(packet.size()) + " hex:" + mem2hex(packet));
return nullptr;
}
return std::make_shared<SSR::Msg>(source, packet);
}
// std::cout << "unknown_type:" << memory2hex(packet);
rotating_log("unknown_type", mem2hex(packet));
return nullptr;
}
void Data_Source_Handler::process_mode_acs_data(const std::string& mode_data) {
auto source = ds(this);
auto size = mode_data.size();
read_speed.update(size);
value_statistics.update(size);
// 预处理数据
static bool mode_s_console = Global::instance()->console_config.mode_s_console;
static bool record_playback = Global::instance()->console_config.record_playback;
if (mode_data.empty()) return;
if (record_playback) {
pure_log(get_exe_dir() + "/playback/" + source->key + "_playback.dat", mem2hex(mode_data, true, " ") + "\n");
}
if (mode_s_console) {
std::cout << source->key + " read:[mode_s_serial]:" << mem2hex(mode_data) << std::endl;
}
SSR::Binary_Format_handle_buffer(source->buffer, mode_data, [this, source](std::string& packet) {
auto msg = create_msg(packet);
if (!msg) return;
source->push_to_feed(msg);
auto mt = msg->type;
bool mode_s = mt == SSR::Msg::S7 || mt == SSR::Msg::S14;
if (mt == SSR::Msg::HULC_Status) {
source->handle_HULC(packet);
}
else if (mt == SSR::Msg::Radarcape_status) {
auto radarcape_msg = SSR::create_Radarcape_STATUS_Message(packet);
std::cout << radarcape_msg.toJson().to_json_string() << std::endl;
SSR::mode_s_logger->debug("Radarcape_status/radarcape", {}, radarcape_msg.toJson().to_json_string());
}
else if (mode_s)
{
// 拓展点
handle_mode_s(std::dynamic_pointer_cast<SSR::Mode_S_Msg>(msg));
}
});
}
void Data_Source_Handler::handle_mode_s(std::shared_ptr<SSR::Mode_S_Msg> mode_s_msg) {
auto source = ds(this);
std::string t = mode_s_msg->mlat_timestamp.to_memory() + mode_s_msg->signal_level + Psc::hex2mem(mode_s_msg->msg_hex);
auto p = mode_s_msg->packet.substr(2);
if (t != p) {
std::cout << mem2hex(t, true, " ") << std::endl;
std::cout << mem2hex(mode_s_msg->packet, true, " ") << std::endl;
std::cout << VAR_STR_2(t, mode_s_msg->packet) << std::endl;
}
// TODO: 可能不需要push_to_feed
source->push_to_feed(mode_s_msg);
auto& cfg = Global::instance()->mode_acs;
SSR::parse_mode_s_bin(source.get(), mode_s_msg, source->base_station.get_pos(),cfg.max_speed_m_s, cfg.air_pos_timeout, cfg.surface_pos_timeout);
auto base = source->get_aircraft(mode_s_msg->icao);
if (base)
{
auto derived = std::dynamic_pointer_cast<Aircraft>(base);
derived->refresh_external_database_info();
}
if (Global::instance()->mlat.merge) {
auto& mh = Global::instance()->mlat_handler;
mh.push(mode_s_msg);
auto tt = mh.get_all();
if (!tt.empty()) {
pure_log("@/logs/mlat.log", "receive[" + std::to_string(tt.size()) + "]:\n");
for (Mlat_MSG& t : tt) {
std::ostringstream oss;
oss << std::fixed << std::setprecision(10);
oss << "===================================================\n";
int n = static_cast<int>(t.size());
auto icao = t.icao().value_or("null");
oss << "\tmlat_msg:" << n;
oss << "\ticao:" << icao;
oss << "\thex:" << t.msg_hex() << std::endl;
bool have_pos = false;
if (icao != "null") {
auto air = source->get_aircraft(icao);
if (air != nullptr) {
auto callsign = air->bds20_call_sign();
oss << "\tcall_sign" << callsign.value_or("null") << std::endl;
auto o_pos = air->pos();
auto o_alt = air->altitude_meter();
if (o_pos.has_value() && o_alt.has_value()) {
have_pos = true;
auto pos = o_pos.value();
source->alt = o_alt.value();
double x, y, z;
SSR::CPR::WGS84_LBH_to_XYZ(pos.lon, pos.lat, source->alt, x, y, z);
oss << "\tpos[" << pos.lon << "," << pos.lat << "," << source->alt << "]" << std::endl;
oss << "\tXYZ[" << x << "," << y << "," << z << "]" << std::endl;
}
}
}
for (int i = 0; i < t.size(); i++) {
auto& msg = t.list[i];
oss << "\t\tds:" << msg->source->get_key();
oss << "\ttime:" << msg->mlat_timestamp.to_string() << std::endl;
}
// if (have_pos) {
//std::cout << oss.str() << std::endl;
pure_log("@/logs/mlat.log", oss.str());
// }
// if (t.size() > 3 && have_pos && icao == "78139F") {
// size_t i = 1;
// auto range = hex_mlat_map.equal_range(t.msg_hex());
// // 遍历与key_to_find对应的所有元素
// for (auto it = range.first; it != range.second; ++it) {
// oss << "\t" << i++ << " " << it->second.msg << std::endl;
// }
// oss << "===================================================\n";
// std::cout << oss.str() << std::endl;
// pure_log("@/logs/icao/" + icao + "_mlat.log", oss.str(), true);
// }
}
}
}
}
void Data_Source_Handler::handle_HULC(const std::string& packet) {
std::uint8_t len = SSR::get_len(packet);
std::uint8_t id = SSR::get_id(packet);
auto msg = mem2hex(packet);
if (len != packet.size() - 4) {
SSR::mode_s_logger->debug("HULC/error_length", {},
"需要: " + std::to_string(len) + " 当前: " + std::to_string(packet.size()) + " hex: " +
mem2hex(packet));
return;
}
if (id == 1) {
// 状态消息
auto status_msg = SSR::create_HULC_Status_Message(packet);
bool gps_ok = status_msg.GPS_device_detected() && status_msg.GPS_valid() && status_msg.GPS_has_valid_fix();
if (gps_ok) {
}
auto g = Global::instance();
base_station.set_msg(status_msg);
Log_Type type({}, {{"msg", msg}});
SSR::mode_s_logger->debug("HULC/status", type, status_msg.toJson().to_json_string());
if (gps_ok) {
}
} else if (id == 24) {
SSR::mode_s_logger->debug("HULC/reply", {}, msg);
} else {
SSR::mode_s_logger->debug("HULC/unknown_id", {}, msg);
}
}