diff --git a/SSR/ADS_B/ADS_B.hpp b/SSR/ADS_B/ADS_B.hpp index c6b97a9..7fbcc3f 100644 --- a/SSR/ADS_B/ADS_B.hpp +++ b/SSR/ADS_B/ADS_B.hpp @@ -1,7 +1,6 @@ #ifndef ADS_B_HPP #define ADS_B_HPP #include -#include #include #include #include "../ACAS/ACAS_9_56.hpp" diff --git a/SSR/Aircraft_Info.cpp b/SSR/Aircraft_Info.cpp index af8a97c..d27a556 100644 --- a/SSR/Aircraft_Info.cpp +++ b/SSR/Aircraft_Info.cpp @@ -3,7 +3,7 @@ #include #include #include -#include "Core/Statistics/Frequency_Limit.h" +#include "Psc_Cpp_Core/Statistics/Frequency_Limit.h" #include "convert/SBS.h" #include "export.h" using namespace Psc; @@ -84,7 +84,6 @@ void set_logger(BaseLogger* logger) { delete mode_s_logger; mode_s_logger = logger; } - bool parse_absb_17(SSR::Data_Source_Interface* src, SSR::P_S mode_s_msg, JSON& msg_json, std::optional base_station_pos, const SSR::ADS_B_T::Constraint& air_constraint, const SSR::ADS_B_T::Constraint& surface_constraint) { diff --git a/SSR/Aircraft_Info.h b/SSR/Aircraft_Info.h index 44a5e76..a8ed261 100644 --- a/SSR/Aircraft_Info.h +++ b/SSR/Aircraft_Info.h @@ -1,23 +1,22 @@ #pragma once +#include #include -#include "Core/system/export.h" #include "ACAS/ACAS.h" #include "ADS_B/ADS_B.h" #include "Commb/Commb.h" #include "Mode_S/Mode_S.h" #include "Msg.h" +#include "Psc_Cpp_Core/system/export.h" #include "convert/DataOutputFormats.h" -#include namespace SSR { #define GET_PRE(name) \ -std::lock_guard lock(name.mtx.mtx); \ -if (!name.value.has_value()) \ -{ \ -return std::nullopt; \ -} \ -auto& w = name.value.value(); -// #define EJ2(NAME) \ -// if (NAME.value.has_value()) ret.append(Psc::Json(STRINGIFY(timestamp_##NAME), NAME.time)); \ + std::lock_guard lock(name.mtx.mtx); \ + if (!name.value.has_value()) { \ + return std::nullopt; \ + } \ + auto& w = name.value.value(); +// #define EJ2(NAME) \ +// if (NAME.value.has_value()) ret.append(Psc::Json(STRINGIFY(timestamp_##NAME), NAME.time)); \ // ret.append(NAME.value.has_value() ? Psc::Json(#NAME, NAME.value.value().toJson()) : Psc::Json(#NAME, nullptr)); template void d(Psc::JSON& ret, T& t, std::string_view name) { @@ -86,8 +85,7 @@ public: } virtual Psc::JSON toJson() { Psc::JSON ret = Psc::JSON::object(); - Ret_J(icao) - ret.append({"每秒位置数", get_pest()}); + Ret_J(icao) ret.append({"每秒位置数", get_pest()}); ret.append({"飞机位置轨迹点数", air_pos_track_list.size()}); ret.append({"地面位置轨迹点数", surface_pos_track_list.size()}); ret.append({"信号强度", signal_level}); @@ -171,8 +169,8 @@ public: } RET is_on_ground() { GET_PRE(Reply_Base_builder) - if (w.get_flight_status() == Flight_Status::alert_on_ground || w.get_flight_status() == - Flight_Status::no_alert_on_ground) { + if (w.get_flight_status() == Flight_Status::alert_on_ground || + w.get_flight_status() == Flight_Status::no_alert_on_ground) { return true; } return false; @@ -185,7 +183,8 @@ public: RET vertical_rate() { GET_PRE(BDS09_Base) auto v = w.get_vertical_rate(); - if (!v.has_value()) return std::nullopt; + if (!v.has_value()) + return std::nullopt; return v.value() * aero::fpm; } RET pos() { @@ -194,7 +193,8 @@ public: // if (it.get_lat().has_value() && it.get_lon().has_value()) { // return CPR::Position{it.get_lat().value(), it.get_lon().value()}; // } - if (surface_pos_track_list.empty()) return std::nullopt; + if (surface_pos_track_list.empty()) + return std::nullopt; return surface_pos_track_list.last(); } RET select_heading() { @@ -210,13 +210,9 @@ public: return w.get_magnetic_heading(); } RET altitude_meter() { - - - GET_PRE(BDS05_airborne_position) return w.get_alt_meter(); } - RET vortex_type() { GET_PRE(BDS08_id) return w.get_vortex_type(); @@ -291,6 +287,4 @@ public: this->timestamp = std::time(nullptr); } }; -} - - +} // namespace SSR diff --git a/SSR/CPR/CPR.h b/SSR/CPR/CPR.h index 1580807..eb81827 100644 --- a/SSR/CPR/CPR.h +++ b/SSR/CPR/CPR.h @@ -1,20 +1,21 @@ #pragma once -#include -#include "Core/Base/JSON.h" #include #include #include #include #include #include +#include #include +#include "Psc_Cpp_Core/Base/JSON.h" namespace SSR { namespace CPR { using Time = long double; using D = long double; using I = std::int64_t; struct Position { - Position(D lat, D lon) : lat(lat), lon(lon) {} + Position(D lat, D lon) : lat(lat), lon(lon) { + } D lat; D lon; [[nodiscard]] std::string to_string() const; @@ -70,9 +71,11 @@ inline std::optional> surface_global_decode(I YZ0 auto [pos0, pos1] = poses.value(); return std::tuple(pos0, pos1); } -inline std::optional> surface_global_decode_ref(I YZ0, I YZ1, I XZ0, I XZ1, D lat_s, D lon_s) { +inline std::optional> surface_global_decode_ref(I YZ0, I YZ1, I XZ0, I XZ1, D lat_s, + D lon_s) { auto poses = surface_global_decode(YZ0, YZ1, XZ0, XZ1); - if (!poses.has_value()) return std::nullopt; + if (!poses.has_value()) + return std::nullopt; auto [pos0, pos1] = poses.value(); auto p0 = Position{bb(pos0.lat, lat_s), bb(pos0.lon, lon_s)}; auto p1 = Position{bb(pos1.lat, lat_s), bb(pos1.lon, lon_s)}; @@ -88,24 +91,14 @@ inline POS surface_locale_decode(D lat_s, D lon_s, I YZi, I XZi, I i) { return Position{bb(lat, lat_s), bb(lon, lon_s)}; } // time -std::string lat_lon_airborne_34(double latitude, double longitude, - CPR::Frame cpr_format); -std::optional airborne_position(std::string_view msg0, - std::string_view msg1, Time t0, - Time t1); -std::optional airborne_position_with_ref(std::string_view msg_bin, - double lat_ref, - double lon_ref, Time t, +std::string lat_lon_airborne_34(double latitude, double longitude, CPR::Frame cpr_format); +std::optional airborne_position(std::string_view msg0, std::string_view msg1, Time t0, Time t1); +std::optional airborne_position_with_ref(std::string_view msg_bin, double lat_ref, double lon_ref, Time t, Time t_ref); -std::string lat_lon_surface_34(double latitude, double longitude, - CPR::Frame cpr_format); -std::optional surface_position(std::string_view msg0, - std::string_view msg1, Time t0, - Time t1, +std::string lat_lon_surface_34(double latitude, double longitude, CPR::Frame cpr_format); +std::optional surface_position(std::string_view msg0, std::string_view msg1, Time t0, Time t1, const CPR::Position& base_station_pos); -std::optional surface_position_with_ref(std::string_view msg_bin, - double lat_ref, - double lon_ref, Time t, +std::optional surface_position_with_ref(std::string_view msg_bin, double lat_ref, double lon_ref, Time t, Time t_ref); // YZ, NZ, i std::tuple get(std::string_view msg_bin); @@ -125,10 +118,8 @@ std::tuple light_time_second_nano(const Position& p1, const Position& p2); // (Longitude):表示经度,用来指示一个点在地球表面相对于本初子午线的角度。它的范围是从 // -180° 到 +180°。 H // (Height):表示高度,通常指的是该点相对于海平面的高度,单位通常是米(m)。 -void WGS84_LBH_to_XYZ(double longitude, double latitude, double height, - double& X, double& Y, double& Z); -void XYZ_to_WGS84_LBH(double X, double Y, double Z, double& longitude, - double& latitude, double& altitude); +void WGS84_LBH_to_XYZ(double longitude, double latitude, double height, double& X, double& Y, double& Z); +void XYZ_to_WGS84_LBH(double X, double Y, double Z, double& longitude, double& latitude, double& altitude); } // namespace CPR } // namespace SSR #include diff --git a/SSR/Mode_S/Mode_S.hpp b/SSR/Mode_S/Mode_S.hpp index 8f1bd56..44abc3d 100644 --- a/SSR/Mode_S/Mode_S.hpp +++ b/SSR/Mode_S/Mode_S.hpp @@ -1,112 +1,100 @@ #pragma once #include #include "../HPP.h" -#include "Core/Base/global_include.h" +#include "Psc_Cpp_Core/Base/global_include.h" namespace SSR { void check_icao(std::string_view icao); namespace T { template struct Reply_Base_Builder { - PROP_T(std::string, icao, std::string {} - ); - PROP_T(Downlink_Format, df, Downlink_Format::Unknown) - PROP_T(Transponder_Capability, transponder_capability, - Transponder_Capability::Level_2_plus_airborne) - PROP_T(Flight_Status, flight_status, Flight_Status::not_assigned) - PROP_T(Downlink_Request, downlink_request, Downlink_Request::no_request) - PROP_T(IDS, ids, IDS::no_information) - PROP_Bit_T ( - - 4 - , - IIS - , - 0 - ) // 询问器标识符代码 - void parse(std::string& msg_bin) { - icao = decode_icao(msg_bin); - df = decode_df(msg_bin); - transponder_capability = decode_transponder_capability(msg_bin); - get_bin < 5, 3, Flight_Status > (msg_bin, flight_status); - get_bin < 8, 5, Downlink_Request > (msg_bin, downlink_request); - get_bin < 13, 4 > (msg_bin, IIS); - get_bin < 17, 2, IDS > (msg_bin, ids); - } - Psc::JSON toJson() { - Psc::JSON ret = Psc::JSON::object(); - Ret_J(icao); - Ret_J(transponder_capability); - Ret_J(flight_status); - Ret_J(ids); - Ret_J(IIS); - return ret; - } + PROP_T(std::string, icao, std::string{}); + PROP_T(Downlink_Format, df, Downlink_Format::Unknown) + PROP_T(Transponder_Capability, transponder_capability, Transponder_Capability::Level_2_plus_airborne) + PROP_T(Flight_Status, flight_status, Flight_Status::not_assigned) + PROP_T(Downlink_Request, downlink_request, Downlink_Request::no_request) + PROP_T(IDS, ids, IDS::no_information) + PROP_Bit_T(4, IIS, + 0) // 询问器标识符代码 + void parse(std::string& msg_bin) { + icao = decode_icao(msg_bin); + df = decode_df(msg_bin); + transponder_capability = decode_transponder_capability(msg_bin); + get_bin<5, 3, Flight_Status>(msg_bin, flight_status); + get_bin<8, 5, Downlink_Request>(msg_bin, downlink_request); + get_bin<13, 4>(msg_bin, IIS); + get_bin<17, 2, IDS>(msg_bin, ids); + } + Psc::JSON toJson() { + Psc::JSON ret = Psc::JSON::object(); + Ret_J(icao); + Ret_J(transponder_capability); + Ret_J(flight_status); + Ret_J(ids); + Ret_J(IIS); + return ret; + } protected: - // void set_crc(std::string& msg_bin, std::string& icao) { - // auto crc = std::bitset<24>(::crc(msg_bin, true)).to_string(); - // auto crcHex = bin2hex(crc); - // std::string last24 = xorHex(crcHex, icao); - // msg_bin.replace(msg_bin.size() - 24, 24, xorBin(crc, hex2bin(icao))); - // } - void set(std::string& msg_bin) { - check_icao(icao); - PSC_ASSERT(msg_bin.size() == 56 || msg_bin.size() == 112, - " Reply_Base_Builder error size == " + - std::to_string(msg_bin.size())); - SSR::set_transponder_capability(msg_bin, transponder_capability); - set_bin < 5, 3 > (msg_bin, static_cast(flight_status)); - set_bin < 8, 5 > (msg_bin, static_cast(downlink_request)); - set_bin < 13, 4 > (msg_bin, IIS); - set_bin < 17, 2 > (msg_bin, static_cast(ids)); - } + // void set_crc(std::string& msg_bin, std::string& icao) { + // auto crc = std::bitset<24>(::crc(msg_bin, true)).to_string(); + // auto crcHex = bin2hex(crc); + // std::string last24 = xorHex(crcHex, icao); + // msg_bin.replace(msg_bin.size() - 24, 24, xorBin(crc, hex2bin(icao))); + // } + void set(std::string& msg_bin) { + check_icao(icao); + PSC_ASSERT(msg_bin.size() == 56 || msg_bin.size() == 112, + " Reply_Base_Builder error size == " + std::to_string(msg_bin.size())); + SSR::set_transponder_capability(msg_bin, transponder_capability); + set_bin<5, 3>(msg_bin, static_cast(flight_status)); + set_bin<8, 5>(msg_bin, static_cast(downlink_request)); + set_bin<13, 4>(msg_bin, IIS); + set_bin<17, 2>(msg_bin, static_cast(ids)); + } }; -T_Parser(Reply_Base_Builder) -template +T_Parser(Reply_Base_Builder) template struct Alt { - PROP_T(int, altitude, 0) - void parse(std::string& msg_bin) { - altitude = altcode(msg_bin); - } - Psc::JSON toJson() { - Psc::JSON ret = Psc::JSON::object(); - Ret_J(altitude); - return ret; - } + PROP_T(int, altitude, 0) + void parse(std::string& msg_bin) { + altitude = altcode(msg_bin); + } + Psc::JSON toJson() { + Psc::JSON ret = Psc::JSON::object(); + Ret_J(altitude); + return ret; + } protected: - void set(std::string& msg_bin) { - set_bin < 19, 13 > (msg_bin, encode_altitude13_feet(altitude)); - } + void set(std::string& msg_bin) { + set_bin<19, 13>(msg_bin, encode_altitude13_feet(altitude)); + } }; -T_Parser(Alt) -template +T_Parser(Alt) template struct Id { - // ATC Mode A 所使用的代码 - PROP_T(std::string, ATC_Squawk, "0000") - void parse(std::string& msg_bin) { - ATC_Squawk = idcode(msg_bin); - } - Psc::JSON toJson() { - Psc::JSON ret = Psc::JSON::object(); - Ret_J(ATC_Squawk); - return ret; - } + // ATC Mode A 所使用的代码 + PROP_T(std::string, ATC_Squawk, "0000") + void parse(std::string& msg_bin) { + ATC_Squawk = idcode(msg_bin); + } + Psc::JSON toJson() { + Psc::JSON ret = Psc::JSON::object(); + Ret_J(ATC_Squawk); + return ret; + } protected: - void set(std::string& msg_bin) { - set_bin < 19, 13 > (msg_bin, encode_squawk13(ATC_Squawk)); - } + void set(std::string& msg_bin) { + set_bin<19, 13>(msg_bin, encode_squawk13(ATC_Squawk)); + } }; -T_Parser(Id) -template +T_Parser(Id) template struct Surveillance_Altitude_Reply : Alt, BDS_ { - void set(std::string& msg_bin) { - set_df(msg_bin, Downlink_Format::Surveillance_Altitude_Reply_4); - } + void set(std::string& msg_bin) { + set_df(msg_bin, Downlink_Format::Surveillance_Altitude_Reply_4); + } }; template struct Surveillance_Identity_Reply : Id, BDS_ { - void set(std::string& msg_bin) { - set_df(msg_bin, Downlink_Format::Surveillance_Identity_Reply_5); - } + void set(std::string& msg_bin) { + set_df(msg_bin, Downlink_Format::Surveillance_Identity_Reply_5); + } }; } // namespace T } // namespace SSR diff --git a/SSR/Msg.h b/SSR/Msg.h index 3d9fa91..090993b 100644 --- a/SSR/Msg.h +++ b/SSR/Msg.h @@ -1,12 +1,12 @@ #pragma once -#include -#include "CPR/CPR.h" -#include "Core/Base/global_include.h" -#include "convert/DataOutputFormats.h" -#include "enum.h" #include +#include #include #include +#include "CPR/CPR.h" +#include "Psc_Cpp_Core/Base/global_include.h" +#include "convert/DataOutputFormats.h" +#include "enum.h" #define STRINGIFY(x) #x // 硬件接收来的 二进制消息族 namespace SSR { @@ -55,10 +55,8 @@ struct Play_Back_Time_Point { std::uint32_t second{}; [[nodiscard]] std::string to_string() const { std::ostringstream oss; - oss << std::setfill('0') - << std::setw(2) << hour << ':' - << std::setw(2) << minute << ':' - << std::setw(2) << second; + oss << std::setfill('0') << std::setw(2) << hour << ':' << std::setw(2) << minute << ':' << std::setw(2) + << second; return oss.str(); } }; @@ -71,8 +69,8 @@ struct Play_Back_Time_Point { } [[nodiscard]] std::string to_string() const { std::ostringstream oss; - oss << "Play_Back_Time_Point[" << day_num << ',' << hms().to_string() - << '.' << std::setfill('0') << std::setw(9) << nanosec << ']'; + oss << "Play_Back_Time_Point[" << day_num << ',' << hms().to_string() << '.' << std::setfill('0') + << std::setw(9) << nanosec << ']'; return oss.str(); } void normalize() noexcept { @@ -98,9 +96,7 @@ struct Play_Back_Time_Point { return nanosec < other.nanosec; } bool operator==(const Play_Back_Time_Point& other) const noexcept { - return day_num == other.day_num && - day_sec == other.day_sec && - nanosec == other.nanosec; + return day_num == other.day_num && day_sec == other.day_sec && nanosec == other.nanosec; } bool operator>(const Play_Back_Time_Point& other) const noexcept { return other < *this; @@ -112,8 +108,7 @@ struct Play_Back_Time_Point { return !(*this < other); } [[nodiscard]] double abs_sec() const noexcept { - return static_cast(day_num) * static_cast(SECS_PER_DAY) + - static_cast(day_sec) + + return static_cast(day_num) * static_cast(SECS_PER_DAY) + static_cast(day_sec) + static_cast(nanosec) / static_cast(NANOSECS_PER_SEC); } void add_sec(std::uint64_t sec) noexcept { @@ -144,15 +139,11 @@ public: std::string msg_hex; std::string msg_bin; char signal_level{}; - explicit Mode_Msg(const std::shared_ptr& source, - std::string_view packet); + explicit Mode_Msg(const std::shared_ptr& source, std::string_view packet); Psc::JSON to_Json() override { Psc::JSON ret = Msg::to_Json(); - Ret_J(msg_hex) - Ret_J(signal_level) - ret.append({"mlat_timestamp", mlat_timestamp.to_string()}); - Ret_J(day_num) - return ret; + Ret_J(msg_hex) Ret_J(signal_level) ret.append({"mlat_timestamp", mlat_timestamp.to_string()}); + Ret_J(day_num) return ret; } ~Mode_Msg() override; Play_Back_Time_Point time() { @@ -165,8 +156,7 @@ public: }; class Mode_AC_Msg : public Mode_Msg { public: - explicit Mode_AC_Msg(const std::shared_ptr& source, - std::string_view packet); + explicit Mode_AC_Msg(const std::shared_ptr& source, std::string_view packet); ~Mode_AC_Msg() override; }; // 1 + 1 + 6 + 1 + 2/7/14 @@ -183,8 +173,7 @@ public: return ret; } // 1a 31 19 b2dd1c7af671 3220 - explicit Mode_S_Msg(const std::shared_ptr& source, - std::string_view packet); + explicit Mode_S_Msg(const std::shared_ptr& source, std::string_view packet); ~Mode_S_Msg() override; std::string to_string() override { auto& time = mlat_timestamp; @@ -202,7 +191,8 @@ public: }; struct Position_3D : CPR::Position { CPR::D alt; - Position_3D(CPR::D lat, CPR::D lon, CPR::D alt) : CPR::Position(lat, lon), alt(alt) {} + Position_3D(CPR::D lat, CPR::D lon, CPR::D alt) : CPR::Position(lat, lon), alt(alt) { + } }; // 这个返回值的意义在于 解码失败后 返回值能反应出是 位置解码失败 // 还是奇偶报文解码位置失败 轨迹点上会显示的信息 @@ -210,27 +200,24 @@ class Pos_Ret { public: CPR::Position pos; Psc::JSON info; - Pos_Ret(CPR::Position p, Psc::JSON info) : pos(p), info(std::move(info)) {} + Pos_Ret(CPR::Position p, Psc::JSON info) : pos(p), info(std::move(info)) { + } }; // 展示出最详细的信息 struct Position_Info : Position_3D { std::int64_t sys_day_ns{}; std::uint64_t utc{}; std::uint64_t odd_even_diff_ns{}; - Position_Info() : Position_3D(0.0, 0.0, 0.0) {} + Position_Info() : Position_3D(0.0, 0.0, 0.0) { + } Psc::JSON info; Position_Info(const Pos_Ret& r, CPR::D alt) : Position_3D(r.pos.lat, r.pos.lon, alt), info(r.info) { using namespace std::chrono; - utc = static_cast( - duration_cast(system_clock::now().time_since_epoch()).count()); + utc = static_cast(duration_cast(system_clock::now().time_since_epoch()).count()); } Psc::JSON to_json() { Psc::JSON ret = Psc::JSON::object(); - Ret_J(lat) - Ret_J(lon) - Ret_J(alt) - Ret_J(utc) - ret.append_list(info.children); + Ret_J(lat) Ret_J(lon) Ret_J(alt) Ret_J(utc) ret.append_list(info.children); return ret; } }; @@ -262,7 +249,8 @@ struct POS_List { } std::optional last() { std::lock_guard g(mtx.mtx); - if (count == 0) return std::nullopt; + if (count == 0) + return std::nullopt; std::size_t idx = (head + max_size - 1) % max_size; return buf[idx]; } @@ -271,7 +259,8 @@ struct POS_List { std::lock_guard g(mtx.mtx); buf[head] = std::move(new_position); head = (head + 1) % max_size; - if (count < max_size) ++count; + if (count < max_size) + ++count; ++seq; } Psc::JSON get_last_array_json(std::uint64_t last_seq); diff --git a/SSR/convert/DataOutputFormats.cpp b/SSR/convert/DataOutputFormats.cpp index bcca45b..2016174 100644 --- a/SSR/convert/DataOutputFormats.cpp +++ b/SSR/convert/DataOutputFormats.cpp @@ -1,5 +1,5 @@ #include "DataOutputFormats.h" -#include "Core/Base/global_include.h" +#include "Psc_Cpp_Core/Base/global_include.h" #include #include #include diff --git a/SSR/convert/base_format.h b/SSR/convert/base_format.h index 722bc86..de9bf1c 100644 --- a/SSR/convert/base_format.h +++ b/SSR/convert/base_format.h @@ -1,47 +1,43 @@ #pragma once -#include -#include "Core/Base/JSON.h" -#include "SSR/global.h" #include +#include +#include "Psc_Cpp_Core/Base/JSON.h" +#include "SSR/global.h" namespace SSR { // 1纳秒是 10 -9次方秒 struct MLAT_timestamp { - explicit MLAT_timestamp(); - explicit MLAT_timestamp(std::string_view memory_6); - MLAT_timestamp(std::uint32_t daysec, std::uint32_t nanosec); - std::uint32_t daysec{}; // 当天的秒数 高18位 - std::uint32_t nanosec{}; // 当天的纳秒数 低30位 - std::string to_bin_string() const; - std::string to_memory() const; - unsigned long hh{}; - unsigned long mm{}; - unsigned long ss{}; - std::string memory{}; - bool operator<(const MLAT_timestamp& other) const { - // 比较 daysec(高18位) - if (daysec != other.daysec) { - return daysec < other.daysec; - } - // 如果 daysec 相等,比较 nanosec(低30位) - return nanosec < other.nanosec; - } - [[nodiscard]] Psc::JSON toJson() const { - Psc::JSON ret = Psc::JSON::object(); - ret.append({"秒", daysec}); - ret.append({"纳秒", nanosec}); - ret.append({ - "时间", std::to_string(hh) + ":" + std::to_string(mm) + ":" + - std::to_string(ss) - }); - return ret; - } - [[nodiscard]] std::string to_string() const { - return "{" + std::to_string(daysec) + "," + std::to_string(nanosec) + "}_" + - "[" + std::to_string(hh) + "时:" + std::to_string(mm) + - "分:" + std::to_string(ss) + - "秒" - "]"; - } - void parse_hhmmss(); + explicit MLAT_timestamp(); + explicit MLAT_timestamp(std::string_view memory_6); + MLAT_timestamp(std::uint32_t daysec, std::uint32_t nanosec); + std::uint32_t daysec{}; // 当天的秒数 高18位 + std::uint32_t nanosec{}; // 当天的纳秒数 低30位 + std::string to_bin_string() const; + std::string to_memory() const; + unsigned long hh{}; + unsigned long mm{}; + unsigned long ss{}; + std::string memory{}; + bool operator<(const MLAT_timestamp& other) const { + // 比较 daysec(高18位) + if (daysec != other.daysec) { + return daysec < other.daysec; + } + // 如果 daysec 相等,比较 nanosec(低30位) + return nanosec < other.nanosec; + } + [[nodiscard]] Psc::JSON toJson() const { + Psc::JSON ret = Psc::JSON::object(); + ret.append({"秒", daysec}); + ret.append({"纳秒", nanosec}); + ret.append({"时间", std::to_string(hh) + ":" + std::to_string(mm) + ":" + std::to_string(ss)}); + return ret; + } + [[nodiscard]] std::string to_string() const { + return "{" + std::to_string(daysec) + "," + std::to_string(nanosec) + "}_" + "[" + std::to_string(hh) + + "时:" + std::to_string(mm) + "分:" + std::to_string(ss) + + "秒" + "]"; + } + void parse_hhmmss(); }; } \ No newline at end of file diff --git a/SSR/export.h b/SSR/export.h index 28ee13a..d9d1b65 100644 --- a/SSR/export.h +++ b/SSR/export.h @@ -9,7 +9,7 @@ #include "py_Mode_S/Common.h" #include "export_type.h" #include -#include "Core/Statistics/Statistics.h" +#include "Psc_Cpp_Core/Statistics/Statistics.h" namespace SSR { void set_logger(BaseLogger* logger); using Parse_Call_Back = std::function #include #include #include @@ -14,290 +13,283 @@ #include #include #include +#include #include #include #include -#include "Core/Base/global_include.h" -#include "Core/spdlog/export.h" +#include "Psc_Cpp_Core/Base/global_include.h" +#include "Psc_Cpp_Core/spdlog/export.h" namespace SSR { -extern BaseLogger *mode_s_logger; +extern BaseLogger* mode_s_logger; std::string crc_hex(std::string_view msg_bin, bool encode); int crc(std::string_view msg_bin, bool encode = false); std::string decode_icao(std::string_view msg_bin); template void handle_range_error(std::string_view log_pos, std::string_view field_name, T value, double min, double max) { - std::string range = - "[" + std::to_string(min) + "," + std::to_string(max) + "]"; - std::string error_info = "ERROR:" + std::string(field_name) + ":" + std::to_string(value) + - "超出范围:" + range + "\n"; - Log_Type type({}, {{"POS", std::string(log_pos)}}); - mode_s_logger->error("out of range", type, error_info); - // #ifdef WIN32 - // Psc::fail_fast("一个只是在windows上崩溃的本质是穿的错误数据 - // 或解析的错误数据"); - // #endif - // throw std::runtime_error(error_info); + std::string range = "[" + std::to_string(min) + "," + std::to_string(max) + "]"; + std::string error_info = + "ERROR:" + std::string(field_name) + ":" + std::to_string(value) + "超出范围:" + range + "\n"; + Log_Type type({}, {{"POS", std::string(log_pos)}}); + mode_s_logger->error("out of range", type, error_info); + // #ifdef WIN32 + // Psc::fail_fast("一个只是在windows上崩溃的本质是穿的错误数据 + // 或解析的错误数据"); + // #endif + // throw std::runtime_error(error_info); } template -void handle_range_error(std::string_view log_pos, - std::string_view field_name, std::optional value, - double min, double max) { - handle_range_error(log_pos, field_name, value.value(), min, max); +void handle_range_error(std::string_view log_pos, std::string_view field_name, std::optional value, double min, + double max) { + handle_range_error(log_pos, field_name, value.value(), min, max); } -#define PROP(TYPE, FIELD, DEFAULT) \ -private: \ - TYPE FIELD = DEFAULT; \ - \ -public: \ - Builder &set_##FIELD(TYPE value) { \ - this->FIELD = std::move(value); \ - return *this; \ - } \ - TYPE get_##FIELD() { return this->FIELD; } -#define PROP_Bit(bits, FIELD, DEFAULT) \ -private: \ - int FIELD = DEFAULT; \ - \ -public: \ - Builder &set_##FIELD(int value) { \ - int MIN = 0; \ - int MAX = (1 << bits); \ - if (value < MIN || value >= MAX) { \ - handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ - } \ - this->FIELD = value; \ - return *this; \ - } \ - int get_##FIELD() { \ - int &value = this->FIELD; \ - int MIN = 0; \ - int MAX = (1 << bits); \ - if (value < MIN || value >= MAX) { \ - handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ - } \ - return value; \ - } -#define PROP_T_FUN(TYPE, FIELD, DEFAULT) \ -public: \ - That &set_##FIELD(TYPE value) { \ - static_cast(this)->FIELD = std::move(value); \ - return *static_cast(this); \ - } \ - TYPE get_##FIELD() { \ - TYPE &value = static_cast(this)->FIELD; \ - return value; \ - } -#define PROP_T(TYPE, FIELD, DEFAULT) \ -protected: \ - TYPE FIELD = DEFAULT; \ - \ -public: \ - That &set_##FIELD(TYPE value) { \ - static_cast(this)->FIELD = std::move(value); \ - return *static_cast(this); \ - } \ - TYPE get_##FIELD() { \ - TYPE &value = static_cast(this)->FIELD; \ - return value; \ - } -#define PROP_Range(TYPE, MIN, MAX, FIELD, DEFAULT) \ -private: \ - TYPE FIELD = DEFAULT; \ - \ -public: \ - Builder &set_##FIELD(const TYPE &value) { \ - if (value < MIN || value > MAX) { \ - handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ - } \ - this->FIELD = value; \ - return *this; \ - } \ - TYPE get_##FIELD() { \ - TYPE &value = this->FIELD; \ - if (value < MIN || value > MAX) { \ - handle_range_error(LOG_POS #FIELD, value, MIN, MAX); \ - } \ - return value; \ - } +#define PROP(TYPE, FIELD, DEFAULT) \ +private: \ + TYPE FIELD = DEFAULT; \ +public: \ + Builder& set_##FIELD(TYPE value) { \ + this->FIELD = std::move(value); \ + return *this; \ + } \ + TYPE get_##FIELD() { \ + return this->FIELD; \ + } +#define PROP_Bit(bits, FIELD, DEFAULT) \ +private: \ + int FIELD = DEFAULT; \ +public: \ + Builder& set_##FIELD(int value) { \ + int MIN = 0; \ + int MAX = (1 << bits); \ + if (value < MIN || value >= MAX) { \ + handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ + } \ + this->FIELD = value; \ + return *this; \ + } \ + int get_##FIELD() { \ + int& value = this->FIELD; \ + int MIN = 0; \ + int MAX = (1 << bits); \ + if (value < MIN || value >= MAX) { \ + handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ + } \ + return value; \ + } +#define PROP_T_FUN(TYPE, FIELD, DEFAULT) \ +public: \ + That& set_##FIELD(TYPE value) { \ + static_cast(this)->FIELD = std::move(value); \ + return *static_cast(this); \ + } \ + TYPE get_##FIELD() { \ + TYPE& value = static_cast(this)->FIELD; \ + return value; \ + } +#define PROP_T(TYPE, FIELD, DEFAULT) \ +protected: \ + TYPE FIELD = DEFAULT; \ +public: \ + That& set_##FIELD(TYPE value) { \ + static_cast(this)->FIELD = std::move(value); \ + return *static_cast(this); \ + } \ + TYPE get_##FIELD() { \ + TYPE& value = static_cast(this)->FIELD; \ + return value; \ + } +#define PROP_Range(TYPE, MIN, MAX, FIELD, DEFAULT) \ +private: \ + TYPE FIELD = DEFAULT; \ +public: \ + Builder& set_##FIELD(const TYPE& value) { \ + if (value < MIN || value > MAX) { \ + handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ + } \ + this->FIELD = value; \ + return *this; \ + } \ + TYPE get_##FIELD() { \ + TYPE& value = this->FIELD; \ + if (value < MIN || value > MAX) { \ + handle_range_error(LOG_POS #FIELD, value, MIN, MAX); \ + } \ + return value; \ + } // [0, 2^n-1] 区间 -#define PROP_Bit_T_Base(Type, bits, FIELD, DEFAULT) \ -protected: \ - Type FIELD = DEFAULT; \ - \ -public: \ - That &set_##FIELD(Type value) { \ - int MIN = 0; \ - int MAX = (1 << bits); \ - if (value < MIN || value >= MAX) { \ - handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ - } \ - static_cast(this)->FIELD = value; \ - return *static_cast(this); \ - } \ - Type get_##FIELD() { \ - Type &value = static_cast(this)->FIELD; \ - int MIN = 0; \ - int MAX = (1 << bits); \ - if (value < MIN || value >= MAX) { \ - handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ - } \ - return value; \ - } -#define PROP_Bit_T(bits, FIELD, DEFAULT) \ - PROP_Bit_T_Base(unsigned char, bits, FIELD, DEFAULT) -#define PROP_Bit_32T(bits, FIELD, DEFAULT) \ - PROP_Bit_T_Base(unsigned int, bits, FIELD, DEFAULT) -#define PROP_Range_T(TYPE, MIN, MAX, FIELD, DEFAULT) \ -private: \ - TYPE FIELD = DEFAULT; \ - \ -public: \ - That &set_##FIELD(const TYPE &value) { \ - if (value < MIN - std::numeric_limits::epsilon() || \ - value > MAX + std::numeric_limits::epsilon()) { \ - handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ - } \ - static_cast(this)->FIELD = value; \ - return *static_cast(this); \ - } \ - TYPE get_##FIELD() { \ - TYPE &value = static_cast(this)->FIELD; \ - if (value < MIN - std::numeric_limits::epsilon() || \ - value > MAX + std::numeric_limits::epsilon()) { \ - handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ - } \ - return value; \ - } -#define BaseADD1(NAME, MSGBase, _T1) \ - struct NAME : MSGBase { \ - struct Builder; \ - using T1 = _T1; \ - struct Builder : T1 { \ - NAME build() { \ - NAME ret; \ - T1::set(ret.msg); \ - this->set_crc(ret.msg, this->icao, this->bds()); \ - return ret; \ - } \ - void parse(std::string &msg) { T1::parse(msg); } \ - Psc::JSON toJson() { \ - Psc::JSON ret = Psc::JSON::object(); \ - ret.append_list(T1::toJson().children); \ - return ret; \ - } \ - }; \ - }; -#define BaseADD2(NAME, MSGBase, _T1, _T2) \ - struct NAME : MSGBase { \ - struct Builder; \ - using T1 = _T1; \ - using T2 = _T2; \ - struct Builder : T1, T2 { \ - NAME build() { \ - NAME ret; \ - T1::set(ret.msg); \ - T2::set(ret.msg); \ - this->set_crc(ret.msg, this->icao, this->bds()); \ - return ret; \ - } \ - void parse(std::string &msg) { \ - T1::parse(msg); \ - T2::parse(msg); \ - } \ - Psc::JSON toJson() { \ - Psc::JSON ret = Psc::JSON::object(); \ - ret.append_list(T1::toJson().children); \ - ret.append_list(T2::toJson().children); \ - return ret; \ - } \ - }; \ - }; -#define BaseADD3(NAME, MSGBase, _T1, _T2, _T3) \ - struct NAME : MSGBase { \ - struct Builder; \ - using T1 = _T1; \ - using T2 = _T2; \ - using T3 = _T3; \ - struct Builder : T1, T2, T3 { \ - NAME build() { \ - NAME ret; \ - T1::set(ret.msg); \ - T2::set(ret.msg); \ - T3::set(ret.msg); \ - this->set_crc(ret.msg, this->icao, this->bds()); \ - return ret; \ - } \ - void parse(std::string &msg) { \ - T1::parse(msg); \ - T2::parse(msg); \ - T3::parse(msg); \ - } \ - Psc::JSON toJson() { \ - Psc::JSON ret = Psc::JSON::object(); \ - ret.append_list(T1::toJson().children); \ - ret.append_list(T2::toJson().children); \ - ret.append_list(T3::toJson().children); \ - return ret; \ - } \ - }; \ - }; -#define BaseADD4(NAME, MSGBase, _T1, _T2, _T3, _T4) \ - struct NAME : MSGBase { \ - struct Builder; \ - using T1 = _T1; \ - using T2 = _T2; \ - using T3 = _T3; \ - using T4 = _T4; \ - struct Builder : T1, T2, T3, T4 { \ - NAME build() { \ - NAME ret; \ - T1::set(ret.msg); \ - T2::set(ret.msg); \ - T3::set(ret.msg); \ - T4::set(ret.msg); \ - this->set_crc(ret.msg, this->icao, this->bds()); \ - return ret; \ - } \ - void parse(std::string &msg) { \ - T1::parse(msg); \ - T2::parse(msg); \ - T3::parse(msg); \ - T4::parse(msg); \ - } \ - Psc::JSON toJson() { \ - Psc::JSON ret = Psc::JSON::object(); \ - ret.append_list(T1::toJson().children); \ - ret.append_list(T2::toJson().children); \ - ret.append_list(T3::toJson().children); \ - ret.append_list(T4::toJson().children); \ - return ret; \ - } \ - }; \ - }; +#define PROP_Bit_T_Base(Type, bits, FIELD, DEFAULT) \ +protected: \ + Type FIELD = DEFAULT; \ +public: \ + That& set_##FIELD(Type value) { \ + int MIN = 0; \ + int MAX = (1 << bits); \ + if (value < MIN || value >= MAX) { \ + handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ + } \ + static_cast(this)->FIELD = value; \ + return *static_cast(this); \ + } \ + Type get_##FIELD() { \ + Type& value = static_cast(this)->FIELD; \ + int MIN = 0; \ + int MAX = (1 << bits); \ + if (value < MIN || value >= MAX) { \ + handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ + } \ + return value; \ + } +#define PROP_Bit_T(bits, FIELD, DEFAULT) PROP_Bit_T_Base(unsigned char, bits, FIELD, DEFAULT) +#define PROP_Bit_32T(bits, FIELD, DEFAULT) PROP_Bit_T_Base(unsigned int, bits, FIELD, DEFAULT) +#define PROP_Range_T(TYPE, MIN, MAX, FIELD, DEFAULT) \ +private: \ + TYPE FIELD = DEFAULT; \ +public: \ + That& set_##FIELD(const TYPE& value) { \ + if (value < MIN - std::numeric_limits::epsilon() || \ + value > MAX + std::numeric_limits::epsilon()) { \ + handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ + } \ + static_cast(this)->FIELD = value; \ + return *static_cast(this); \ + } \ + TYPE get_##FIELD() { \ + TYPE& value = static_cast(this)->FIELD; \ + if (value < MIN - std::numeric_limits::epsilon() || \ + value > MAX + std::numeric_limits::epsilon()) { \ + handle_range_error(LOG_POS, #FIELD, value, MIN, MAX); \ + } \ + return value; \ + } +#define BaseADD1(NAME, MSGBase, _T1) \ + struct NAME : MSGBase { \ + struct Builder; \ + using T1 = _T1; \ + struct Builder : T1 { \ + NAME build() { \ + NAME ret; \ + T1::set(ret.msg); \ + this->set_crc(ret.msg, this->icao, this->bds()); \ + return ret; \ + } \ + void parse(std::string& msg) { \ + T1::parse(msg); \ + } \ + Psc::JSON toJson() { \ + Psc::JSON ret = Psc::JSON::object(); \ + ret.append_list(T1::toJson().children); \ + return ret; \ + } \ + }; \ + }; +#define BaseADD2(NAME, MSGBase, _T1, _T2) \ + struct NAME : MSGBase { \ + struct Builder; \ + using T1 = _T1; \ + using T2 = _T2; \ + struct Builder : T1, T2 { \ + NAME build() { \ + NAME ret; \ + T1::set(ret.msg); \ + T2::set(ret.msg); \ + this->set_crc(ret.msg, this->icao, this->bds()); \ + return ret; \ + } \ + void parse(std::string& msg) { \ + T1::parse(msg); \ + T2::parse(msg); \ + } \ + Psc::JSON toJson() { \ + Psc::JSON ret = Psc::JSON::object(); \ + ret.append_list(T1::toJson().children); \ + ret.append_list(T2::toJson().children); \ + return ret; \ + } \ + }; \ + }; +#define BaseADD3(NAME, MSGBase, _T1, _T2, _T3) \ + struct NAME : MSGBase { \ + struct Builder; \ + using T1 = _T1; \ + using T2 = _T2; \ + using T3 = _T3; \ + struct Builder : T1, T2, T3 { \ + NAME build() { \ + NAME ret; \ + T1::set(ret.msg); \ + T2::set(ret.msg); \ + T3::set(ret.msg); \ + this->set_crc(ret.msg, this->icao, this->bds()); \ + return ret; \ + } \ + void parse(std::string& msg) { \ + T1::parse(msg); \ + T2::parse(msg); \ + T3::parse(msg); \ + } \ + Psc::JSON toJson() { \ + Psc::JSON ret = Psc::JSON::object(); \ + ret.append_list(T1::toJson().children); \ + ret.append_list(T2::toJson().children); \ + ret.append_list(T3::toJson().children); \ + return ret; \ + } \ + }; \ + }; +#define BaseADD4(NAME, MSGBase, _T1, _T2, _T3, _T4) \ + struct NAME : MSGBase { \ + struct Builder; \ + using T1 = _T1; \ + using T2 = _T2; \ + using T3 = _T3; \ + using T4 = _T4; \ + struct Builder : T1, T2, T3, T4 { \ + NAME build() { \ + NAME ret; \ + T1::set(ret.msg); \ + T2::set(ret.msg); \ + T3::set(ret.msg); \ + T4::set(ret.msg); \ + this->set_crc(ret.msg, this->icao, this->bds()); \ + return ret; \ + } \ + void parse(std::string& msg) { \ + T1::parse(msg); \ + T2::parse(msg); \ + T3::parse(msg); \ + T4::parse(msg); \ + } \ + Psc::JSON toJson() { \ + Psc::JSON ret = Psc::JSON::object(); \ + ret.append_list(T1::toJson().children); \ + ret.append_list(T2::toJson().children); \ + ret.append_list(T3::toJson().children); \ + ret.append_list(T4::toJson().children); \ + return ret; \ + } \ + }; \ + }; struct Base_56 { - std::string msg; - Base_56() { - msg.resize(56, '0'); - } + std::string msg; + Base_56() { + msg.resize(56, '0'); + } }; struct Base_112 { - std::string msg; - Base_112() { - msg.resize(112, '0'); - } + std::string msg; + Base_112() { + msg.resize(112, '0'); + } }; #define ADD_112_1(NAME, _T1) BaseADD1(NAME, Base_112, _T1) #define ADD_112_2(NAME, _T1, _T2) BaseADD2(NAME, Base_112, _T1, _T2) #define ADD_112_3(NAME, _T1, _T2, _T3) BaseADD3(NAME, Base_112, _T1, _T2, _T3) -#define ADD_112_4(NAME, _T1, _T2, _T3, _T4) \ - BaseADD4(NAME, Base_112, _T1, _T2, _T3, _T4) +#define ADD_112_4(NAME, _T1, _T2, _T3, _T4) BaseADD4(NAME, Base_112, _T1, _T2, _T3, _T4) #define ADD_56_1(NAME, _T1) BaseADD1(NAME, Base_56, _T1) #define ADD_56_2(NAME, _T1, _T2) BaseADD2(NAME, Base_56, _T1, _T2) #define ADD_56_3(NAME, _T1, _T2, _T3) BaseADD3(NAME, Base_56, _T1, _T2, _T3) -#define ADD_56_4(NAME, _T1, _T2, _T3, _T4) \ - BaseADD4(NAME, Base_56, _T1, _T2, _T3, _T4) -#define T_Parser(Template_name) \ - struct Parser_##Template_name : Template_name {}; +#define ADD_56_4(NAME, _T1, _T2, _T3, _T4) BaseADD4(NAME, Base_56, _T1, _T2, _T3, _T4) +#define T_Parser(Template_name) \ + struct Parser_##Template_name : Template_name {}; // 模式 S 使用三种类型的奇偶校验。 // 第一个只是 CRC 提醒,用于扩展 squitter 中的 ADS-B(参见第 // [章:adsb_parity])。 其他两种类型的奇偶校验是地址奇偶校验 (AP) @@ -308,38 +300,36 @@ struct Base_112 { // Surveillance replies DF=4,5 AP // All call reply struct with_PI { - virtual ~with_PI() = default; - void set_crc(std::string& msg, std::string icao, std::string bds) { - icao.resize(6, '0'); - bds.resize(6, '0'); - int size = static_cast(msg.size()); - auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); - auto transponder_address = get_crc_transponder_address(); - msg.replace(size - 24, 24, Psc::xorBin(crc_24, transponder_address)); - } - // All call reply 是基于审讯的报文,PI是 询问器设备码 和 crc 异或而成的 - // 所以,必须知道询问器标识符 才能校验是否有错误 - // 每个设备应该只有一个询问器标识符 - static bool check_crc(std::string& msg_bin, std::string icao_hex, - std::string bds = "") { - auto crc_24 = std::bitset<24>(crc(msg_bin, true)).to_string(); - auto last_24 = msg_bin.substr(msg_bin.size() - 24); - return crc_24 == last_24; - } - static std::string parse_transponder_address(std::string& msg_bin, - std::string icao_hex) { - int size = static_cast(msg_bin.size()); - icao_hex.resize(6, '0'); - auto crc_24 = std::bitset<24>(crc(msg_bin, true)).to_string(); - auto PA = Psc::hex2bin(icao_hex); - auto last_24 = msg_bin.substr(size - 24); - return Psc::bin2hex(Psc::xorBin(crc_24, Psc::xorBin(PA, last_24))); - } + virtual ~with_PI() = default; + void set_crc(std::string& msg, std::string icao, std::string bds) { + icao.resize(6, '0'); + bds.resize(6, '0'); + int size = static_cast(msg.size()); + auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); + auto transponder_address = get_crc_transponder_address(); + msg.replace(size - 24, 24, Psc::xorBin(crc_24, transponder_address)); + } + // All call reply 是基于审讯的报文,PI是 询问器设备码 和 crc 异或而成的 + // 所以,必须知道询问器标识符 才能校验是否有错误 + // 每个设备应该只有一个询问器标识符 + static bool check_crc(std::string& msg_bin, std::string icao_hex, std::string bds = "") { + auto crc_24 = std::bitset<24>(crc(msg_bin, true)).to_string(); + auto last_24 = msg_bin.substr(msg_bin.size() - 24); + return crc_24 == last_24; + } + static std::string parse_transponder_address(std::string& msg_bin, std::string icao_hex) { + int size = static_cast(msg_bin.size()); + icao_hex.resize(6, '0'); + auto crc_24 = std::bitset<24>(crc(msg_bin, true)).to_string(); + auto PA = Psc::hex2bin(icao_hex); + auto last_24 = msg_bin.substr(size - 24); + return Psc::bin2hex(Psc::xorBin(crc_24, Psc::xorBin(PA, last_24))); + } protected: - virtual std::string get_crc_transponder_address() { - return Psc::hex2bin(std::string("000000")); - } - // ADS-B 是自发的,所以解不出询问器地址 询问器地址都是0 + virtual std::string get_crc_transponder_address() { + return Psc::hex2bin(std::string("000000")); + } + // ADS-B 是自发的,所以解不出询问器地址 询问器地址都是0 }; using Psc::bin2; using Psc::bin2hex; @@ -350,29 +340,28 @@ using Psc::xorBin; // icao = crc0 xor last // crc === icao xor last === crc0 struct with_AP { - void set_crc(std::string& msg, std::string icao, std::string bds) { - icao.resize(6, '0'); - bds.resize(6, '0'); - auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); - auto PA = xorBin(crc_24, std::bitset<24>(icao).to_string()); - msg.replace(msg.size() - 24, 24, PA); - } - static bool check_crc(std::string& msg_bin, std::string icao_hex, - std::string bds = "") { - int size = static_cast(msg_bin.size()); - icao_hex.resize(6, '0'); - bds.resize(6, '0'); - auto icao_24 = hex2bin(icao_hex); - auto last_24 = msg_bin.substr(size - 24); - std::string crc_code = xorBin(last_24, icao_24); - std::string temp = msg_bin; - temp.replace(size - 24, 24, crc_code); - bool ret = crc(temp) == 0; - if (!ret) { - return false; - } - return ret; - } + void set_crc(std::string& msg, std::string icao, std::string bds) { + icao.resize(6, '0'); + bds.resize(6, '0'); + auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); + auto PA = xorBin(crc_24, std::bitset<24>(icao).to_string()); + msg.replace(msg.size() - 24, 24, PA); + } + static bool check_crc(std::string& msg_bin, std::string icao_hex, std::string bds = "") { + int size = static_cast(msg_bin.size()); + icao_hex.resize(6, '0'); + bds.resize(6, '0'); + auto icao_24 = hex2bin(icao_hex); + auto last_24 = msg_bin.substr(size - 24); + std::string crc_code = xorBin(last_24, icao_24); + std::string temp = msg_bin; + temp.replace(size - 24, 24, crc_code); + bool ret = crc(temp) == 0; + if (!ret) { + return false; + } + return ret; + } }; // ICAO: DD33AA 1101 1101 0011 0011 1010 1010 // @@ -384,37 +373,36 @@ struct with_AP { // 不知道什么消息用这个校验 // struct with_DP { - void set_crc(std::string& msg, std::string icao, std::string bds) { - icao.resize(6, '0'); - bds.resize(6, '0'); - auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); - auto icao_24 = hex2bin(icao); - auto bds_24 = hex2bin(bds); - auto transponder_address = hex2bin(std::string("000000")); - auto last24 = - xorBin(xorBin(crc_24, icao_24), xorBin(bds_24, transponder_address)); - msg.replace(msg.size() - 24, 24, last24); - } - static bool check_crc(std::string& msg_bin, std::string_view icao_hex, - std::string_view bds) { - return true; - } - static std::string transponder_address(std::string& msg, std::string icao, - std::string bds) { - int size = static_cast(msg.size()); - icao.resize(6, '0'); - bds.resize(6, '0'); - auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); - auto last_24 = msg.substr(size - 24); - auto icao_bin = hex2bin(icao); - auto bds_bin = hex2bin(bds); - return bin2hex(xorBin(xorBin(last_24, crc_24), xorBin(icao_bin, bds_bin))); - } + void set_crc(std::string& msg, std::string icao, std::string bds) { + icao.resize(6, '0'); + bds.resize(6, '0'); + auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); + auto icao_24 = hex2bin(icao); + auto bds_24 = hex2bin(bds); + auto transponder_address = hex2bin(std::string("000000")); + auto last24 = xorBin(xorBin(crc_24, icao_24), xorBin(bds_24, transponder_address)); + msg.replace(msg.size() - 24, 24, last24); + } + static bool check_crc(std::string& msg_bin, std::string_view icao_hex, std::string_view bds) { + return true; + } + static std::string transponder_address(std::string& msg, std::string icao, std::string bds) { + int size = static_cast(msg.size()); + icao.resize(6, '0'); + bds.resize(6, '0'); + auto crc_24 = std::bitset<24>(crc(msg, true)).to_string(); + auto last_24 = msg.substr(size - 24); + auto icao_bin = hex2bin(icao); + auto bds_bin = hex2bin(bds); + return bin2hex(xorBin(xorBin(last_24, crc_24), xorBin(icao_bin, bds_bin))); + } }; -#define D_BDS(number) \ - struct BDS##number { \ - static std::string bds() { return #number; } \ - }; +#define D_BDS(number) \ + struct BDS##number { \ + static std::string bds() { \ + return #number; \ + } \ + }; D_BDS(_) // 凑数的 // ADS-B D_BDS(05) // 机载位置 @@ -436,15 +424,15 @@ D_BDS(60) // 航向和速度报告 // Commb MS Meteorological services D_BDS(44) // 气象例行空气报告 D_BDS(45) // 气象灾害报告 -#define CE(cond, msg) \ - if (cond) { \ - static Log_Type log_type({}, {{"POS", LOG_POS}}); \ - SSR::mode_s_logger->error("", log_type, msg); \ - } -#define CE2(cond, msg) \ - if (cond) { \ - static Log_Type log_type({}, {{"POS", LOG_POS}}); \ - SSR::mode_s_logger->error("", log_type, msg); \ - return std::nullopt; \ - } -} +#define CE(cond, msg) \ + if (cond) { \ + static Log_Type log_type({}, {{"POS", LOG_POS}}); \ + SSR::mode_s_logger->error("", log_type, msg); \ + } +#define CE2(cond, msg) \ + if (cond) { \ + static Log_Type log_type({}, {{"POS", LOG_POS}}); \ + SSR::mode_s_logger->error("", log_type, msg); \ + return std::nullopt; \ + } +} // namespace SSR diff --git a/SSR/py_Mode_S/Common.cpp b/SSR/py_Mode_S/Common.cpp index 0176b37..5625af9 100644 --- a/SSR/py_Mode_S/Common.cpp +++ b/SSR/py_Mode_S/Common.cpp @@ -1,5 +1,5 @@ #include "Common.h" -#include "Core/Base/global_include.h" +#include "Psc_Cpp_Core/Base/global_include.h" #include #undef max #undef min diff --git a/SSR/py_Mode_S/Common.h b/SSR/py_Mode_S/Common.h index bb0f372..5254b7e 100644 --- a/SSR/py_Mode_S/Common.h +++ b/SSR/py_Mode_S/Common.h @@ -1,66 +1,64 @@ #pragma once #include #include "../CPR/CPR.h" -#include "Core/Base/global_include.h" +#include "Psc_Cpp_Core/Base/global_include.h" #include "SSR/enum.h" #ifndef M_PI #define M_PI 3.14159265358979323846 #endif -#define Handle_Error(msg) \ - std::cerr << msg; \ - return std::nullopt; -#define Handle_Error2(cond, msg) \ - if (cond) { \ - std::cerr << msg; \ - return std::nullopt; \ - } -#define Handle_Error3(cond, msg) \ - if (cond) { \ - std::cerr << msg; \ - } -#define Exec(var, expr) \ - auto _opt_##var = type_code(msg); \ - if (!_opt_##var.has_value()) \ - return std::nullopt; \ - auto var = _opt_##var.value(); -#define Exec2(var, expr) \ - auto _opt_##var = expr; \ - auto var = _opt_##var.value(); +#define Handle_Error(msg) \ + std::cerr << msg; \ + return std::nullopt; +#define Handle_Error2(cond, msg) \ + if (cond) { \ + std::cerr << msg; \ + return std::nullopt; \ + } +#define Handle_Error3(cond, msg) \ + if (cond) { \ + std::cerr << msg; \ + } +#define Exec(var, expr) \ + auto _opt_##var = type_code(msg); \ + if (!_opt_##var.has_value()) \ + return std::nullopt; \ + auto var = _opt_##var.value(); +#define Exec2(var, expr) \ + auto _opt_##var = expr; \ + auto var = _opt_##var.value(); // 定义一个宏 release模式输出core // dump信息到控制台,到文件,这个文件名还要是自增的,这样不丢, // 然后直接崩溃能看调用栈 // Debug模式下,然后抛出异常,异常在最顶层集中处理,没有异常才把该报文的信息汇总 namespace SSR { struct Air_Speed { - double speed = -1; // kt - double angle = -1; // degree - int vertical_rate = -1; // ft/min - std::string - speed_type; // Speed type: 'GS' for ground speed, 'AS' for airspeed - std::string direction_source; // Optional: Direction source ('TRUE_NORTH' or - // 'MAGNETIC_NORTH') - std::string - vertical_rate_source; // Optional: Vertical rate source ('BARO' or 'GNSS') - Psc::JSON toJson() { - return Psc::JSON::object({ - {"speed", speed}, - {"angle", angle}, - {"vertical_rate", vertical_rate}, - {"speed_type", speed_type}, - {"direction_source", direction_source}, - {"vertical_rate_source", vertical_rate_source}, - }); - } + double speed = -1; // kt + double angle = -1; // degree + int vertical_rate = -1; // ft/min + std::string speed_type; // Speed type: 'GS' for ground speed, 'AS' for airspeed + std::string direction_source; // Optional: Direction source ('TRUE_NORTH' or + // 'MAGNETIC_NORTH') + std::string vertical_rate_source; // Optional: Vertical rate source ('BARO' or 'GNSS') + Psc::JSON toJson() { + return Psc::JSON::object({ + {"speed", speed}, + {"angle", angle}, + {"vertical_rate", vertical_rate}, + {"speed_type", speed_type}, + {"direction_source", direction_source}, + {"vertical_rate_source", vertical_rate_source}, + }); + } }; struct Ground_Speed { - double speed = -1; // kt - double angle = -1; // degree - Psc::JSON toJson() { - return Psc::JSON::object({ - {"speed", speed}, - {"angle", angle}, - }); - } + double speed = -1; // kt + double angle = -1; // degree + Psc::JSON toJson() { + return Psc::JSON::object({ + {"speed", speed}, + {"angle", angle}, + }); + } }; // common Downlink_Format decode_df(std::string_view msg); @@ -78,15 +76,14 @@ void set_df(std::string& msg, Downlink_Format df); // return result; // }; Transponder_Capability decode_transponder_capability(std::string_view msg); -void set_transponder_capability(std::string& msg, - Transponder_Capability transponder_capability); +void set_transponder_capability(std::string& msg, Transponder_Capability transponder_capability); int crc(std::string_view msg_bin, bool encode); std::string decode_icao(std::string_view msg_bin); std::string set_icao(std::string& msg, std::string_view icaoHex); bool is_icao_assigned(std::string_view icao); int type_code(std::string_view msg); void set_type_code(std::string& msg, int type_code); -int get_type_code(std::string & msg); +int get_type_code(std::string& msg); std::string idcode(std::string_view msg); void set_idcode(std::string& msg, std::string_view idcode); std::string decode_squawk13(std::string_view binstr); @@ -128,17 +125,16 @@ const double beta = -0.0065; // [K/m] ISA temp gradient below tropopause const double r_earth = 6371000; // m, average earth radius const double a0 = 340.293988; // m/s, sea level speed of sound ISA struct Atmos { - double p; - double rho; - double T; + double p; + double rho; + double T; }; Atmos atmos(double H); double temperature(double H); double pressure(double H); double density(double H); double vsound(double H); -double distance(double lat1, double lon1, double lat2, double lon2, - double H = 0); +double distance(double lat1, double lon1, double lat2, double lon2, double H = 0); double bearing(double lat1, double lon1, double lat2, double lon2); double tas2mach(double Vtas, double H); double mach2tas(double Mach, double H); @@ -156,8 +152,7 @@ double cas2mach(double Vcas, double H); Airborne position ------------------------------------------ */ -double decode_altitude_12_meter(std::string_view msg_bin, - Altitude_type altitude_type); +double decode_altitude_12_meter(std::string_view msg_bin, Altitude_type altitude_type); std::string encode_altitude_code_12(double height, Altitude_type altitude_type); Vortex_Type parse_vortex_type(std::string_view msg); // ------------------------------------------ @@ -190,8 +185,7 @@ double altitude_diff(std::string_view msg); std::string vertical_rate_code_10(double vertical_rate); double decode_vertical_rate_10(std::string_view vertical_rate); std::string GNSS_barometric_altitudes_difference_8(double altitude_difference); -std::string encode_velocity_22(Ground_Speed_Type subType, double track_angle, - double ground_speed); +std::string encode_velocity_22(Ground_Speed_Type subType, double track_angle, double ground_speed); std::string encode_magnetic_heading_11(double heading); std::string encode_airspeed_10(Air_Speed_Code_Type subtype, double airspeed); // ------------------------------------------ @@ -233,13 +227,13 @@ RET alt40fms(std::string_view msg); // ------------------------------------------ bool is44(std::string_view msg); struct Wind { - int wind_speed; - double direction; + int wind_speed; + double direction; }; RET wind44(std::string_view msg); struct Temperature { - double temperature; - double temperature_alternative; + double temperature; + double temperature_alternative; }; Temperature temp44(std::string_view msg); int p44(std::string_view msg); @@ -319,8 +313,7 @@ Emergency_Type emergency_status(std::string_view msg); // ------------------------------------------ // BDS // ------------------------------------------ -std::string is50or60(std::string_view msg, double spd_ref, double trk_ref, - double alt_ref); +std::string is50or60(std::string_view msg, double spd_ref, double trk_ref, double alt_ref); std::string infer(std::string_view msg_bin, bool mrar = false); std::vector infer2(std::string_view msg, bool mrar = false); // ADS-B diff --git a/SSR/py_Mode_S/bds.cpp b/SSR/py_Mode_S/bds.cpp index 012b85c..0c5e84a 100644 --- a/SSR/py_Mode_S/bds.cpp +++ b/SSR/py_Mode_S/bds.cpp @@ -1,5 +1,5 @@ #include "./Common.h" -#include "Core/Statistics/Frequency_Limit.h" +#include "Psc_Cpp_Core/Statistics/Frequency_Limit.h" #include "SSR/CPR/CPR.h" #include #undef max diff --git a/main.cmake b/main.cmake index e66427b..b7796cc 100644 --- a/main.cmake +++ b/main.cmake @@ -1,15 +1,16 @@ -_create(interface SSR) - -set(Core Core_Static) -_attach_include_dir("SSR" "${CMAKE_CURRENT_LIST_DIR}") -_attach_source_dir("SSR" "${CMAKE_CURRENT_LIST_DIR}/SSR") -_attach_source_dir("SSR" "${CMAKE_CURRENT_LIST_DIR}/test") -_depend(SSR ${Core}) -#_create(dll readsb2) -#_attach_include_dir(readsb2 "${CMAKE_CURRENT_LIST_DIR}") -#_attach_source_dir(readsb2 "${CMAKE_CURRENT_LIST_DIR}/readsb2") + + + + +set(Core Psc_Core_Static) +set(SSR_srcs) +append_glob_source(SSR_srcs "${CMAKE_CURRENT_LIST_DIR}/SSR" "${CMAKE_CURRENT_LIST_DIR}/test") +add_library(SSR STATIC ${SSR_srcs}) +target_include_directories(SSR PUBLIC "${CMAKE_CURRENT_LIST_DIR}") +target_link_libraries(SSR PUBLIC ${Core}) +