implement additional packet types

This commit is contained in:
liamcottle 2025-02-11 17:31:28 +13:00
parent f2e56f3924
commit 581e159f0d
4 changed files with 159 additions and 13 deletions

View file

@ -39,6 +39,27 @@ class BufferWriter {
this.writeBytes(new TextEncoder().encode(string));
}
writeCString(string, maxLength) {
// create buffer of max length
const bytes = new Uint8Array(new ArrayBuffer(maxLength));
// encode string to bytes
const encodedString = new TextEncoder().encode(string);
// copy in string until we hit the max length, or we run out of string bytes
for(var i = 0; i < maxLength && i < encodedString.length; i++){
bytes[i] = encodedString[i];
}
// ensure the last byte is always a null terminator
bytes[bytes.length - 1] = 0;
// write to buffer
this.writeBytes(bytes);
}
}
export default BufferWriter;

View file

@ -7,17 +7,17 @@ class Constants {
static CommandCodes = {
AppStart: 1, // done
SendTxtMsg: 2,
SendTxtMsg: 2, // done
SendChannelTxtMsg: 3,
GetContacts: 4, // done
GetDeviceTime: 5, // done
SetDeviceTime: 6, // done
SendSelfAdvert: 7, // done
SetAdvertName: 8, // done
AddUpdateContact: 9,
AddUpdateContact: 9, // done
SyncNextMessage: 10, // done
SetRadioParams: 11,
SetTxPower: 12,
SetRadioParams: 11, // done
SetTxPower: 12, // done
}
static ResponseCodes = {
@ -27,18 +27,25 @@ class Constants {
Contact: 3, // done
EndOfContacts: 4, // done
SelfInfo: 5, // done
Sent: 6,
Sent: 6, // done
ContactMsgRecv: 7, // done
ChannelMsgRecv: 8,
CurrTime: 9, // done
NoMoreMessages: 10,
NoMoreMessages: 10, // done
}
static PushCodes = {
Advert: 0x80,
Advert: 0x80, // done
PathUpdated: 0x81,
SendConfirmed: 0x82,
MsgWaiting: 0x83,
SendConfirmed: 0x82, // done
MsgWaiting: 0x83, // done
}
static AdvType = {
None: 0,
Chat: 1,
Repeater: 2,
Room: 3,
}
static SelfAdvertTypes = {
@ -46,6 +53,12 @@ class Constants {
Flood: 1,
}
static TxtTypes = {
Plain: 0,
CliData: 1,
SignedPlain: 2,
}
}
export default Constants;

View file

@ -81,6 +81,17 @@ class Device {
await this.sendToRadioFrame(data.toBytes());
}
async sendCommandSendTxtMsg(txtType, attempt, senderTimestamp, pubKeyPrefix, text) {
const data = new BufferWriter();
data.writeByte(Constants.CommandCodes.SendTxtMsg);
data.writeByte(txtType);
data.writeByte(attempt);
data.writeUInt32LE(senderTimestamp);
data.writeBytes(pubKeyPrefix.slice(0, 6)); // only the first 6 bytes of pubKey are sent
data.writeString(text);
await this.sendToRadioFrame(data.toBytes());
}
async sendCommandGetContacts(since) {
const data = new BufferWriter();
data.writeByte(Constants.CommandCodes.GetContacts);
@ -117,12 +128,44 @@ class Device {
await this.sendToRadioFrame(data.toBytes());
}
async sendCommandAddUpdateContact(publicKey, type, flags, outPathLen, outPath, advName, lastAdvert, advLat, advLon) {
const data = new BufferWriter();
data.writeByte(Constants.CommandCodes.AddUpdateContact);
data.writeBytes(publicKey);
data.writeByte(type);
data.writeByte(flags);
data.writeByte(outPathLen);
data.writeBytes(outPath); // 64 bytes
data.writeCString(advName, 32); // 32 bytes
data.writeUInt32LE(lastAdvert);
data.writeUInt32LE(advLat);
data.writeUInt32LE(advLon);
await this.sendToRadioFrame(data.toBytes());
}
async sendCommandSyncNextMessage() {
const data = new BufferWriter();
data.writeByte(Constants.CommandCodes.SyncNextMessage);
await this.sendToRadioFrame(data.toBytes());
}
async sendCommandSetRadioParams(radioFreq, radioBw, radioSf, radioCr) {
const data = new BufferWriter();
data.writeByte(Constants.CommandCodes.SetRadioParams);
data.writeUInt32LE(radioFreq);
data.writeUInt32LE(radioBw);
data.writeByte(radioSf);
data.writeByte(radioCr);
await this.sendToRadioFrame(data.toBytes());
}
async sendCommandSetTxPower(txPower) {
const data = new BufferWriter();
data.writeByte(Constants.CommandCodes.SetTxPower);
data.writeByte(txPower);
await this.sendToRadioFrame(data.toBytes());
}
async readLoop() {
try {
while(true){
@ -209,6 +252,8 @@ class Device {
this.onSelfInfoResponse(bufferReader);
} else if(responseCode === Constants.ResponseCodes.CurrTime){
this.onCurrTimeResponse(bufferReader);
} else if(responseCode === Constants.ResponseCodes.NoMoreMessages){
this.onNoMoreMessagesResponse(bufferReader);
} else if(responseCode === Constants.ResponseCodes.ContactMsgRecv){
this.onContactMsgRecvResponse(bufferReader);
} else if(responseCode === Constants.ResponseCodes.ContactsStart){
@ -217,8 +262,12 @@ class Device {
this.onContactResponse(bufferReader);
} else if(responseCode === Constants.ResponseCodes.EndOfContacts){
this.onEndOfContactsResponse(bufferReader);
} else if(responseCode === Constants.ResponseCodes.Sent){
this.onSentResponse(bufferReader);
} else if(responseCode === Constants.PushCodes.Advert){
this.onAdvertPush(bufferReader);
} else if(responseCode === Constants.PushCodes.SendConfirmed){
this.onSendConfirmedPush(bufferReader);
} else if(responseCode === Constants.PushCodes.MsgWaiting){
this.onMsgWaitingPush(bufferReader);
} else {
@ -233,6 +282,13 @@ class Device {
});
}
onSendConfirmedPush(bufferReader) {
console.log("onSendConfirmedPush", {
ackCode: bufferReader.readBytes(4),
roundTrip: bufferReader.readUInt32LE(),
});
}
onMsgWaitingPush(bufferReader) {
console.log("onMsgWaitingPush", {
@ -266,6 +322,12 @@ class Device {
});
}
onSentResponse(bufferReader) {
console.log("onSentResponse", {
});
}
onSelfInfoResponse(bufferReader) {
console.log("onSelfInfoResponse", {
type: bufferReader.readByte(),
@ -287,6 +349,12 @@ class Device {
});
}
onNoMoreMessagesResponse(bufferReader) {
console.log("onNoMoreMessagesResponse", {
});
}
onContactMsgRecvResponse(bufferReader) {
console.log("onContactMsgRecvResponse", {
pubKeyPrefix: bufferReader.readBytes(6),