mirror of
https://github.com/meshcore-dev/MeshCore.git
synced 2026-03-30 12:45:45 +00:00
* companion radio: new CMD_SHARE_CONTACT
* room server: push notify loop interval changed to 2 secs
This commit is contained in:
@@ -107,6 +107,7 @@ static uint32_t _atoi(const char* sp) {
|
||||
#define CMD_RESET_PATH 13
|
||||
#define CMD_SET_ADVERT_LATLON 14
|
||||
#define CMD_REMOVE_CONTACT 15
|
||||
#define CMD_SHARE_CONTACT 16
|
||||
|
||||
#define RESP_CODE_OK 0
|
||||
#define RESP_CODE_ERR 1
|
||||
@@ -229,6 +230,49 @@ class MyMesh : public BaseChatMesh {
|
||||
}
|
||||
}
|
||||
|
||||
int getBlobByKey(const uint8_t key[], int key_len, uint8_t dest_buf[]) override {
|
||||
char path[64];
|
||||
char fname[18];
|
||||
|
||||
if (key_len > 8) key_len = 8; // just use first 8 bytes (prefix)
|
||||
mesh::Utils::toHex(fname, key, key_len);
|
||||
sprintf(path, "/bl/%s", fname);
|
||||
|
||||
if (_fs->exists(path)) {
|
||||
File f = _fs->open(path);
|
||||
if (f) {
|
||||
int len = f.read(dest_buf, 255); // currently MAX 255 byte blob len supported!!
|
||||
f.close();
|
||||
return len;
|
||||
}
|
||||
}
|
||||
return 0; // not found
|
||||
}
|
||||
|
||||
bool putBlobByKey(const uint8_t key[], int key_len, const uint8_t src_buf[], int len) override {
|
||||
char path[64];
|
||||
char fname[18];
|
||||
|
||||
if (key_len > 8) key_len = 8; // just use first 8 bytes (prefix)
|
||||
mesh::Utils::toHex(fname, key, key_len);
|
||||
sprintf(path, "/bl/%s", fname);
|
||||
|
||||
#if defined(NRF52_PLATFORM)
|
||||
File f = _fs->open(path, FILE_O_WRITE);
|
||||
if (f) { f.seek(0); f.truncate(); }
|
||||
#else
|
||||
File f = _fs->open(path, "w", true);
|
||||
#endif
|
||||
if (f) {
|
||||
int n = f.write(src_buf, len);
|
||||
f.close();
|
||||
if (n == len) return true; // success!
|
||||
|
||||
_fs->remove(path); // blob was only partially written!
|
||||
}
|
||||
return false; // error
|
||||
}
|
||||
|
||||
void writeOKFrame() {
|
||||
uint8_t buf[1];
|
||||
buf[0] = RESP_CODE_OK;
|
||||
@@ -441,6 +485,9 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
// init 'blob store' support
|
||||
_fs->mkdir("/bl");
|
||||
|
||||
loadContacts();
|
||||
_public = addChannel(PUBLIC_GROUP_PSK); // pre-configure Andy's public channel
|
||||
|
||||
@@ -657,6 +704,14 @@ public:
|
||||
} else {
|
||||
writeErrFrame(); // not found, or unable to remove
|
||||
}
|
||||
} else if (cmd_frame[0] == CMD_SHARE_CONTACT) {
|
||||
uint8_t* pub_key = &cmd_frame[1];
|
||||
ContactInfo* recipient = lookupContactByPubKey(pub_key, PUB_KEY_SIZE);
|
||||
if (recipient && shareContactZeroHop(*recipient)) {
|
||||
writeOKFrame();
|
||||
} else {
|
||||
writeErrFrame(); // not found, or unable to send
|
||||
}
|
||||
} else if (cmd_frame[0] == CMD_SYNC_NEXT_MESSAGE) {
|
||||
int out_len;
|
||||
if ((out_len = getFromOfflineQueue(out_frame)) > 0) {
|
||||
|
||||
@@ -119,8 +119,8 @@ struct PostInfo {
|
||||
};
|
||||
|
||||
#define REPLY_DELAY_MILLIS 1500
|
||||
#define PUSH_NOTIFY_DELAY_MILLIS 1000
|
||||
#define SYNC_PUSH_INTERVAL 1000
|
||||
#define PUSH_NOTIFY_DELAY_MILLIS 2000
|
||||
#define SYNC_PUSH_INTERVAL 2000
|
||||
|
||||
#define PUSH_ACK_TIMEOUT_FLOOD 12000
|
||||
#define PUSH_TIMEOUT_BASE 4000
|
||||
|
||||
@@ -50,6 +50,10 @@ void BaseChatMesh::onAdvertRecv(mesh::Packet* packet, const mesh::Identity& id,
|
||||
}
|
||||
}
|
||||
|
||||
// save a copy of raw advert packet (to support "Share..." function)
|
||||
int plen = packet->writeTo(temp_buf);
|
||||
putBlobByKey(id.pub_key, PUB_KEY_SIZE, temp_buf, plen);
|
||||
|
||||
// update
|
||||
strncpy(from->name, parser.getName(), sizeof(from->name)-1);
|
||||
from->name[sizeof(from->name)-1] = 0;
|
||||
@@ -246,6 +250,18 @@ bool BaseChatMesh::sendGroupMessage(uint32_t timestamp, mesh::GroupChannel& chan
|
||||
return false;
|
||||
}
|
||||
|
||||
bool BaseChatMesh::shareContactZeroHop(const ContactInfo& contact) {
|
||||
int plen = getBlobByKey(contact.id.pub_key, PUB_KEY_SIZE, temp_buf); // retrieve last raw advert packet
|
||||
if (plen == 0) return false; // not found
|
||||
|
||||
auto packet = obtainNewPacket();
|
||||
if (packet == NULL) return false; // no Packets available
|
||||
|
||||
packet->readFrom(temp_buf, plen); // restore Packet from 'blob'
|
||||
sendZeroHop(packet);
|
||||
return true; // success
|
||||
}
|
||||
|
||||
bool BaseChatMesh::sendLogin(const ContactInfo& recipient, const char* password, uint32_t& est_timeout) {
|
||||
uint8_t shared_secret[32];
|
||||
self_id.calcSharedSecret(shared_secret, recipient.id); // TODO: cache this
|
||||
|
||||
@@ -60,6 +60,7 @@ class BaseChatMesh : public mesh::Mesh {
|
||||
mesh::GroupChannel channels[MAX_GROUP_CHANNELS];
|
||||
int num_channels;
|
||||
#endif
|
||||
uint8_t temp_buf[MAX_TRANS_UNIT];
|
||||
|
||||
mesh::Packet* composeMsgPacket(const ContactInfo& recipient, uint32_t timestamp, uint8_t attempt, const char *text, uint32_t& expected_ack);
|
||||
|
||||
@@ -85,6 +86,10 @@ protected:
|
||||
virtual void onChannelMessageRecv(const mesh::GroupChannel& channel, int in_path_len, uint32_t timestamp, const char *text) = 0;
|
||||
virtual void onContactResponse(const ContactInfo& contact, const uint8_t* data, uint8_t len) = 0;
|
||||
|
||||
// storage concepts, for sub-classes to override/implement
|
||||
virtual int getBlobByKey(const uint8_t key[], int key_len, uint8_t dest_buf[]) { return 0; } // not implemented
|
||||
virtual bool putBlobByKey(const uint8_t key[], int key_len, const uint8_t src_buf[], int len) { return false; }
|
||||
|
||||
// Mesh overrides
|
||||
void onAdvertRecv(mesh::Packet* packet, const mesh::Identity& id, uint32_t timestamp, const uint8_t* app_data, size_t app_data_len) override;
|
||||
int searchPeersByHash(const uint8_t* hash) override;
|
||||
@@ -102,6 +107,7 @@ public:
|
||||
int sendMessage(const ContactInfo& recipient, uint32_t timestamp, uint8_t attempt, const char* text, uint32_t& expected_ack, uint32_t& est_timeout);
|
||||
bool sendGroupMessage(uint32_t timestamp, mesh::GroupChannel& channel, const char* sender_name, const char* text, int text_len);
|
||||
bool sendLogin(const ContactInfo& recipient, const char* password, uint32_t& est_timeout);
|
||||
bool shareContactZeroHop(const ContactInfo& contact);
|
||||
void resetPathTo(ContactInfo& recipient);
|
||||
void scanRecentContacts(int last_n, ContactVisitor* visitor);
|
||||
ContactInfo* searchContactsByPrefix(const char* name_prefix);
|
||||
|
||||
Reference in New Issue
Block a user