[RTTY] Simplified transmission encoding configuration

pull/13/head
jgromes 2018-10-02 20:46:52 +02:00
rodzic 8562b7a71e
commit a13b4f9537
4 zmienionych plików z 80 dodań i 79 usunięć

Wyświetl plik

@ -48,9 +48,9 @@ void setup() {
// low frequency: 434.0 MHz
// frequency shift: 183 Hz
// baud rate: 45 baud
// data bits: 8 (ASCII encoding)
// encoding: ASCII (7-bit)
// stop bits: 1
state = rtty.begin(434, 183, 45, 8);
state = rtty.begin(434, 183, 45);
if(state == ERR_NONE) {
Serial.println(F("success!"));
} else {
@ -58,6 +58,17 @@ void setup() {
Serial.println(state);
while(true);
}
/*
// KiteLib also provides ITA2 ("Baudot") encoding support
rtty.begin(434, 183, 45, ITA2);
// All transmissions in loop() (strings and numbers)
// will now be encoded using ITA2 code
// ASCII characters that do not have ITA2 euqivalent
// will be sent as NUL (including lower case letters!)
*/
}
void loop() {
@ -73,8 +84,8 @@ void loop() {
String aStr = "Arduino String";
rtty.println(aStr);
// character array (C-string)
rtty.println("C-string");
// character array (C-String)
rtty.println("C-String");
// character
rtty.println('c');
@ -91,35 +102,6 @@ void loop() {
// floating point number
float f = -3.1415;
rtty.println(f, 3);
/*
// KiteLib also provides ITA2 ("Baudot") code support
// To enable ITA2 encoding, set RTTY client
// to 5 data bits
rtty.begin(434, 183, 45, 5);
// send synchronization string ("RYRY..." corresponds
// to binary 01010101010101010101... in ITA2 encoding)
rtty.println("RYRYRYRY");
// send ITA2-encoded string (all ASCII characters
// that do not have ITA2 equivalent will be replaced
// with NUL
rtty.println("HELLO WORLD!");
String aStr = "ARDUINO STRING";
rtty.println(aStr);
// character array (C-string)
rtty.println("C-STRING");
// character
rtty.println('C');
// all numbers can also be sent using ITA2
float f = -3.1415;
rtty.println(f, 3);
*/
// turn transmitter off
fsk.standby();

Wyświetl plik

@ -80,7 +80,6 @@
#define ERR_INVALID_PREAMBLE_LENGTH -18
#define ERR_INVALID_GAIN -19
#define ERR_WRONG_MODEM -20
#define ERR_INVALID_RTTY_SHIFT -21
// RF69-specific status codes
#define ERR_INVALID_BIT_RATE -101
@ -112,4 +111,8 @@
#define ERR_FRAME_INCORRECT_CHECKSUM -303
#define ERR_FRAME_UNEXPECTED_ID -304
// RTTY status codes
#define ERR_INVALID_RTTY_SHIFT -401
#define ERR_UNSUPPORTED_ENCODING -402
#endif

Wyświetl plik

@ -1,22 +1,22 @@
#include "RTTY.h"
ITA2::ITA2(char c) {
ITA2String::ITA2String(char c) {
_len = 1;
_str = new char[1];
_str[0] = c;
}
ITA2::ITA2(const char* str) {
ITA2String::ITA2String(const char* str) {
_len = strlen(str);
_str = new char[_len];
strcpy(_str, str);
}
ITA2::~ITA2() {
ITA2String::~ITA2String() {
delete[] _str;
}
size_t ITA2::length() {
size_t ITA2String::length() {
// length returned by this method is different than the length of ASCII-encoded _str
// ITA2-encoded string length varies based on how many number and characters the string contains
size_t length = 0;
@ -35,7 +35,7 @@ size_t ITA2::length() {
return(length);
}
uint8_t* ITA2::byteArr() {
uint8_t* ITA2String::byteArr() {
// create temporary array 3x the string length (figures may be 3 bytes)
uint8_t* temp = new uint8_t[_len*3];
@ -60,7 +60,7 @@ uint8_t* ITA2::byteArr() {
return(arr);
}
uint16_t ITA2::getBits(char c) {
uint16_t ITA2String::getBits(char c) {
// search ITA2 table
uint16_t code = 0x0000;
for(uint8_t i = 0; i < ITA2_LENGTH; i++) {
@ -82,7 +82,7 @@ RTTYClient::RTTYClient(PhysicalLayer* phy) {
_phy = phy;
}
int16_t RTTYClient::begin(float base, uint16_t shift, uint16_t rate, uint8_t dataBits, uint8_t stopBits) {
int16_t RTTYClient::begin(float base, uint16_t shift, uint16_t rate, uint8_t encoding, uint8_t stopBits) {
// check supplied values
if(shift % 61 != 0) {
return(ERR_INVALID_RTTY_SHIFT);
@ -90,9 +90,23 @@ int16_t RTTYClient::begin(float base, uint16_t shift, uint16_t rate, uint8_t dat
// save configuration
_shift = shift / 61;
_dataBits = dataBits;
_encoding = encoding;
_stopBits = stopBits;
switch(encoding) {
case ASCII:
_dataBits = 7;
break;
case ASCII_EXTENDED:
_dataBits = 8;
break;
case ITA2:
_dataBits = 5;
break;
default:
return(ERR_UNSUPPORTED_ENCODING);
}
// calculate duration of 1 bit
_bitDuration = (uint32_t)1000000/rate;
@ -145,7 +159,7 @@ size_t RTTYClient::write(uint8_t b) {
return(1);
}
size_t RTTYClient::print(ITA2& ita2) {
size_t RTTYClient::print(ITA2String& ita2) {
uint8_t* arr = ita2.byteArr();
size_t n = RTTYClient::write(arr, ita2.length());
delete[] arr;
@ -154,10 +168,10 @@ size_t RTTYClient::print(ITA2& ita2) {
size_t RTTYClient::print(const String& str) {
size_t n = 0;
if(_dataBits == 5) {
ITA2 ita2 = str.c_str();
if(_encoding == ITA2) {
ITA2String ita2 = str.c_str();
n = RTTYClient::print(ita2);
} else {
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
n = RTTYClient::write((uint8_t*)str.c_str(), str.length());
}
return(n);
@ -165,10 +179,10 @@ size_t RTTYClient::print(const String& str) {
size_t RTTYClient::print(const char str[]) {
size_t n = 0;
if(_dataBits == 5) {
ITA2 ita2 = str;
if(_encoding == ITA2) {
ITA2String ita2 = str;
n = RTTYClient::print(ita2);
} else {
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
n = RTTYClient::write((uint8_t*)str, strlen(str));
}
return(n);
@ -176,10 +190,10 @@ size_t RTTYClient::print(const char str[]) {
size_t RTTYClient::print(char c) {
size_t n = 0;
if(_dataBits == 5) {
ITA2 ita2 = c;
if(_encoding == ITA2) {
ITA2String ita2 = c;
n = RTTYClient::print(ita2);
} else {
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
n = RTTYClient::write(c);
}
return(n);
@ -226,18 +240,16 @@ size_t RTTYClient::print(double n, int digits) {
size_t RTTYClient::println(void) {
size_t n = 0;
if(_dataBits == 5) {
// use ITA2 line
ITA2 lf = "\r\n";
if(_encoding == ITA2) {
ITA2String lf = "\r\n";
n = RTTYClient::print(lf);
} else {
// use ASCII line
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
n = RTTYClient::write("\r\n");
}
return(n);
}
size_t RTTYClient::println(ITA2& ita2) {
size_t RTTYClient::println(ITA2String& ita2) {
size_t n = RTTYClient::print(ita2);
n += RTTYClient::println();
return(n);
@ -327,14 +339,12 @@ size_t RTTYClient::printNumber(unsigned long n, uint8_t base) {
} while(n);
size_t l = 0;
if(_dataBits == 5) {
// use ITA2 encoding
ITA2 ita2 = str;
if(_encoding == ITA2) {
ITA2String ita2 = str;
uint8_t* arr = ita2.byteArr();
l = RTTYClient::write(arr, ita2.length());
delete[] arr;
} else {
// use ASCII encoding
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
l = RTTYClient::write(str);
}
@ -351,25 +361,25 @@ size_t RTTYClient::printFloat(double number, uint8_t digits) {
if (number <-4294967040.0) strcpy(code, "ovf"); // constant determined empirically
if(code[0] != 0x00) {
if(_dataBits == 5) {
ITA2 ita2 = code;
if(_encoding == ITA2) {
ITA2String ita2 = code;
uint8_t* arr = ita2.byteArr();
n = RTTYClient::write(arr, ita2.length());
delete[] arr;
return(n);
} else {
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
return(RTTYClient::write(code));
}
}
// Handle negative numbers
if (number < 0.0) {
if(_dataBits == 5) {
ITA2 ita2 = "-";
if(_encoding == ITA2) {
ITA2String ita2 = "-";
uint8_t* arr = ita2.byteArr();
n += RTTYClient::write(arr, ita2.length());
delete[] arr;
} else {
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
n += RTTYClient::print('-');
}
number = -number;
@ -389,12 +399,12 @@ size_t RTTYClient::printFloat(double number, uint8_t digits) {
// Print the decimal point, but only if there are digits beyond
if(digits > 0) {
if(_dataBits == 5) {
ITA2 ita2 = ".";
if(_encoding == ITA2) {
ITA2String ita2 = ".";
uint8_t* arr = ita2.byteArr();
n += RTTYClient::write(arr, ita2.length());
delete[] arr;
} else {
} else if((_encoding == ASCII) || (_encoding == ASCII_EXTENDED)) {
n += RTTYClient::print('.');
}
}

Wyświetl plik

@ -16,11 +16,11 @@ const char ITA2Table[ITA2_LENGTH][2] = {{'\0', '\0'}, {'E', '3'}, {'\n', '\n'},
{'T', '5'}, {'Z', '+'}, {'L', ')'}, {'W', '2'}, {'H', 0x7F}, {'Y', '6'}, {'P', '0'}, {'Q', '1'},
{'O', '9'}, {'B', '?'}, {'G', '&'}, {0x7F, 0x7F}, {'M', '.'}, {'X', '/'}, {'V', ';'}, {0x7F, 0x7F}};
class ITA2 {
class ITA2String {
public:
ITA2(char c);
ITA2(const char* str);
~ITA2();
ITA2String(char c);
ITA2String(const char* str);
~ITA2String();
size_t length();
uint8_t* byteArr();
@ -32,18 +32,23 @@ class ITA2 {
uint16_t getBits(char c);
};
// supported ancoding schemes
#define ASCII 0
#define ASCII_EXTENDED 1
#define ITA2 2
class RTTYClient {
public:
RTTYClient(PhysicalLayer* phy);
// basic methods
int16_t begin(float base, uint16_t shift, uint16_t rate, uint8_t dataBits = 8, uint8_t stopBits = 1);
int16_t begin(float base, uint16_t shift, uint16_t rate, uint8_t encoding = ASCII, uint8_t stopBits = 1);
void idle();
size_t write(const char* str);
size_t write(uint8_t* buff, size_t len);
size_t write(uint8_t b);
size_t print(ITA2 &);
size_t print(ITA2String &);
size_t print(const String &);
size_t print(const char[]);
size_t print(char);
@ -55,7 +60,7 @@ class RTTYClient {
size_t print(double, int = 2);
size_t println(void);
size_t println(ITA2 &);
size_t println(ITA2String &);
size_t println(const String &s);
size_t println(const char[]);
size_t println(char);
@ -69,6 +74,7 @@ class RTTYClient {
private:
PhysicalLayer* _phy;
uint8_t _encoding;
uint32_t _base;
uint16_t _shift;
uint16_t _bitDuration;