syntax = "proto3"; package meshtastic; /* trunk-ignore(buf-lint/COMPILE) */ import "meshtastic/channel.proto"; import "meshtastic/config.proto"; import "meshtastic/localonly.proto"; import "meshtastic/mesh.proto"; import "meshtastic/telemetry.proto"; import "nanopb.proto"; option csharp_namespace = "Meshtastic.Protobufs"; option go_package = "github.com/meshtastic/go/generated"; option java_outer_classname = "DeviceOnly"; option java_package = "org.meshtastic.proto"; option swift_prefix = ""; option (nanopb_fileopt).include = ""; /* * Position with static location information only for NodeDBLite */ message PositionLite { /* * The new preferred location encoding, multiply by 1e-7 to get degrees * in floating point */ sfixed32 latitude_i = 1; /* * TODO: REPLACE */ sfixed32 longitude_i = 2; /* * In meters above MSL (but see issue #359) */ int32 altitude = 3; /* * This is usually not sent over the mesh (to save space), but it is sent * from the phone so that the local device can set its RTC If it is sent over * the mesh (because there are devices on the mesh without GPS), it will only * be sent by devices which has a hardware GPS clock. * seconds since 1970 */ fixed32 time = 4; /* * TODO: REPLACE */ Position.LocSource location_source = 5; /* * Indicates the bits of precision set by the sending node */ uint32 precision_bits = 6; } message UserLite { /* * This is the addr of the radio. */ bytes macaddr = 1 [deprecated = true]; /* * A full name for this user, i.e. "Kevin Hester" */ string long_name = 2; /* * A VERY short name, ideally two characters. * Suitable for a tiny OLED screen */ string short_name = 3; /* * TBEAM, HELTEC, etc... * Starting in 1.2.11 moved to hw_model enum in the NodeInfo object. * Apps will still need the string here for older builds * (so OTA update can find the right image), but if the enum is available it will be used instead. */ HardwareModel hw_model = 4; /* * In some regions Ham radio operators have different bandwidth limitations than others. * If this user is a licensed operator, set this flag. * Also, "long_name" should be their licence number. */ bool is_licensed = 5; /* * Indicates that the user's role in the mesh */ Config.DeviceConfig.Role role = 6; /* * The public key of the user's device. * This is sent out to other nodes on the mesh to allow them to compute a shared secret key. */ bytes public_key = 7; /* * Whether or not the node can be messaged */ optional bool is_unmessagable = 9; } message NodeInfoLite { /* * The node number */ uint32 num = 1; // Tag 2 was UserLite user; flattened into tags 14..18 (presence via // NODEINFO_BITFIELD_HAS_USER). // Tag 3 was PositionLite position; moved to NodeDatabase.positions. reserved 2, 3; reserved "user", "position"; /* * In-memory SNR of the last received message in dB. Not serialised directly: * always zeroed before encode; persisted as snr_q4 = 19 below. */ float snr = 4; /* * Set to indicate the last time we received a packet from this node */ fixed32 last_heard = 5; // Tag 6 was DeviceMetrics device_metrics; moved to NodeDatabase.telemetry. reserved 6; reserved "device_metrics"; /* * local channel index we heard that node on. Only populated if its not the default channel. */ uint32 channel = 7; // Tags 8/10/11 were via_mqtt/is_favorite/is_ignored bools; packed into bitfield. reserved 8, 10, 11; reserved "via_mqtt", "is_favorite", "is_ignored"; /* * Number of hops away from us this node is (0 if direct neighbor) */ optional uint32 hops_away = 9; /* * Last byte of the node number of the node that should be used as the next hop to reach this node. */ uint32 next_hop = 12; /* * Bitfield for storing booleans. See NODEINFO_BITFIELD_* in src/mesh/NodeDB.h. */ uint32 bitfield = 13; // Flattened user fields (formerly UserLite). macaddr dropped (deprecated 1.2.11). /* * A full name for this user, i.e. "Kevin Hester". */ string long_name = 14; /* * A VERY short name, ideally two characters or an emoji. * Suitable for a tiny OLED screen. */ string short_name = 15; /* * Hardware model the user's device is running. */ HardwareModel hw_model = 16; /* * The user's role in the mesh. */ Config.DeviceConfig.Role role = 17; /* * The public key of the user's device, for PKI-based encrypted DMs. */ bytes public_key = 18; /* * Q4-encoded SNR: dB × 4, sint32 zigzag. Matches RouteDiscovery convention. * Encode: snr_q4 = (int32_t)(snr * 4.0f). Decode: snr = snr_q4 / 4.0f. * float snr is always zeroed on disk; this field carries all persisted SNR. */ sint32 snr_q4 = 19; } /* * This message is never sent over the wire, but it is used for serializing DB * state to flash in the device code * FIXME, since we write this each time we enter deep sleep (and have infinite * flash) it would be better to use some sort of append only data structure for * the receive queue and use the preferences store for the other stuff */ message DeviceState { /* * Read only settings/info about this node */ MyNodeInfo my_node = 2; /* * My owner info */ User owner = 3; /* * Received packets saved for delivery to the phone */ repeated MeshPacket receive_queue = 5; /* * A version integer used to invalidate old save files when we make * incompatible changes This integer is set at build time and is private to * NodeDB.cpp in the device code. */ uint32 version = 8; /* * We keep the last received text message (only) stored in the device flash, * so we can show it on the screen. * Might be null */ MeshPacket rx_text_message = 7; /* * Used only during development. * Indicates developer is testing and changes should never be saved to flash. * Deprecated in 2.3.1 */ bool no_save = 9 [deprecated = true]; /* * Previously used to manage GPS factory resets. * Deprecated in 2.5.23 */ bool did_gps_reset = 11 [deprecated = true]; /* * We keep the last received waypoint stored in the device flash, * so we can show it on the screen. * Might be null */ MeshPacket rx_waypoint = 12; /* * The mesh's nodes with their available gpio pins for RemoteHardware module */ repeated NodeRemoteHardwarePin node_remote_hardware_pins = 13; } // Satellite per-node entries; stored alongside the slim NodeInfoLite so nodes // that never report don't pay the embedded cost. message NodePositionEntry { uint32 num = 1; PositionLite position = 2; } message NodeTelemetryEntry { uint32 num = 1; DeviceMetrics device_metrics = 2; } message NodeEnvironmentEntry { uint32 num = 1; EnvironmentMetrics environment_metrics = 2; } message NodeStatusEntry { uint32 num = 1; StatusMessage status = 2; } message NodeDatabase { /* * A version integer used to invalidate old save files when we make * incompatible changes This integer is set at build time and is private to * NodeDB.cpp in the device code. */ uint32 version = 1; /* * New lite version of NodeDB to decrease memory footprint */ repeated NodeInfoLite nodes = 2 [(nanopb).callback_datatype = "std::vector"]; // Per-NodeNum satellite arrays. Constrained platforms (e.g. STM32WL) omit // these via MESHTASTIC_EXCLUDE_*DB build flags. repeated NodePositionEntry positions = 3 [(nanopb).callback_datatype = "std::vector"]; repeated NodeTelemetryEntry telemetry = 4 [(nanopb).callback_datatype = "std::vector"]; repeated NodeStatusEntry status = 5 [(nanopb).callback_datatype = "std::vector"]; repeated NodeEnvironmentEntry environment = 6 [(nanopb).callback_datatype = "std::vector"]; } /* * The on-disk saved channels */ message ChannelFile { /* * The channels our node knows about */ repeated Channel channels = 1; /* * A version integer used to invalidate old save files when we make * incompatible changes This integer is set at build time and is private to * NodeDB.cpp in the device code. */ uint32 version = 2; } /* * The on-disk backup of the node's preferences */ message BackupPreferences { /* * The version of the backup */ uint32 version = 1; /* * The timestamp of the backup (if node has time) */ fixed32 timestamp = 2; /* * The node's configuration */ LocalConfig config = 3; /* * The node's module configuration */ LocalModuleConfig module_config = 4; /* * The node's channels */ ChannelFile channels = 5; /* * The node's user (owner) information */ User owner = 6; }