Repository: meshtastic/Meshtastic-arduino
Pull request #42: update to library and example to create robust processing and callbacks for both decoded and encrypted and generic PortNum
Author: login: rabarar
Created: 2025-05-08T14:59:31Z | Merged: 2025-05-23T13:39:09Z

- added additional callbacks for encrypted and non-TEXT portNums
- added robust serial output for incoming packets for information visibility on packets for all PortNum and subvariants




Diff:
diff --git a/examples/NodeInfoClient/NodeInfoClient.ino b/examples/NodeInfoClient/NodeInfoClient.ino
index bdce026..2be73c4 100644
--- a/examples/NodeInfoClient/NodeInfoClient.ino
+++ b/examples/NodeInfoClient/NodeInfoClient.ino
@@ -16,6 +16,9 @@
 
 */
 
+// Uncomment the line below to enable debugging 
+// #define MT_DEBUGGING
+
 #include <Meshtastic.h>
 
 // Pins to use for WiFi; these defaults are for an Adafruit Feather M0 WiFi.
@@ -67,9 +70,6 @@ void setup() {
 #endif
   Serial.println(" mode");
 
-  // Set to true if you want debug messages
-  mt_set_debug(false);
-  
   randomSeed(micros());
 }
 
diff --git a/examples/SendReceiveClient/SendReceiveClient.ino b/examples/SendReceiveClient/SendReceiveClient.ino
index 758eec6..134a6d9 100644
--- a/examples/SendReceiveClient/SendReceiveClient.ino
+++ b/examples/SendReceiveClient/SendReceiveClient.ino
@@ -9,6 +9,9 @@
     which prints the message to the serial console.
 */
 
+// Uncomment the line below to enable debugging 
+// #define MT_DEBUGGING
+
 #include <Meshtastic.h>
 
 // Pins to use for WiFi; these defaults are for an Adafruit Feather M0 WiFi.
@@ -23,7 +26,7 @@
 #define SERIAL_RX_PIN 13
 #define SERIAL_TX_PIN 15
 // A different baud rate to communicate with the Meshtastic device can be specified here
-#define BAUD_RATE 9600
+#define BAUD_RATE 38400
 
 // Send a text message every this many seconds
 #define SEND_PERIOD 300
@@ -38,6 +41,58 @@ void connected_callback(mt_node_t *node, mt_nr_progress_t progress) {
   not_yet_connected = false;
 }
 
+
+const char* meshtastic_portnum_to_string(meshtastic_PortNum port) {
+  switch (port) {
+      case meshtastic_PortNum_UNKNOWN_APP: return "UNKNOWN_APP";
+      case meshtastic_PortNum_TEXT_MESSAGE_APP: return "TEXT_MESSAGE_APP";
+      case meshtastic_PortNum_REMOTE_HARDWARE_APP: return "REMOTE_HARDWARE_APP";
+      case meshtastic_PortNum_POSITION_APP: return "POSITION_APP";
+      case meshtastic_PortNum_NODEINFO_APP: return "NODEINFO_APP";
+      case meshtastic_PortNum_ROUTING_APP: return "ROUTING_APP";
+      case meshtastic_PortNum_ADMIN_APP: return "ADMIN_APP";
+      case meshtastic_PortNum_TEXT_MESSAGE_COMPRESSED_APP: return "TEXT_MESSAGE_COMPRESSED_APP";
+      case meshtastic_PortNum_WAYPOINT_APP: return "WAYPOINT_APP";
+      case meshtastic_PortNum_AUDIO_APP: return "AUDIO_APP";
+      case meshtastic_PortNum_DETECTION_SENSOR_APP: return "DETECTION_SENSOR_APP";
+      case meshtastic_PortNum_REPLY_APP: return "REPLY_APP";
+      case meshtastic_PortNum_IP_TUNNEL_APP: return "IP_TUNNEL_APP";
+      case meshtastic_PortNum_PAXCOUNTER_APP: return "PAXCOUNTER_APP";
+      case meshtastic_PortNum_SERIAL_APP: return "SERIAL_APP";
+      case meshtastic_PortNum_STORE_FORWARD_APP: return "STORE_FORWARD_APP";
+      case meshtastic_PortNum_RANGE_TEST_APP: return "RANGE_TEST_APP";
+      case meshtastic_PortNum_TELEMETRY_APP: return "TELEMETRY_APP";
+      case meshtastic_PortNum_ZPS_APP: return "ZPS_APP";
+      case meshtastic_PortNum_SIMULATOR_APP: return "SIMULATOR_APP";
+      case meshtastic_PortNum_TRACEROUTE_APP: return "TRACEROUTE_APP";
+      case meshtastic_PortNum_NEIGHBORINFO_APP: return "NEIGHBORINFO_APP";
+      case meshtastic_PortNum_ATAK_PLUGIN: return "ATAK_PLUGIN";
+      case meshtastic_PortNum_MAP_REPORT_APP: return "MAP_REPORT_APP";
+      case meshtastic_PortNum_POWERSTRESS_APP: return "POWERSTRESS_APP";
+      case meshtastic_PortNum_PRIVATE_APP: return "PRIVATE_APP";
+      case meshtastic_PortNum_ATAK_FORWARDER: return "ATAK_FORWARDER";
+      case meshtastic_PortNum_MAX: return "MAX";
+      default: return "UNKNOWN_PORTNUM";
+  }
+}
+
+void displayPubKey(meshtastic_MeshPacket_public_key_t pubKey, char *hex_str) {
+      for (int i = 0; i < 32; i++) {
+          sprintf(&hex_str[i * 2], "%02x", (unsigned char)pubKey.bytes[i]);
+      }
+  
+      hex_str[64] = '\0'; // Null terminator
+}
+
+
+void encrypted_callback(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_MeshPacket_public_key_t pubKey, meshtastic_MeshPacket_encrypted_t *enc_payload) {
+  Serial.printf("Received an ENCRYPTED callback from: %x to: %x\r\n", from, to);
+}
+
+void portnum_callback(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_PortNum portNum, meshtastic_Data_payload_t *payload) {
+  Serial.printf("Received a callback for PortNum %s\r\n", meshtastic_portnum_to_string(portNum));
+}
+
 // This callback function will be called whenever the radio receives a text message
 void text_message_callback(uint32_t from, uint32_t to,  uint8_t channel, const char* text) {
   // Do your own thing here. This example just prints the message to the serial console.
@@ -59,8 +114,8 @@ void text_message_callback(uint32_t from, uint32_t to,  uint8_t channel, const c
 }
 
 void setup() {
-  // Try for up to five seconds to find a serial port; if not, the show must go on
-  Serial.begin(9600);
+  // Try for up to five seconds to find a serial port; if not, the show must gox on
+  Serial.begin(115200);
   while(true) {
     if (Serial) break;
     if (millis() > 5000) {
@@ -82,9 +137,6 @@ void setup() {
 #endif
   Serial.println(" mode");
 
-  // Set to true if you want debug messages
-  mt_set_debug(false);
-  
   randomSeed(micros());
 
   // Initial connection to the Meshtastic device
@@ -92,6 +144,8 @@ void setup() {
 
   // Register a callback function to be called whenever a text message is received
   set_text_message_callback(text_message_callback);
+  set_portnum_callback(portnum_callback);
+  set_encrypted_callback(encrypted_callback);
 }
 
 void loop() {
diff --git a/src/Meshtastic.h b/src/Meshtastic.h
index 3cc9fbe..ba6d615 100644
--- a/src/Meshtastic.h
+++ b/src/Meshtastic.h
@@ -75,6 +75,12 @@ bool mt_request_node_report(void (*callback)(mt_node_t *, mt_nr_progress_t));
 // Set the callback function that gets called when the node receives a text message.
 void set_text_message_callback(void (*callback)(uint32_t from, uint32_t to, uint8_t channel, const char * text));
 
+// Set the callback function that gets called when the node receives any other portNum
+void set_portnum_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_PortNum port, meshtastic_Data_payload_t *payload));
+
+// Set the callback function that gets called when the node receives an encrypted payload
+void set_encrypted_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_MeshPacket_public_key_t pubKey, meshtastic_MeshPacket_encrypted_t *payload));
+
 // Send a text message with *text* as payload, to a destination node (optional), on a certain channel (optional).
 bool mt_send_text(const char * text, uint32_t dest = BROADCAST_ADDR, uint8_t channel_index = 0);
 
diff --git a/src/mt_internals.h b/src/mt_internals.h
index a0a5c95..943249c 100644
--- a/src/mt_internals.h
+++ b/src/mt_internals.h
@@ -3,9 +3,13 @@
 
 #include "Meshtastic.h"
 
-extern bool mt_debugging;
-void mt_debug_print(const char * s);
-#define d(s) mt_debug_print(s)
+#ifdef MT_DEBUGGING
+#define d(...) _d(__VA_ARGS__)
+#else
+#define d(...) do {} while (0) 
+#endif
+
+void _d(const char * fmt, ...);
 
 extern bool mt_wifi_mode;
 extern bool mt_serial_mode;
diff --git a/src/mt_protocol.cpp b/src/mt_protocol.cpp
index 4633e9d..e3f98b9 100644
--- a/src/mt_protocol.cpp
+++ b/src/mt_protocol.cpp
@@ -32,20 +32,24 @@ uint32_t want_config_id = 0;
 // Node number of the MT node hosting our WiFi
 uint32_t my_node_num = 0;
 
-bool mt_debugging = false;
 void (*text_message_callback)(uint32_t from, uint32_t to,  uint8_t channel, const char* text) = NULL;
+void (*portnum_callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_PortNum port, meshtastic_Data_payload_t *payload) = NULL;
+void (*encrypted_callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_MeshPacket_public_key_t pubKey, meshtastic_MeshPacket_encrypted_t *enc_payload) = NULL;
+
 void (*node_report_callback)(mt_node_t *, mt_nr_progress_t) = NULL;
 mt_node_t node;
 
 bool mt_wifi_mode = false;
 bool mt_serial_mode = false;
 
-void d(const char * s) {
-  if (mt_debugging) Serial.println(s);
-}
-
-void mt_set_debug(bool on) {
-  mt_debugging = on;
+#define VA_BUFSIZE 512
+void _d(const char * fmt, ...) {
+  static char vabuf[VA_BUFSIZE];
+  va_list ap;
+  va_start(ap, fmt);
+  vsnprintf(vabuf, sizeof(vabuf), fmt, ap);
+  Serial.println(vabuf);
+  Serial.flush();
 }
 
 bool mt_send_radio(const char * buf, size_t len) {
@@ -93,10 +97,10 @@ bool mt_request_node_report(void (*callback)(mt_node_t *, mt_nr_progress_t)) {
   want_config_id = random(0x7FffFFff);  // random() can't handle anything bigger
   toRadio.want_config_id = want_config_id;
 
-  if (mt_debugging) {
-    Serial.print("Requesting node report with random ID ");
-    Serial.println(want_config_id);
-  }
+#ifdef MT_DEBUGGING
+  Serial.print("Requesting node report with random ID ");
+  Serial.println(want_config_id);
+#endif
 
   bool rv = _mt_send_toRadio(toRadio);
 
@@ -138,10 +142,365 @@ bool mt_send_heartbeat() {
 
 }
 
+void set_portnum_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_PortNum port, meshtastic_Data_payload_t *payload)) {
+  portnum_callback = callback;
+}
+
+void set_encrypted_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_MeshPacket_public_key_t pubKey, meshtastic_MeshPacket_encrypted_t *payload)) {
+  encrypted_callback = callback;
+}
+
 void set_text_message_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, const char* text)) {
   text_message_callback = callback;
 }
 
+bool handle_id_tag(uint32_t id) {
+  d("id_tag: ID: %d\r\n", id);
+  return true;
+}
+
+bool handle_config_tag(meshtastic_Config *config) {
+  switch (config->which_payload_variant) {
+    case meshtastic_Config_device_tag:
+      d("Config:device_tag:  role: %d\r\n", config->payload_variant.device.role);
+      d("Config:device_tag:  serial enabled: %d\r\n", config->payload_variant.device.serial_enabled);
+      d("Config:device_tag:  button gpio: %d\r\n", config->payload_variant.device.button_gpio);
+      d("Config:device_tag:  buzzer gpio: %d\r\n", config->payload_variant.device.buzzer_gpio);
+      d("Config:device_tag:  rebroadcast mode: %d\r\n", config->payload_variant.device.rebroadcast_mode);
+      d("Config:device_tag:  node_info_broadcast_secs: %d\r\n", config->payload_variant.device.node_info_broadcast_secs);
+      d("Config:device_tag:  double-tap-as-button-press: %d\r\n", config->payload_variant.device.double_tap_as_button_press);
+      d("Config:device_tag:  is_managed: %d\r\n", config->payload_variant.device.is_managed);
+      d("Config:device_tag:  disable_triple_click: %d\r\n", config->payload_variant.device.disable_triple_click);
+      d("Config:device_tag:  tz_def: %s\r\n", config->payload_variant.device.tzdef);
+      d("Config:device_tag:  led_heartbeat_disabled: %d\r\n", config->payload_variant.device.led_heartbeat_disabled);
+      break;
+
+    case meshtastic_Config_position_tag:
+      d("Config:position_tag:  position_broadcast_secs: %d\r\n", config->payload_variant.position.position_broadcast_secs);
+      d("Config:position_tag:  position_broadcast_smart_enabled: %d\r\n", config->payload_variant.position.position_broadcast_smart_enabled);
+      d("Config:position_tag:  fixed_position: %d\r\n", config->payload_variant.position.fixed_position);
+      d("Config:position_tag:  gps_enabled: %d\r\n", config->payload_variant.position.gps_enabled);
+      d("Config:position_tag:  gps_update_interval: %d\r\n", config->payload_variant.position.gps_update_interval);
+      d("Config:position_tag:  gps_attempt_time: %d\r\n", config->payload_variant.position.gps_attempt_time);
+      d("Config:position_tag:  position_flags: %d\r\n", config->payload_variant.position.position_flags);
+      d("Config:position_tag:  rx_gpio: %d\r\n", config->payload_variant.position.rx_gpio);
+      d("Config:position_tag:  tx_gpio: %d\r\n", config->payload_variant.position.tx_gpio);
+      d("Config:position_tag:  broadcast_smart_min_distance: %d\r\n", config->payload_variant.position.broadcast_smart_minimum_distance);
+      d("Config:position_tag:  broadcast_smart_min_interval_secs: %d\r\n", config->payload_variant.position.broadcast_smart_minimum_interval_secs);
+      d("Config:position_tag:  gps_en_gpio: %d\r\n", config->payload_variant.position.gps_en_gpio);
+      d("Config:position_tag:  gps_mode %d\r\n", config->payload_variant.position.gps_mode);
+      break;
+
+    case meshtastic_Config_power_tag: 
+      d("Config:power_tag:  is_power_saving %d\r\n", config->payload_variant.power.is_power_saving);
+      d("Config:power_tag:  on_battery_shutdown_after_secs %d\r\n", config->payload_variant.power.on_battery_shutdown_after_secs);
+      d("Config:power_tag:  adv_multiplier_override %f\r\n", config->payload_variant.power.adc_multiplier_override);
+      d("Config:power_tag:  wait_bluetooth_secs %d\r\n", config->payload_variant.power.wait_bluetooth_secs);
+      d("Config:power_tag:  sds_secs %d\r\n", config->payload_variant.power.sds_secs);
+      d("Config:power_tag:  ls_secs %d\r\n", config->payload_variant.power.ls_secs);
+      d("Config:power_tag:  min_wake_secs %d\r\n", config->payload_variant.power.min_wake_secs);
+      d("Config:power_tag:  device_battery_ina_aaddr %d\r\n", config->payload_variant.power.device_battery_ina_address);
+      d("Config:power_tag:  powermon_enables %d\r\n", config->payload_variant.power.powermon_enables);
+      break;
+
+    case meshtastic_Config_network_tag:
+      d("Config:network_tag:wifi_enabled: %d  \r\n", config->payload_variant.network.wifi_enabled);
+      d("Config:network_tag:wifi_ssid: %s  \r\n", config->payload_variant.network.wifi_ssid);
+      d("Config:network_tag:wifi_psk: %s  \r\n", config->payload_variant.network.wifi_psk);
+      d("Config:network_tag:ntp_server: %s  \r\n", config->payload_variant.network.ntp_server);
+      d("Config:network_tag:eth_enabled: %d  \r\n", config->payload_variant.network.eth_enabled);
+      d("Config:network_tag:addr_mode: %d  \r\n", config->payload_variant.network.address_mode);
+      d("Config:network_tag:has_ipv4_config: %d  \r\n", config->payload_variant.network.has_ipv4_config);
+      d("Config:network_tag:ipv4_config: %d  \r\n", config->payload_variant.network.ipv4_config);
+      d("Config:network_tag:rsyslog_server: %s  \r\n", config->payload_variant.network.rsyslog_server);
+      break;
+
+    case meshtastic_Config_display_tag: 
+      d("Config:display_tag:screen_on_seconds: %d  \r\n", config->payload_variant.display.screen_on_secs);
+      d("Config:display_tag:gps_format: %d  \r\n", config->payload_variant.display.gps_format);
+      d("Config:display_tag:auto_screen_carousel_secs: %d  \r\n", config->payload_variant.display.auto_screen_carousel_secs);
+      d("Config:display_tag:compass_north_top: %d  \r\n", config->payload_variant.display.compass_north_top);
+      d("Config:display_tag:flip_screen: %d  \r\n", config->payload_variant.display.flip_screen);
+      d("Config:display_tag:units: %d  \r\n", config->payload_variant.display.units);
+      d("Config:display_tag:oled: %d  \r\n", config->payload_variant.display.oled);
+      d("Config:display_tag:displayMode: %d  \r\n", config->payload_variant.display.displaymode);
+      d("Config:display_tag:heading_bold: %d  \r\n", config->payload_variant.display.heading_bold);
+      d("Config:display_tag:wake_on_tap_or_motion: %d  \r\n", config->payload_variant.display.wake_on_tap_or_motion);
+      d("Config:display_tag:compass_orientation: %d  \r\n", config->payload_variant.display.compass_orientation);
+      break;
+
+    case meshtastic_Config_lora_tag:
+      d("Config:lora_tag:use_preset: %d  \r\n", config->payload_variant.lora.use_preset);
+      d("Config:lora_tag:modem_preset: %d  \r\n", config->payload_variant.lora.modem_preset);
+      d("Config:lora_tag:bandwidth: %d  \r\n", config->payload_variant.lora.bandwidth);
+      d("Config:lora_tag:spread_factor: %d  \r\n", config->payload_variant.lora.spread_factor);
+      d("Config:lora_tag:coding_rate: %d  \r\n", config->payload_variant.lora.coding_rate);
+      d("Config:lora_tag:frequency_offset: %d  \r\n", config->payload_variant.lora.frequency_offset);
+      d("Config:lora_tag:region: %d  \r\n", config->payload_variant.lora.region);
+      d("Config:lora_tag:hot_limit: %d  \r\n", config->payload_variant.lora.hop_limit);
+      d("Config:lora_tag:tx_enabled: %d  \r\n", config->payload_variant.lora.tx_enabled);
+      d("Config:lora_tag:tx_power: %d  \r\n", config->payload_variant.lora.tx_power);
+      d("Config:lora_tag:channel_num: %d  \r\n", config->payload_variant.lora.channel_num);
+      d("Config:lora_tag:override_duty_cycle: %d  \r\n", config->payload_variant.lora.override_duty_cycle);
+      d("Config:lora_tag:sx126x_rx_boosted_gain: %d  \r\n", config->payload_variant.lora.sx126x_rx_boosted_gain);
+      d("Config:lora_tag:override_frequency: %d  \r\n", config->payload_variant.lora.override_frequency);
+      d("Config:lora_tag:pa_fan_disabled: %d  \r\n", config->payload_variant.lora.pa_fan_disabled);
+      d("Config:lora_tag:ignore_incoming_count: %d  \r\n", config->payload_variant.lora.ignore_incoming_count);
+      d("Config:lora_tag:ignore_mqtt: %d  \r\n", config->payload_variant.lora.ignore_mqtt);
+      d("Config:lora_tag:config_okay_to_mqtt: %d  \r\n", config->payload_variant.lora.config_ok_to_mqtt);
+      break;
+
+    case meshtastic_Config_bluetooth_tag: 
+      d("Config:bluetooth_tag:enabled: %d  \r\n", config->payload_variant.bluetooth.enabled);
+      d("Config:bluetooth_tag:fixed_pin: %d  \r\n", config->payload_variant.bluetooth.fixed_pin);
+      d("Config:bluetooth_tag:mode: %d  \r\n", config->payload_variant.bluetooth.mode);
+      break;
+
+    case meshtastic_Config_security_tag: 
+      d("Config:security_tag:is_managed: %d \r\n", config->payload_variant.security.is_managed);
+      d("Config:security_tag:public_key: %x \r\n", config->payload_variant.security.public_key);
+      d("Config:security_tag:private_key: %x \r\n", config->payload_variant.security.private_key);
+      d("Config:security_tag:admin_key_count: %x \r\n", config->payload_variant.security.admin_key_count);
+      d("Config:security_tag:serial_enabled: %x \r\n", config->payload_variant.security.serial_enabled);
+      d("Config:security_tag:debug_log_api_enabled: %x \r\n", config->payload_variant.security.debug_log_api_enabled);
+      d("Config:security_tag:admin_channel_enabled: %x \r\n", config->payload_variant.security.admin_channel_enabled);
+      break;
+
+    case meshtastic_Config_sessionkey_tag: 
+      d("Config:sessionkey_tag:dummy_field: %x \r\n", config->payload_variant.sessionkey.dummy_field);
+      break;
+
+    case meshtastic_Config_device_ui_tag:
+      d("Config.device_ui:alert_enabled: %d\r\n", config->payload_variant.device_ui.alert_enabled);
+      d("Config.device_ui:banner_enabled: %d\r\n", config->payload_variant.device_ui.banner_enabled);
+      d("Config.device_ui:has_node_filter: %d\r\n", config->payload_variant.device_ui.has_node_filter);
+      d("Config.device_ui:has_node_highlight: %d\r\n", config->payload_variant.device_ui.has_node_highlight);
+      d("Config.device_ui:language: %d\r\n", config->payload_variant.device_ui.language);
+      d("Config.device_ui:node_filter: %d\r\n", config->payload_variant.device_ui.node_filter);
+      d("Config.device_ui:node_highlight: %d\r\n", config->payload_variant.device_ui.node_highlight);
+      d("Config.device_ui:pin_code: %d\r\n", config->payload_variant.device_ui.pin_code);
+      d("Config.device_ui:ring_tone_id: %d\r\n", config->payload_variant.device_ui.ring_tone_id);
+      d("Config.device_ui:screen_brightness: %d\r\n", config->payload_variant.device_ui.screen_brightness);
+      d("Config.device_ui:screen_lock: %d\r\n", config->payload_variant.device_ui.screen_lock);
+      d("Config.device_ui:screen_timeout: %d\r\n", config->payload_variant.device_ui.screen_timeout);
+      break;
+
+    default:
+      d("Unknown Config_Tag payload variant: %d\r\n", config->which_payload_variant);
+  }
+  return true;
+}
+
+bool handle_channel_tag(meshtastic_Channel *channel) {
+  d("ChannelTag:index: %d\r\n", channel->index);
+  d("ChannelTag:has_settings: %d\r\n", channel->has_settings);
+  d("ChannelTag:role: %d\r\n", channel->role);
+  return true;
+}
+
+bool handle_FromRadio_log_record_tag(meshtastic_LogRecord *record) {
+  d("FromRadio_log_record:message: %s\r\n", record->message);
+  d("FromRadio_log_record:time: %d\r\n", record->time);
+  d("FromRadio_log_record:source: %s\r\n", record->source);
+  d("FromRadio_log_record:level: %s\r\n", record->level);
+  return true;
+}
+
+bool handle_moduleConfig_tag(meshtastic_ModuleConfig *module){ 
+  switch (module->which_payload_variant) {
+      case meshtastic_ModuleConfig_mqtt_tag:
+      d("ModuleConfig:mqtt:enabled: %d\r\n", module->payload_variant.mqtt.enabled);
+      d("ModuleConfig:mqtt:address: %s\r\n", module->payload_variant.mqtt.address);
+      d("ModuleConfig:mqtt:username: %s\r\n", module->payload_variant.mqtt.username);
+      d("ModuleConfig:mqtt:password: %s\r\n", module->payload_variant.mqtt.password);
+      d("ModuleConfig:mqtt:encryption_enabled: %d\r\n", module->payload_variant.mqtt.encryption_enabled);
+      d("ModuleConfig:mqtt:json_enabled: %d\r\n", module->payload_variant.mqtt.json_enabled);
+      d("ModuleConfig:mqtt:root: %s\r\n", module->payload_variant.mqtt.root);
+      d("ModuleConfig:mqtt:proxy_to_client_enabled: %d\r\n", module->payload_variant.mqtt.proxy_to_client_enabled);
+      d("ModuleConfig:mqtt:map_reporting_enabled %d\r\n", module->payload_variant.mqtt.map_report_settings);
+      d("ModuleConfig:mqtt:has_map_report_settings %d\r\n", module->payload_variant.mqtt.has_map_report_settings);
+      break;
+
+      case meshtastic_ModuleConfig_serial_tag:
+        d("ModuleConfig:serial:enabled: %d\r\n", module->payload_variant.serial.enabled);
+        d("ModuleConfig:serial:echo: %d\r\n", module->payload_variant.serial.echo);
+        d("ModuleConfig:serial:rxd-gpio-pin: %d\r\n", module->payload_variant.serial.rxd);
+        d("ModuleConfig:serial:txd-gpio-pin: %d\r\n", module->payload_variant.serial.txd);
+        d("ModuleConfig:serial:baud: %d\r\n", module->payload_variant.serial.baud);
+        d("ModuleConfig:serial:timeout: %d\r\n", module->payload_variant.serial.timeout);
+        d("ModuleConfig:serial:mode: %d\r\n", module->payload_variant.serial.mode);
+        d("ModuleConfig:serial:override_console_serial_port: %d\r\n", module->payload_variant.serial.override_console_serial_port);
+      break;
+
+      case meshtastic_ModuleConfig_external_notification_tag:
+        d("ModuleConfig:external_notification:enabled: %d\r\n", module->payload_variant.external_notification.enabled);
+        d("ModuleConfig:external_notification:output_ms: %d\r\n", module->payload_variant.external_notification.output_ms);
+        d("ModuleConfig:external_notification:output: %d\r\n", module->payload_variant.external_notification.output);
+        d("ModuleConfig:external_notification:active: %d\r\n", module->payload_variant.external_notification.active);
+        d("ModuleConfig:external_notification:alert_message: %d\r\n", module->payload_variant.external_notification.alert_message);
+        d("ModuleConfig:external_notification:alert_bell: %d\r\n", module->payload_variant.external_notification.alert_bell);
+        d("ModuleConfig:external_notification:use_pwm: %d\r\n", module->payload_variant.external_notification.use_pwm);
+        d("ModuleConfig:external_notification:output_vibra: %d\r\n", module->payload_variant.external_notification.output_vibra);
+        d("ModuleConfig:external_notification:output_buzzer: %d\r\n", module->payload_variant.external_notification.output_buzzer);
+        d("ModuleConfig:external_notification:alert_message_vibra: %d\r\n", module->payload_variant.external_notification.alert_message_vibra);
+        d("ModuleConfig:external_notification:alert_message_buzzer: %d\r\n", module->payload_variant.external_notification.alert_message_buzzer);
+        d("ModuleConfig:external_notification:alert_bell_vibra: %d\r\n", module->payload_variant.external_notification.alert_bell_vibra);
+        d("ModuleConfig:external_notification:alert_bell_buzzer: %d\r\n", module->payload_variant.external_notification.alert_bell_buzzer);
+        d("ModuleConfig:external_notification:nag_timeout: %d\r\n", module->payload_variant.external_notification.nag_timeout);
+        d("ModuleConfig:external_notification:use_i2s_as_buzzer: %d\r\n", module->payload_variant.external_notification.use_i2s_as_buzzer);
+      break;
+
+      case meshtastic_ModuleConfig_store_forward_tag:
+        d("ModuleConfig:store_forward:enabled: %d\r\n", module->payload_variant.store_forward.enabled);
+        d("ModuleConfig:store_forward:heartbeat: %d\r\n", module->payload_variant.store_forward.heartbeat);
+        d("ModuleConfig:store_forward:history_return_max: %d\r\n", module->payload_variant.store_forward.history_return_max);
+        d("ModuleConfig:store_forward:history_return_window: %d\r\n", module->payload_variant.store_forward.history_return_window);
+        d("ModuleConfig:store_forward:is_server: %d\r\n", module->payload_variant.store_forward.is_server);
+        d("ModuleConfig:store_forward:records: %d\r\n", module->payload_variant.store_forward.records);
+      break;
+
+      case meshtastic_ModuleConfig_range_test_tag: 
+        d("ModuleConfig:range_test:enabled: %d\r\n", module->payload_variant.range_test.enabled);
+        d("ModuleConfig:range_test:save: %d\r\n", module->payload_variant.range_test.save);
+        d("ModuleConfig:range_test:sender: %d\r\n", module->payload_variant.range_test.sender);
+      break;
+
+      case meshtastic_ModuleConfig_telemetry_tag:
+        d("ModuleConfig:telemetry:air_quality_enabled: %d\r\n", module->payload_variant.telemetry.air_quality_enabled);
+        d("ModuleConfig:telemetry:air_quality_interval: %d\r\n", module->payload_variant.telemetry.air_quality_interval);
+        d("ModuleConfig:telemetry:device_update_interval: %d\r\n", module->payload_variant.telemetry.device_update_interval);
+        d("ModuleConfig:telemetry:environment_display_fahrenheit: %d\r\n", module->payload_variant.telemetry.environment_display_fahrenheit);
+        d("ModuleConfig:telemetry:environment_measurement_enabled: %d\r\n", module->payload_variant.telemetry.environment_measurement_enabled);
+        d("ModuleConfig:telemetry:environment_screen_enabled: %d\r\n", module->payload_variant.telemetry.environment_screen_enabled);
+        d("ModuleConfig:telemetry:environment_update_interval: %d\r\n", module->payload_variant.telemetry.environment_update_interval);
+        d("ModuleConfig:telemetry:health_measurement_enabled: %d\r\n", module->payload_variant.telemetry.health_measurement_enabled);
+        d("ModuleConfig:telemetry:health_screen_enabled: %d\r\n", module->payload_variant.telemetry.health_screen_enabled);
+        d("ModuleConfig:telemetry:health_update_interval: %d\r\n", module->payload_variant.telemetry.health_update_interval);
+        d("ModuleConfig:telemetry:power_measurement_enabled: %d\r\n", module->payload_variant.telemetry.power_measurement_enabled);
+        d("ModuleConfig:telemetry:power_update_interval: %d\r\n", module->payload_variant.telemetry.power_update_interval);
+
+      break;
+
+      case meshtastic_ModuleConfig_canned_message_tag: 
+        d("ModuleConfig:canned_message:enabled: %d\r\n", module->payload_variant.canned_message.enabled);
+        d("ModuleConfig:canned_message:allow_input_source: %d\r\n", module->payload_variant.canned_message.allow_input_source);
+        d("ModuleConfig:canned_message:inputbroker_event_ccw: %d\r\n", module->payload_variant.canned_message.inputbroker_event_ccw);
+        d("ModuleConfig:canned_message:inputbroker_event_cw: %d\r\n", module->payload_variant.canned_message.inputbroker_event_cw);
+        d("ModuleConfig:canned_message:inputbroker_event_pass: %d\r\n", module->payload_variant.canned_message.inputbroker_event_press);
+        d("ModuleConfig:canned_message:inputbroker_pin_a: %d\r\n", module->payload_variant.canned_message.inputbroker_pin_a);
+        d("ModuleConfig:canned_message:inputbroker_pin_b: %d\r\n", module->payload_variant.canned_message.inputbroker_pin_b);
+        d("ModuleConfig:canned_message:inputbroker_pin_press: %d\r\n", module->payload_variant.canned_message.inputbroker_pin_press);
+        d("ModuleConfig:canned_message:rotary1_enabled: %d\r\n", module->payload_variant.canned_message.rotary1_enabled);
+        d("ModuleConfig:canned_message:send_bell: %d\r\n", module->payload_variant.canned_message.send_bell);
+        d("ModuleConfig:canned_message:updown1_enabled: %d\r\n", module->payload_variant.canned_message.updown1_enabled);
+      break;
+
+      case meshtastic_ModuleConfig_audio_tag: 
+        d("ModuleConfig:audio:codec2_enabled: %d\r\n", module->payload_variant.audio.codec2_enabled);
+        d("ModuleConfig:audio:bitrate: %d\r\n", module->payload_variant.audio.bitrate);
+        d("ModuleConfig:audio:i2s_din: %d\r\n", module->payload_variant.audio.i2s_din);
+        d("ModuleConfig:audio:i2s_sck: %d\r\n", module->payload_variant.audio.i2s_sck);
+        d("ModuleConfig:audio:i2s_sd: %d\r\n", module->payload_variant.audio.i2s_sd);
+        d("ModuleConfig:audio:i2s_ws: %d\r\n", module->payload_variant.audio.i2s_ws);
+        d("ModuleConfig:audio:ptt_pin: %d\r\n", module->payload_variant.audio.ptt_pin);
+      break;
+
+      case meshtastic_ModuleConfig_remote_hardware_tag: 
+        d("ModuleConfig:remote_hardware:enabled: %d\r\n", module->payload_variant.remote_hardware.enabled);
+        d("ModuleConfig:remote_hardware:allow_undefined_pin_access: %d\r\n", module->payload_variant.remote_hardware.allow_undefined_pin_access);
+        d("ModuleConfig:remote_hardware:available_pins: %d\r\n", module->payload_variant.remote_hardware.available_pins);
+        d("ModuleConfig:remote_hardware:available_pins_count: %d\r\n", module->payload_variant.remote_hardware.available_pins_count);
+
+      break;
+
+      case meshtastic_ModuleConfig_neighbor_info_tag: 
+        d("ModuleConfig:neighbor_info:enabled: %d\r\n", module->payload_variant.neighbor_info.enabled);
+        d("ModuleConfig:neighbor_info:transmit_over_lora: %d\r\n", module->payload_variant.neighbor_info.transmit_over_lora);
+        d("ModuleConfig:neighbor_info:update_interval: %d\r\n", module->payload_variant.neighbor_info.update_interval);
+      break;
+
+      case meshtastic_ModuleConfig_ambient_lighting_tag:
+        d("ModuleConfig:ambient_lighting:led_state: %d\r\n", module->payload_variant.ambient_lighting.led_state);
+        d("ModuleConfig:ambient_lighting:current: %d\r\n", module->payload_variant.ambient_lighting.current);
+        d("ModuleConfig:ambient_lighting:red: %d\r\n", module->payload_variant.ambient_lighting.red);
+        d("ModuleConfig:ambient_lighting:green: %d\r\n", module->payload_variant.ambient_lighting.green);
+        d("ModuleConfig:ambient_lighting:blue: %d\r\n", module->payload_variant.ambient_lighting.blue);
+      break;
+
+      case meshtastic_ModuleConfig_detection_sensor_tag: 
+        d("ModuleConfig:detection_sensor:enabled: %d\r\n", module->payload_variant.detection_sensor.enabled);
+        d("ModuleConfig:detection_sensor:detection_trigger_type: %d\r\n", module->payload_variant.detection_sensor.detection_trigger_type);
+        d("ModuleConfig:detection_sensor:min_broadcast_secs: %d\r\n", module->payload_variant.detection_sensor.minimum_broadcast_secs);
+        d("ModuleConfig:detection_sensor:monitor_pin: %d\r\n", module->payload_variant.detection_sensor.monitor_pin);
+        d("ModuleConfig:detection_sensor:name: %d\r\n", module->payload_variant.detection_sensor.name);
+        d("ModuleConfig:detection_sensor:send_bell: %d\r\n", module->payload_variant.detection_sensor.send_bell);
+        d("ModuleConfig:detection_sensor:state_broadcast_secs: %d\r\n", module->payload_variant.detection_sensor.state_broadcast_secs);
+        d("ModuleConfig:detection_sensor:use_pullup: %d\r\n", module->payload_variant.detection_sensor.use_pullup);
+      break;
+
+      case meshtastic_ModuleConfig_paxcounter_tag:
+        d("ModuleConfig:paxcounter:enabled: %d\r\n", module->payload_variant.paxcounter.enabled);
+        d("ModuleConfig:paxcounter:ble_threshold: %d\r\n", module->payload_variant.paxcounter.ble_threshold);
+        d("ModuleConfig:paxcounter:paxcounter_update_interval: %d\r\n", module->payload_variant.paxcounter.paxcounter_update_interval);
+        d("ModuleConfig:paxcounter:wifi_threshold: %d\r\n", module->payload_variant.paxcounter.wifi_threshold);
+      break;
+
+      default:
+        d("Unknown payload variant: %d\r\n", module->which_payload_variant);
+  }
+  return true;
+}
+
+bool handle_queueStatus_tag(meshtastic_QueueStatus *qstatus) {
+  d("queueStatus: maxlen: %d\r\n", qstatus->maxlen);
+  d("queueStatus: res: %d\r\n", qstatus->res);
+  d("queueStatus: free: %d\r\n", qstatus->free);
+  d("queueStatus: mesh_packet_id: %d\r\n", qstatus->mesh_packet_id);
+  return true;
+}
+
+bool handle_xmodemPacket_tag(meshtastic_XModem *packet) {
+  d("XmodemPacket: XModem control #: %d\r\n", packet->control);
+  d("XmodemPacket: XModem sequence #: %d\r\n", packet->seq);
+  d("XmodemPacket: XModem crc16: %d\r\n", packet->crc16);
+  return true;
+}
+
+bool handle_metatag_data(meshtastic_DeviceMetadata *meta) {
+  d("metatag_data:FW Version: %s\r\n", meta->firmware_version);
+  d("metatag_data:device_state_version: %d\r\n", meta->device_state_version);
+  d("metatag_data:canShutdown: %d\r\n", meta->canShutdown);
+  d("metatag_data:hasWiFi: %d\r\n", meta->hasWifi);
+  d("metatag_data:hasBluetooth: %d\r\n", meta->hasBluetooth);
+  d("metatag_data:hasEthernet: %d\r\n", meta->hasEthernet);
+  d("metatag_data:role: %d\r\n", meta->role);
+  d("metatag_data:positionFlags: %d\r\n", meta->position_flags);
+  d("metatag_data:hw_model: %d\r\n", meta->hw_model);
+  d("metatag_data:hasRemoteHardware: %d\r\n", meta->hasRemoteHardware);
+  d("metatag_data:excludedModules: %d\r\n", meta->excluded_modules);
+  return true;
+}
+
+bool handle_mqttClientProxyMessage_tag(meshtastic_MqttClientProxyMessage *mqtt) {
+  d("mqttClientProxyMessage:Topic: %s\r\n", mqtt->topic);
+  switch (mqtt->which_payload_variant) {
+    case meshtastic_MqttClientProxyMessage_data_tag:
+      // TODO - INVALID d("mqttClientProxyMessage:data: %s\r\n", mqtt->payload_variant.data);
+      break;
+    case meshtastic_MqttClientProxyMessage_text_tag:
+      d("mqttClientProxyMessage:text %s\r\n", mqtt->payload_variant.text);
+      break;
+  }
+  d("mqttClientProxyMessage:retained: %d\r\n", mqtt->retained);
+  return true;
+}
+
+bool handle_fileInfo_tag(meshtastic_FileInfo *fInfo) {
+  d("fileInfo:fileName: %s\r\n", fInfo->file_name);
+  d("fileInfo:sizeBytes: %d\r\n", fInfo->size_bytes);
+  return true;
+}
+
 bool handle_my_info(meshtastic_MyNodeInfo *myNodeInfo) {
   my_node_num = myNodeInfo->my_node_num;
   return true;
@@ -210,15 +569,55 @@ bool handle_config_complete_id(uint32_t now, uint32_t config_complete_id) {
 
 bool handle_mesh_packet(meshtastic_MeshPacket *meshPacket) {
   if (meshPacket->which_payload_variant == meshtastic_MeshPacket_decoded_tag) {
-    if (meshPacket->decoded.portnum == meshtastic_PortNum_TEXT_MESSAGE_APP) {
-      if (text_message_callback != NULL)
-        text_message_callback(meshPacket->from, meshPacket->to, meshPacket->channel, (const char*)meshPacket->decoded.payload.bytes);
-    } else {
-      // TODO handle other portnums
-      return false;
+    switch (meshPacket->decoded.portnum) {
+        case meshtastic_PortNum_TEXT_MESSAGE_APP:
+            if (text_message_callback != NULL) {
+              text_message_callback(meshPacket->from, meshPacket->to, meshPacket->channel, (const char*)meshPacket->decoded.payload.bytes);
+          } else {
+        }
+        break;
+      case meshtastic_PortNum_ADMIN_APP:
+      case meshtastic_PortNum_ATAK_FORWARDER:
+      case meshtastic_PortNum_ATAK_PLUGIN:
+      case meshtastic_PortNum_AUDIO_APP: 
+      case meshtastic_PortNum_DETECTION_SENSOR_APP: 
+      case meshtastic_PortNum_IP_TUNNEL_APP: 
+      case meshtastic_PortNum_MAP_REPORT_APP:
+      case meshtastic_PortNum_MAX: 
+      case meshtastic_PortNum_NEIGHBORINFO_APP: 
+      case meshtastic_PortNum_NODEINFO_APP: 
+      case meshtastic_PortNum_PAXCOUNTER_APP:
+      case meshtastic_PortNum_POSITION_APP: 
+      case meshtastic_PortNum_POWERSTRESS_APP: 
+      case meshtastic_PortNum_PRIVATE_APP: 
+      case meshtastic_PortNum_RANGE_TEST_APP:
+      case meshtastic_PortNum_REMOTE_HARDWARE_APP: 
+      case meshtastic_PortNum_REPLY_APP: 
+      case meshtastic_PortNum_ROUTING_APP:
+      case meshtastic_PortNum_SERIAL_APP:
+      case meshtastic_PortNum_SIMULATOR_APP:
+      case meshtastic_PortNum_STORE_FORWARD_APP:
+      case meshtastic_PortNum_TELEMETRY_APP: 
+      case meshtastic_PortNum_TEXT_MESSAGE_COMPRESSED_APP:
+      case meshtastic_PortNum_TRACEROUTE_APP: 
+      case meshtastic_PortNum_UNKNOWN_APP: 
+      case meshtastic_PortNum_WAYPOINT_APP: 
+      case meshtastic_PortNum_ZPS_APP:
+        if (portnum_callback != NULL)
+          portnum_callback(meshPacket->from, meshPacket->to, meshPacket->channel, meshPacket->decoded.portnum, &meshPacket->decoded.payload);
+        break;
+
+      default:
+          d("Unknown portnum %d\r\n", meshPacket->decoded.portnum);
+            return false;
     }
-  } else {
-    return false;
+  } else if  (meshPacket -> which_payload_variant == meshtastic_MeshPacket_encrypted_tag ) {
+      d("encoded packet From: %x To: %x\r\n", meshPacket->from, meshPacket->to);
+      if (encrypted_callback != NULL) {
+          encrypted_callback(meshPacket->from, meshPacket->to, meshPacket->channel, meshPacket->public_key, &meshPacket->encrypted);
+    	    return true;
+      }
+    	return false;
   }
   return true;
 }
@@ -245,18 +644,40 @@ bool handle_packet(uint32_t now, size_t payload_len) {
   }
 
   switch (fromRadio.which_payload_variant) {
-    case meshtastic_FromRadio_my_info_tag:
+    case meshtastic_FromRadio_id_tag: // 1
+      return handle_id_tag(fromRadio.id);
+    case meshtastic_FromRadio_packet_tag: //2
+      return handle_mesh_packet(&fromRadio.packet);
+    case meshtastic_FromRadio_my_info_tag: // 3
       return handle_my_info(&fromRadio.my_info);
-    case meshtastic_FromRadio_node_info_tag:
+    case meshtastic_FromRadio_node_info_tag: // 4
       return handle_node_info(&fromRadio.node_info);
-    case meshtastic_FromRadio_config_complete_id_tag:
+    case meshtastic_FromRadio_config_tag : // 5
+      return handle_config_tag(&fromRadio.config);
+    case meshtastic_FromRadio_log_record_tag: // 6
+      return handle_FromRadio_log_record_tag(&fromRadio.log_record);
+    case meshtastic_FromRadio_config_complete_id_tag: // 7
       return handle_config_complete_id(now, fromRadio.config_complete_id);
-    case meshtastic_FromRadio_packet_tag:
-      return handle_mesh_packet(&fromRadio.packet);
-    case meshtastic_FromRadio_rebooted_tag:
+    case meshtastic_FromRadio_rebooted_tag: // 8
       _mt_send_toRadio(toRadio);
+
+    case  meshtastic_FromRadio_moduleConfig_tag: // 9
+      return handle_moduleConfig_tag(&fromRadio.moduleConfig);
+    case meshtastic_FromRadio_channel_tag: // 10
+      return handle_channel_tag(&fromRadio.channel);
+    case meshtastic_FromRadio_queueStatus_tag: // 11
+      return handle_queueStatus_tag(&fromRadio.queueStatus); 
+    case  meshtastic_FromRadio_xmodemPacket_tag: // 12
+      return handle_xmodemPacket_tag(&fromRadio.xmodemPacket);
+    case meshtastic_FromRadio_metadata_tag: //        13
+      return handle_metatag_data(&fromRadio.metadata);
+    case meshtastic_FromRadio_mqttClientProxyMessage_tag: // 14
+      return handle_mqttClientProxyMessage_tag(&fromRadio.mqttClientProxyMessage);
+    case meshtastic_FromRadio_fileInfo_tag :  // 15
+      return handle_fileInfo_tag(&fromRadio.fileInfo); 
+
     default:
-      if (mt_debugging) {
+#ifdef MT_DEBUGGING
         // Rate limit
         // Serial input buffer overflows during initial connection, while we're slowly printing these at 9600 baud
         constexpr uint32_t limitMs = 100; 
@@ -267,7 +688,7 @@ bool handle_packet(uint32_t now, size_t payload_len) {
             Serial.print("Got a payloadVariant we don't recognize: ");
             Serial.println(fromRadio.which_payload_variant);
         }
-      }
+#endif
       return false;
   }
 
@@ -301,14 +722,14 @@ void mt_protocol_check_packet(uint32_t now) {
   }
 
   /*
-  if (mt_debugging) {
+#ifdef MT_DEBUGGING
     Serial.print("Got a full packet! ");
     for (int i = 0 ; i < pb_size ; i++) {
       Serial.print(pb_buf[i], HEX);
       Serial.print(" ");
     }
     Serial.println();
-  }
+#endif
   */
 
   handle_packet(now, payload_len);
diff --git a/src/mt_serial.cpp b/src/mt_serial.cpp
index c87d116..ec5803d 100644
--- a/src/mt_serial.cpp
+++ b/src/mt_serial.cpp
@@ -32,12 +32,12 @@ bool mt_serial_send_radio(const char * buf, size_t len) {
   size_t wrote = serial->write(buf, len);
   if (wrote == len) return true;
 
-  if (mt_debugging) {
+#ifdef MT_DEBUGGING
     Serial.print("Tried to send radio ");
     Serial.print(len);
     Serial.print(" but actually sent ");
     Serial.println(wrote);
-  }
+#endif
 
   return false;
 }
diff --git a/src/mt_wifi.cpp b/src/mt_wifi.cpp
index 364086c..841ca95 100644
--- a/src/mt_wifi.cpp
+++ b/src/mt_wifi.cpp
@@ -99,7 +99,9 @@ bool mt_wifi_loop(uint32_t now) {
       // We just connected to WiFi! Now try to make a TCP connection. If it fails, nobody's
       // actually noticing, but we'll time out soon enough when no packets come in, and then
       // we'll try again from the beginning.
-      if (mt_debugging) print_wifi_status();
+#ifdef MT_DEBUGGING	
+	  print_wifi_status();
+#endif
       mt_wifi_reset_idle_timeout(now);
       open_tcp_connection();
       return can_send;
@@ -117,10 +119,10 @@ bool mt_wifi_loop(uint32_t now) {
     default:
       // None of these should ever happen. If they do, let me know what led to them and I'll
       // update this switch statement.
-      if (mt_debugging) {
+#if MT_DEBUGGING
         Serial.print("Unknown WiFi status ");
         Serial.println(wifi_status);
-      }
+#endif
       while(true);
   }
 }
@@ -162,12 +164,12 @@ bool mt_wifi_send_radio(const char * buf, size_t len) {
   size_t wrote = client.write(buf, len);
   if (wrote == len) return true;
 
-  if (mt_debugging) {
+#ifdef MT_DEBUGGING
     Serial.print("Tried to send radio ");
     Serial.print(len);
     Serial.print(" but actually sent ");
     Serial.println(wrote);
-  }
+#endif
   client.stop();
   return false;
 }


Reviews:
user: login: GUVWAF
body: Thanks for the PR, I left two comments.
state: CHANGES_REQUESTED
author_association: MEMBER
submitted_at: 2025-05-11T14:31:41Z
user: login: GUVWAF
state: COMMENTED
author_association: MEMBER
submitted_at: 2025-05-12T18:26:46Z
user: login: GUVWAF
state: COMMENTED
author_association: MEMBER
submitted_at: 2025-05-13T17:13:26Z
user: login: GUVWAF
state: APPROVED
author_association: MEMBER
submitted_at: 2025-05-13T18:03:22Z
user: login: caveman99
state: APPROVED
author_association: MEMBER
submitted_at: 2025-05-23T13:38:27Z

Review comments:
diff_hunk: @@ -138,10 +141,365 @@ bool mt_send_heartbeat() {
 
 }
 
+void set_portnum_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_PortNum port, meshtastic_Data_payload_t *payload)) {
+  portnum_callback = callback;
+}
+
+void set_encrypted_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_MeshPacket_public_key_t pubKey, meshtastic_MeshPacket_encrypted_t *payload)) {
+  encrypted_callback = callback;
+}
+
 void set_text_message_callback(void (*callback)(uint32_t from, uint32_t to,  uint8_t channel, const char* text)) {
   text_message_callback = callback;
 }
 
+bool handle_id_tag(uint32_t id) {
+  Serial.printf("id_tag: ID: %d\r\n", id);
+  return true;
+}
+
+bool handle_config_tag(meshtastic_Config *config) {
+  switch (config->which_payload_variant) {
+    case meshtastic_Config_device_tag:
+      Serial.printf("Config:device_tag:  role: %d\r\n", config->payload_variant.device.role);
path: src/mt_protocol.cpp
user: login: GUVWAF
body: Not sure it's a good idea to print every single entry in a function of the library itself. It creates a wall of text and you cannot disable it unless you modify the library. These entries also may change, and new ones may be added in the future. 
If you want to print something, I would just only print which tag it is, and only when `mt_debugging` is enabled.
created_at: 2025-05-11T14:30:57Z
author_association: MEMBER
diff_hunk: @@ -20,10 +20,10 @@
 // Pins to use for SoftwareSerial. Boards that don't use SoftwareSerial, and
 // instead provide their own Serial1 connection through fixed pins
 // will ignore these settings and use their own.
-#define SERIAL_RX_PIN 13
-#define SERIAL_TX_PIN 15
+#define SERIAL_RX_PIN D5
path: examples/SendReceiveClient/SendReceiveClient.ino
user: login: GUVWAF
body: Please do not check in unrelated changes.
created_at: 2025-05-11T14:31:11Z
author_association: MEMBER
diff_hunk: @@ -34,14 +34,24 @@ uint32_t my_node_num = 0;
 
 bool mt_debugging = false;
 void (*text_message_callback)(uint32_t from, uint32_t to,  uint8_t channel, const char* text) = NULL;
+void (*portnum_callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_PortNum port, meshtastic_Data_payload_t *payload) = NULL;
+void (*encrypted_callback)(uint32_t from, uint32_t to,  uint8_t channel, meshtastic_MeshPacket_public_key_t pubKey, meshtastic_MeshPacket_encrypted_t *enc_payload) = NULL;
+
 void (*node_report_callback)(mt_node_t *, mt_nr_progress_t) = NULL;
 mt_node_t node;
 
 bool mt_wifi_mode = false;
 bool mt_serial_mode = false;
 
-void d(const char * s) {
-  if (mt_debugging) Serial.println(s);
+#define VA_BUFSIZE 512
+void d(const char * fmt, ...) {
+  static char vabuf[VA_BUFSIZE];
+  if (mt_debugging) {
path: src/mt_protocol.cpp
user: login: GUVWAF
body: Since there's now a lot of hardcoded strings, I would rather make `mt_debugging` a  pre-processor macro and make the print a no-op when it's not enabled. This is especially for more flash-constrained devices.
created_at: 2025-05-12T18:26:45Z
author_association: MEMBER
diff_hunk: @@ -83,7 +135,7 @@ void setup() {
   Serial.println(" mode");
 
   // Set to true if you want debug messages
-  mt_set_debug(false);
+  mt_set_debug(true);
path: examples/SendReceiveClient/SendReceiveClient.ino
user: login: GUVWAF
body: We'll need to change this function (also in the NodeInfoClient example) to the new macro.
created_at: 2025-05-13T17:13:26Z
author_association: MEMBER

PR comments:
user: login: rabarar
created_at: 2025-05-13T17:15:27Z
body: 
Change as in remove it altogether?


> On May 13, 2025, at 1:13 PM, GUVWAF ***@***.***> wrote:
> 
> 
> @GUVWAF commented on this pull request.
> 
> In examples/SendReceiveClient/SendReceiveClient.ino <https://github.com/meshtastic/Meshtastic-arduino/pull/42#discussion_r2087293890>:
> 
> > @@ -83,7 +135,7 @@ void setup() {
>    Serial.println(" mode");
>  
>    // Set to true if you want debug messages
> -  mt_set_debug(false);
> +  mt_set_debug(true);
> We'll need to change this function (also in the NodeInfoClient example) to the new macro.
> 
> —
> Reply to this email directly, view it on GitHub <https://github.com/meshtastic/Meshtastic-arduino/pull/42#pullrequestreview-2837555556>, or unsubscribe <https://github.com/notifications/unsubscribe-auth/ABB2J6HZEGJN3EQYWN76PRL26IR4ZAVCNFSM6AAAAAB4WXZMXGVHI2DSMVQWIX3LMV43YUDVNRWFEZLROVSXG5CSMV3GSZLXHMZDQMZXGU2TKNJVGY>.
> You are receiving this because you authored the thread.
> 


author_association: CONTRIBUTOR
user: login: GUVWAF
created_at: 2025-05-13T17:19:39Z
body: Yes, since `mt_set_debug()` is removed from the library.
author_association: MEMBER
user: login: rabarar
created_at: 2025-05-13T17:23:24Z
body: Just making sure! Will do…


> On May 13, 2025, at 1:20 PM, GUVWAF ***@***.***> wrote:
> 
> 
> GUVWAF
>  left a comment 
> (meshtastic/Meshtastic-arduino#42)
>  <https://github.com/meshtastic/Meshtastic-arduino/pull/42#issuecomment-2877360121>
> Yes, since mt_set_debug() is removed from the library.
> 
> —
> Reply to this email directly, view it on GitHub <https://github.com/meshtastic/Meshtastic-arduino/pull/42#issuecomment-2877360121>, or unsubscribe <https://github.com/notifications/unsubscribe-auth/ABB2J6E62PHXB4U7IY5GNK326IST7AVCNFSM6AAAAAB4WXZMXGVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMZDQNZXGM3DAMJSGE>.
> You are receiving this because you authored the thread.
> 


author_association: CONTRIBUTOR
user: login: GUVWAF
created_at: 2025-05-13T17:30:48Z
body: And then I would add 
```
// Uncomment the line below to enable debugging 
// #define MT_DEBUGGING
```

To show how it can be enabled.
author_association: MEMBER
user: login: GUVWAF
created_at: 2025-05-13T17:39:11Z
body: Sorry, but I meant in the example, as the user is not supposed to change the library.
author_association: MEMBER
user: login: rabarar
created_at: 2025-05-13T17:45:29Z
body: 
Got - but then we need to remove the UNDEF in the library as that would override it - so I’ll take that out and place the comment/#define into the examples? Yes?


> On May 13, 2025, at 1:39 PM, GUVWAF ***@***.***> wrote:
> 
> 
> GUVWAF
>  left a comment 
> (meshtastic/Meshtastic-arduino#42)
>  <https://github.com/meshtastic/Meshtastic-arduino/pull/42#issuecomment-2877431922>
> Sorry, but I meant in the example, as the user is not supposed to change the library.
> 
> —
> Reply to this email directly, view it on GitHub <https://github.com/meshtastic/Meshtastic-arduino/pull/42#issuecomment-2877431922>, or unsubscribe <https://github.com/notifications/unsubscribe-auth/ABB2J6AHQEQNGYEI2VIK4BL26IU5JAVCNFSM6AAAAAB4WXZMXGVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMZDQNZXGQZTCOJSGI>.
> You are receiving this because you authored the thread.
> 


author_association: CONTRIBUTOR
user: login: GUVWAF
created_at: 2025-05-13T17:47:50Z
body: Yes, if you then place it before `#include <Meshtastic.h>`, I believe this should work.
author_association: MEMBER
user: login: rabarar
created_at: 2025-05-13T17:56:22Z
body: Exactly - done.


> On May 13, 2025, at 1:48 PM, GUVWAF ***@***.***> wrote:
> 
> 
> GUVWAF
>  left a comment 
> (meshtastic/Meshtastic-arduino#42)
>  <https://github.com/meshtastic/Meshtastic-arduino/pull/42#issuecomment-2877454253>
> Yes, if you then place it before #include <Meshtastic.h>, I believe this should work.
> 
> —
> Reply to this email directly, view it on GitHub <https://github.com/meshtastic/Meshtastic-arduino/pull/42#issuecomment-2877454253>, or unsubscribe <https://github.com/notifications/unsubscribe-auth/ABB2J6GKPNEHIB5JZF2Q3J326IV5ZAVCNFSM6AAAAAB4WXZMXGVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMZDQNZXGQ2TIMRVGM>.
> You are receiving this because you authored the thread.
> 


author_association: CONTRIBUTOR
user: login: rabarar
created_at: 2025-05-13T18:07:30Z
body: ￼


> On May 13, 2025, at 2:03 PM, GUVWAF ***@***.***> wrote:
> 
> 
> @GUVWAF approved this pull request.
> 
> —
> Reply to this email directly, view it on GitHub <https://github.com/meshtastic/Meshtastic-arduino/pull/42#pullrequestreview-2837688545>, or unsubscribe <https://github.com/notifications/unsubscribe-auth/ABB2J6AOWIRKXWWFUPTV2SD26IXX7AVCNFSM6AAAAAB4WXZMXGVHI2DSMVQWIX3LMV43YUDVNRWFEZLROVSXG5CSMV3GSZLXHMZDQMZXGY4DQNJUGU>.
> You are receiving this because you authored the thread.
> 


author_association: CONTRIBUTOR