Skip to content

Commit d9640a9

Browse files
authored
Merge pull request #117 from fdufnews/pioarduino
Added a sniff command to UART mode
2 parents 37f35ed + c4dc3df commit d9640a9

File tree

5 files changed

+143
-21
lines changed

5 files changed

+143
-21
lines changed

src/Controllers/UartController.cpp

Lines changed: 75 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@ void UartController::handleCommand(const TerminalCommand& cmd) {
5353
else if (cmd.getRoot() == "glitch") handleGlitch();
5454
else if (cmd.getRoot() == "xmodem") handleXmodem(cmd);
5555
else if (cmd.getRoot() == "swap") handleSwap();
56+
else if (cmd.getRoot() == "sniff") handleSniff();
5657
else if (cmd.getRoot() == "config") handleConfig();
5758
else handleHelp();
5859
}
@@ -997,6 +998,80 @@ void UartController::handleTrigger(const TerminalCommand& cmd) {
997998
}
998999
}
9991000

1001+
1002+
/*
1003+
sniff exchanges on a serial communication
1004+
*/
1005+
void UartController::handleSniff() {
1006+
GlobalState& state = GlobalState::getInstance();
1007+
enum source {NONE, UART1, UART2};
1008+
1009+
const unsigned long baud = state.getUartBaudRate();
1010+
const uint32_t config = state.getUartConfig();
1011+
const bool inverted = state.isUartInverted();
1012+
1013+
const uint8_t rxPin1 = state.getUartRxPin();
1014+
const uint8_t rxPin2 = state.getUartTxPin();
1015+
const int8_t noTxPin = -1;
1016+
1017+
int lastUart = NONE;
1018+
1019+
if (rxPin1 == rxPin2) {
1020+
terminalView.println("UART Sniff: RX and TX pins are identical.");
1021+
return;
1022+
}
1023+
1024+
if (state.isPinProtected(rxPin1) || state.isPinProtected(rxPin2)) {
1025+
terminalView.println("UART Sniff: protected pin.");
1026+
return;
1027+
}
1028+
1029+
terminalView.println("UART Sniff: press ENTER to stop");
1030+
1031+
UartService uart1;
1032+
UartService uart2;
1033+
1034+
uart1.configure(baud, config, rxPin1, noTxPin, inverted, &Serial1, false);
1035+
uart2.configure(baud, config, rxPin2, noTxPin, inverted, &Serial2, false);
1036+
1037+
uart1.flush();
1038+
uart2.flush();
1039+
while (uart1.available()) {uart1.read();}
1040+
while (uart2.available()) {uart2.read();}
1041+
1042+
while (true) {
1043+
char key = terminalInput.readChar();
1044+
if (key == '\r' || key == '\n') {
1045+
terminalView.println("\nUART Sniff: stopped");
1046+
break;
1047+
}
1048+
1049+
if (uart1.available() > 0) {
1050+
if (lastUart != UART1){
1051+
terminalView.print("\n\r\t[RX] ");
1052+
lastUart = UART1;
1053+
}
1054+
terminalView.print(std::string(1, uart1.read()));
1055+
}
1056+
1057+
if (uart2.available() > 0) {
1058+
if (lastUart != UART2){
1059+
terminalView.print("\n\r[TX] ");
1060+
lastUart = UART2;
1061+
}
1062+
terminalView.print(std::string(1, uart2.read()));
1063+
}
1064+
1065+
yield();
1066+
}
1067+
1068+
uart1.end();
1069+
uart2.end();
1070+
1071+
ensureConfigured();
1072+
}
1073+
1074+
10001075
/*
10011076
Ensure Config
10021077
*/

src/Controllers/UartController.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -97,6 +97,9 @@ class UartController {
9797

9898
// Handle trigger setup to send response on pattern match
9999
void handleTrigger(const TerminalCommand& cmd);
100+
101+
// sniff on a serial communication
102+
void handleSniff();
100103

101104
ITerminalView& terminalView;
102105
IDeviceView& deviceView;

src/Services/UartService.cpp

Lines changed: 62 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
#include "UartService.h"
22

3+
/*
34
void UartService::configure(unsigned long baud, uint32_t config, uint8_t rx, uint8_t tx, bool inverted) {
45
Serial1.end();
56
Serial1.begin(baud, config, rx, tx, inverted);
@@ -26,9 +27,50 @@ void UartService::configure(unsigned long baud, uint32_t config, uint8_t rx, uin
2627
buffersAllocated = true;
2728
}
2829
}
30+
*/
31+
32+
void UartService::configure(unsigned long baud,
33+
uint32_t config,
34+
uint8_t rx,
35+
uint8_t tx,
36+
bool inverted,
37+
HardwareSerial* serial,
38+
bool noBuffer) {
39+
40+
_serial = serial;
41+
42+
_serial->end();
43+
_serial->begin(baud, config, rx, tx, inverted);
44+
45+
if (noBuffer) {
46+
return;
47+
}
48+
49+
if (!buffersAllocated) {
50+
51+
edgeIntervals = (uint32_t*) heap_caps_malloc(
52+
sizeof(uint32_t) * 50,
53+
MALLOC_CAP_INTERNAL
54+
);
55+
56+
edgeCounts = (uint32_t*) heap_caps_malloc(
57+
sizeof(uint32_t) * 64,
58+
MALLOC_CAP_INTERNAL
59+
);
60+
61+
if (!edgeIntervals || !edgeCounts) {
62+
buffersAllocated = false;
63+
return;
64+
}
65+
66+
memset((void*)edgeCounts, 0, sizeof(uint32_t) * 64);
67+
68+
buffersAllocated = true;
69+
}
70+
}
2971

3072
void UartService::release() {
31-
Serial1.end();
73+
_serial->end();
3274

3375
if (buffersAllocated) {
3476
heap_caps_free((void*)edgeIntervals);
@@ -40,27 +82,27 @@ void UartService::release() {
4082
}
4183

4284
void UartService::end() {
43-
Serial1.end();
85+
_serial->end();
4486
}
4587

4688
std::string UartService::readLine() {
4789
std::string input;
4890
bool lastWasCR = false;
4991

5092
while (true) {
51-
if (!Serial1.available()) continue;
93+
if (!_serial->available()) continue;
5294

53-
char c = Serial1.read();
95+
char c = _serial->read();
5496

5597
if (c == '\r') {
5698
lastWasCR = true;
57-
Serial1.println();
99+
_serial->println();
58100
break;
59101
}
60102

61103
if (c == '\n') {
62104
if (!lastWasCR) {
63-
Serial1.println();
105+
_serial->println();
64106
break;
65107
}
66108
continue;
@@ -69,11 +111,11 @@ std::string UartService::readLine() {
69111
if (c == '\b' || c == 127) {
70112
if (!input.empty()) {
71113
input.pop_back();
72-
Serial1.print("\b \b");
114+
_serial->print("\b \b");
73115
}
74116
} else {
75117
input += c;
76-
Serial1.print(c);
118+
_serial->print(c);
77119
lastWasCR = false;
78120
}
79121
}
@@ -82,27 +124,27 @@ std::string UartService::readLine() {
82124
}
83125

84126
void UartService::print(const std::string& msg) {
85-
Serial1.print(msg.c_str());
127+
_serial->print(msg.c_str());
86128
}
87129

88130
void UartService::println(const std::string& msg) {
89-
Serial1.println(msg.c_str());
131+
_serial->println(msg.c_str());
90132
}
91133

92134
bool UartService::available() const {
93-
return Serial1.available();
135+
return _serial->available();
94136
}
95137

96138
char UartService::read() {
97-
return Serial1.read();
139+
return _serial->read();
98140
}
99141

100142
void UartService::write(char c) {
101-
Serial1.write(c);
143+
_serial->write(c);
102144
}
103145

104146
void UartService::write(const std::string& str) {
105-
Serial1.write(reinterpret_cast<const uint8_t*>(str.c_str()), str.length());
147+
_serial->write(reinterpret_cast<const uint8_t*>(str.c_str()), str.length());
106148
}
107149

108150
std::string UartService::executeByteCode(const std::vector<ByteCode>& bytecodes) {
@@ -115,15 +157,15 @@ std::string UartService::executeByteCode(const std::vector<ByteCode>& bytecodes)
115157
switch (code.getCommand()) {
116158
case ByteCodeEnum::Write:
117159
for (uint32_t i = 0; i < code.getRepeat(); ++i) {
118-
Serial1.write(code.getData());
160+
_serial->write(code.getData());
119161
}
120162
break;
121163

122164
case ByteCodeEnum::Read:
123165
start = millis();
124166
while (received < code.getRepeat() && (millis() - start < timeout)) {
125-
if (Serial1.available()) {
126-
char c = Serial1.read();
167+
if (_serial->available()) {
168+
char c = _serial->read();
127169
result += c;
128170
++received;
129171
} else {
@@ -149,11 +191,11 @@ std::string UartService::executeByteCode(const std::vector<ByteCode>& bytecodes)
149191
}
150192

151193
void UartService::switchBaudrate(unsigned long newBaud) {
152-
Serial1.updateBaudRate(newBaud);
194+
_serial->updateBaudRate(newBaud);
153195
}
154196

155197
void UartService::flush() {
156-
Serial.flush();
198+
_serial->flush();
157199
}
158200

159201
void UartService::clearUartBuffer() {
@@ -213,7 +255,7 @@ void UartService::setXmodemSendHandler(void (*handler)(void*, size_t, byte*, siz
213255
}
214256

215257
void UartService::initXmodem() {
216-
xmodem.begin(Serial1, xmodemProtocol);
258+
xmodem.begin(*_serial, xmodemProtocol);
217259
xmodem.setDataSize(xmodemBlockSize);
218260
xmodem.setIdSize(xmodemIdSize);
219261
}

src/Services/UartService.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ class UartService {
2323
uint32_t approxBaud;
2424
};
2525

26-
void configure(unsigned long baud, uint32_t config, uint8_t rx, uint8_t tx, bool inverted);
26+
void configure(unsigned long baud, uint32_t config, uint8_t rx, uint8_t tx, bool inverted, HardwareSerial* serial = &Serial1, bool noBuffer = false);
2727
void release();
2828
void print(const std::string& msg);
2929
void println(const std::string& msg);
@@ -95,4 +95,5 @@ class UartService {
9595
};
9696

9797
static constexpr size_t kBaudRatesCount = sizeof(kBaudRates) / sizeof(kBaudRates[0]);
98+
HardwareSerial* _serial;
9899
};

src/Shells/HelpShell.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -156,6 +156,7 @@ void HelpShell::cmdUart() {
156156
"xmodem <recv> <path> - Receive file via XMODEM",
157157
"config - Configure settings",
158158
"swap - Swap RX and TX GPIOs",
159+
"sniff - View traffic on an UART",
159160
"['Hello'] [r:64]... - Instruction syntax"
160161
};
161162
printLines(lines, (int)(sizeof(lines) / sizeof(lines[0])));

0 commit comments

Comments
 (0)