mirror of
https://github.com/ArduPilot/ardupilot.git
synced 2026-10-06 19:00:27 +08:00
AP_Logger: log long MSG messages in multiple chunks
This commit is contained in:
committed by
Peter Barker
parent
bcf7f93060
commit
6ed9b2c3f2
@@ -908,6 +908,10 @@ void AP_Logger::Write_Message(const char *message)
|
||||
{
|
||||
FOR_EACH_BACKEND(Write_Message(message));
|
||||
}
|
||||
void AP_Logger::Write_MessageChunk(uint8_t id, const char *messagechunk, uint8_t chunk_seq)
|
||||
{
|
||||
FOR_EACH_BACKEND(Write_MessageChunk(id, messagechunk, chunk_seq));
|
||||
}
|
||||
|
||||
void AP_Logger::Write_Mode(uint8_t mode, const ModeReason reason)
|
||||
{
|
||||
|
||||
@@ -262,6 +262,16 @@ public:
|
||||
void Write_Power(void);
|
||||
void Write_Radio(const mavlink_radio_t &packet);
|
||||
void Write_Message(const char *message);
|
||||
// support for multi-chunk messages:
|
||||
uint8_t get_MSG_id() {
|
||||
uint8_t ret = ++MSG_id;
|
||||
if (ret > 0) {
|
||||
return ret;
|
||||
}
|
||||
return ++MSG_id;
|
||||
}
|
||||
void Write_MessageChunk(uint8_t id, const char *messagechunk, uint8_t chunk_seq);
|
||||
|
||||
void Write_MessageF(const char *fmt, ...);
|
||||
void Write_Compass();
|
||||
void Write_Mode(uint8_t mode, const ModeReason reason);
|
||||
@@ -616,6 +626,9 @@ private:
|
||||
void log_file_content(FileContent &file_content, const char *filename);
|
||||
void file_content_update(FileContent &file_content);
|
||||
#endif
|
||||
|
||||
// support for multi-chunk messages:
|
||||
uint8_t MSG_id;
|
||||
};
|
||||
|
||||
namespace AP {
|
||||
|
||||
@@ -139,6 +139,7 @@ public:
|
||||
}
|
||||
bool Write_Message(const char *message);
|
||||
bool Write_MessageF(const char *fmt, ...);
|
||||
bool Write_MessageChunk(uint8_t id, const char *messagechunk, uint8_t chunk_seq);
|
||||
bool Write_Mission_Cmd(const AP_Mission &mission,
|
||||
const AP_Mission::Mission_Command &cmd,
|
||||
LogMessages id);
|
||||
@@ -275,6 +276,7 @@ private:
|
||||
bool emit_format_for_type(LogMessages a_type);
|
||||
Bitmask<256> _formats_written;
|
||||
|
||||
uint8_t msg_id; // the ID of the next MSG message that will be logged
|
||||
};
|
||||
|
||||
#endif // HAL_LOGGING_ENABLED
|
||||
|
||||
@@ -339,13 +339,37 @@ bool AP_Logger_Backend::Write_EntireMission()
|
||||
// Write a text message to the log
|
||||
bool AP_Logger_Backend::Write_Message(const char *message)
|
||||
{
|
||||
struct log_Message pkt{
|
||||
LOG_PACKET_HEADER_INIT(LOG_MESSAGE_MSG),
|
||||
// i==0 here means we log an empty string if it is passed in:
|
||||
const uint8_t id = AP::logger().get_MSG_id(); // there is a race condition on this ID; if a thread logs a message at the same time as the main thread then we can re-use this
|
||||
|
||||
uint8_t chunk_seq = 0;
|
||||
for (uint8_t i=0; i == 0 || i<strlen(message); i += 64, chunk_seq++) {
|
||||
const bool success = Write_MessageChunk(id, &message[i], chunk_seq);
|
||||
if (i == 0 && !success) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
bool AP_Logger_Backend::Write_MessageChunk(uint8_t id, const char *messagechunk, uint8_t chunk_seq)
|
||||
{
|
||||
struct log_MSG pkt{
|
||||
LOG_PACKET_HEADER_INIT(LOG_MSG_MSG),
|
||||
time_us : AP_HAL::micros64(),
|
||||
id : id,
|
||||
chunk_seq : chunk_seq,
|
||||
msg : {}
|
||||
};
|
||||
strncpy_noterm(pkt.msg, message, sizeof(pkt.msg));
|
||||
return WriteCriticalBlock(&pkt, sizeof(pkt));
|
||||
const uint16_t remaining = strlen(messagechunk);
|
||||
strncpy_noterm(pkt.msg, messagechunk, MIN(sizeof(pkt.msg), remaining));
|
||||
// result comes from success writing the first chunk; this
|
||||
// prevents trying to write out the front of a message
|
||||
// repeatedly.
|
||||
const bool success = WriteCriticalBlock(&pkt, sizeof(pkt));
|
||||
if (chunk_seq == 0) {
|
||||
return success;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void AP_Logger::Write_Power(void)
|
||||
|
||||
@@ -246,9 +246,11 @@ struct PACKED log_Error {
|
||||
};
|
||||
|
||||
|
||||
struct PACKED log_Message {
|
||||
struct PACKED log_MSG {
|
||||
LOG_PACKET_HEADER;
|
||||
uint64_t time_us;
|
||||
uint8_t id;
|
||||
uint8_t chunk_seq;
|
||||
char msg[64];
|
||||
};
|
||||
|
||||
@@ -813,6 +815,8 @@ struct PACKED log_VER {
|
||||
// @LoggerMessage: MSG
|
||||
// @Description: Textual messages
|
||||
// @Field: TimeUS: Time since system startup
|
||||
// @Field: ID: identifier for chunks making up a message
|
||||
// @Field: Seq: chunk sequence number within message identified by ID
|
||||
// @Field: Message: message text
|
||||
|
||||
// @LoggerMessage: MULT
|
||||
@@ -1154,8 +1158,8 @@ struct PACKED log_VER {
|
||||
{ LOG_PARAMETER_MSG, sizeof(log_Parameter), \
|
||||
"PARM", "QNff", "TimeUS,Name,Value,Default", "s---", "F---" }, \
|
||||
LOG_STRUCTURE_FROM_GPS \
|
||||
{ LOG_MESSAGE_MSG, sizeof(log_Message), \
|
||||
"MSG", "QZ", "TimeUS,Message", "s-", "F-"}, \
|
||||
{ LOG_MSG_MSG, sizeof(log_MSG), \
|
||||
"MSG", "QBBZ", "TimeUS,ID,Seq,Message", "s---", "F---"}, \
|
||||
{ LOG_RCIN_MSG, sizeof(log_RCIN), \
|
||||
"RCIN", "QHHHHHHHHHHHHHH", "TimeUS,C1,C2,C3,C4,C5,C6,C7,C8,C9,C10,C11,C12,C13,C14", "sYYYYYYYYYYYYYY", "F--------------", true }, \
|
||||
{ LOG_RCI2_MSG, sizeof(log_RCI2), \
|
||||
@@ -1271,7 +1275,7 @@ enum LogMessages : uint8_t {
|
||||
LOG_PARAMETER_MSG = 32,
|
||||
LOG_IDS_FROM_NAVEKF2,
|
||||
LOG_IDS_FROM_NAVEKF3,
|
||||
LOG_MESSAGE_MSG,
|
||||
LOG_MSG_MSG,
|
||||
LOG_RCIN_MSG,
|
||||
LOG_RCI2_MSG,
|
||||
LOG_RCOUT_MSG,
|
||||
|
||||
@@ -80,8 +80,8 @@ static const struct LogStructure log_structure[] = {
|
||||
"s---------",
|
||||
"F---------"
|
||||
},
|
||||
{ LOG_MESSAGE_MSG,
|
||||
sizeof(log_Message),
|
||||
{ LOG_MSG_MSG,
|
||||
sizeof(log_MSG),
|
||||
"MSG",
|
||||
"QZ",
|
||||
"TimeUS,Message",
|
||||
|
||||
Reference in New Issue
Block a user