Hi all,
for my 3D printing host app I need to encrypt some data while send over network, then decrypt on server side that receive over the network and send to the 3D Printer over USB.
For this purpose I've used a Raspberry PI Zero W that acts as WiFi-Serial bridge to remotely control a 3D printer.
Because I had necessity to adapt to ESP8266 and ESP32 (instead of Raspberry), I never used B4XEncryption and tried to use a sort of simple algorithm XORing all strings I send.
This worked well between my Android SmartPhone and Raspberry (B4A <-> B4J), but now that I converted the server side to run on ESP8266 (In C++ on Arduino IDE) instead of Raspberry it won't work correctly. I've found a lots of problems because different characters encoding UTF8 vs ASCII (or extended ASCII).
Some strings are decrypted good and some others are incomplete and/or not correct decrypted.
The algorithm work well from Android to Android using B4A, I even tried it on B4J and seem to work well too.
The same work well from ESP8266 to another ESP8266 or ESP32 or dencrypt/decrypt on the same sketch.
But when I try it between different platforms eg. B4A <-> ESP8266, as already explained, sometime work and sometime not.
Note that because I use XOR there are no function to Encrypt and function to Decrypt, just call the function will encrypt the string, calling it again will decrypt.
This function is pretty fast too, it encrypt/decrypt about 3.500.000 characters every second on my old Dualcore PC, but won't work between different platforms.
On ESP8266 with CPU clocked @ 160Mhz it require about 3 microseconds every character to encrypt/decrypt, so very fast too...
On B4X side I use this:
On Arduino IDE side I use this:
Note that I've used String object, but the right way will be tu use a char array. Anyway Ive used it in conjuntion with Arduino utf8ascii functions that convert UTF8 to extended ASCII by check multiple bytes.
Arduino utf8ascii
In Arduino String object (as it will be) the string length() functions return the byte length, so any 'special' charater outside ASCII code return the byte length, eg:
will return 2 and not 1. It can be from 1 to 4 bytes depending of the character.
To the B4X side I actually manage default UTF8 encode, maybe manage it with String.getBytes("ASCII") instead of String.getBytes("UTF-8") ?
But in this code I never used String.getBytes at all.... tried it with others encryption algorithms but not here in these functions.
Please guys, is there a simple way to do this?
Many thanks
for my 3D printing host app I need to encrypt some data while send over network, then decrypt on server side that receive over the network and send to the 3D Printer over USB.
For this purpose I've used a Raspberry PI Zero W that acts as WiFi-Serial bridge to remotely control a 3D printer.
Because I had necessity to adapt to ESP8266 and ESP32 (instead of Raspberry), I never used B4XEncryption and tried to use a sort of simple algorithm XORing all strings I send.
This worked well between my Android SmartPhone and Raspberry (B4A <-> B4J), but now that I converted the server side to run on ESP8266 (In C++ on Arduino IDE) instead of Raspberry it won't work correctly. I've found a lots of problems because different characters encoding UTF8 vs ASCII (or extended ASCII).
Some strings are decrypted good and some others are incomplete and/or not correct decrypted.
The algorithm work well from Android to Android using B4A, I even tried it on B4J and seem to work well too.
The same work well from ESP8266 to another ESP8266 or ESP32 or dencrypt/decrypt on the same sketch.
But when I try it between different platforms eg. B4A <-> ESP8266, as already explained, sometime work and sometime not.
Note that because I use XOR there are no function to Encrypt and function to Decrypt, just call the function will encrypt the string, calling it again will decrypt.
This function is pretty fast too, it encrypt/decrypt about 3.500.000 characters every second on my old Dualcore PC, but won't work between different platforms.
On ESP8266 with CPU clocked @ 160Mhz it require about 3 microseconds every character to encrypt/decrypt, so very fast too...
On B4X side I use this:
B4X:
Sub XorMessage (Text As String, Key As String) As String
Dim out As StringBuilder
out.Initialize
Dim msglen As Int = Text.Length
Dim keylen As Int = Key.Length
Dim n1 As Int
Dim n2 As Int
For i = 0 To msglen-1
n1 = Asc(Text.CharAt(i))
n2 = Asc(Key.CharAt(i Mod keylen))
out.Append(Chr(Bit.Xor(n1, n2)))
Next
Return out.ToString
End Sub
On Arduino IDE side I use this:
C++:
String XorMessage (String Msg, String Key) {
String tmpMsg = "";
String tmpKey = "";
if (fromUTF8) {
tmpMsg = utf8ascii (Msg);
tmpKey = utf8ascii (Key);
} else {
tmpMsg = Msg;
tmpKey = Key;
}
const unsigned int msglen = tmpMsg.length();
const unsigned int keylen = tmpKey.length();
String out = "";
for (unsigned int i = 0; i < msglen; i++) {
out += (char) (tmpMsg[i] ^ tmpKey[i % keylen]);
}
return out;
}
Arduino utf8ascii
In Arduino String object (as it will be) the string length() functions return the byte length, so any 'special' charater outside ASCII code return the byte length, eg:
C++:
String s = "è";
// This return 2 because 'è' characters is 2 bytes encoded in UTF8
Serial.println(s.length());
To the B4X side I actually manage default UTF8 encode, maybe manage it with String.getBytes("ASCII") instead of String.getBytes("UTF-8") ?
But in this code I never used String.getBytes at all.... tried it with others encryption algorithms but not here in these functions.
Please guys, is there a simple way to do this?
Many thanks
Last edited: