Compare commits

..

3 Commits

Author SHA1 Message Date
jLynx d1a2318fe4 Merge pull request #3106 from portapack-mayhem/next
v2.4.0
2026-03-24 22:54:24 +13:00
gullradriel 93775129cb Merge pull request #2896 from portapack-mayhem/next
Christmas stable merge
2025-12-21 12:00:18 +01:00
jLynx fe9448f149 Merge pull request #2859 from portapack-mayhem/next
V2.3.1
2025-11-08 10:35:16 +13:00
6 changed files with 61 additions and 124 deletions
+1 -17
View File
@@ -1,17 +1 @@
# Security Policy
## Scope and Threat Model
This repository hosts the codebase for an embedded system designed for security research. Because the system operates primarily offline, traditional network-based vulnerabilities are generally not applicable. However, we still welcome and review security reports concerning the code within this repository.
## Reporting a Vulnerability
If you discover a vulnerability within this tool itself, please submit a report. Please be aware that the maintainers do not promise assistance with obtaining CVE IDs or managing formal security advisories.
## Out of Scope
* **Vulnerabilities found *using* this tool:** Please do not submit reports here for vulnerabilities you have discovered in other systems or targets using this tool. This channel is strictly for reporting vulnerabilities found *in* the tool itself.
* **Other Repositories:** For security issues concerning related tools, such as MayhemHub, please submit your reports directly to their respective repositories.
## Research Attribution
If you utilize this tool to successfully discover vulnerabilities in external systems, we would greatly appreciate it if you credit or mention our project in your published research or write-ups.
## Legal and Security Disclaimer
For comprehensive guidelines regarding the legal and secure usage of this tool, as well as our full liability disclaimer, please refer to: [Intended-Use-and-Legality](https://github.com/portapack-mayhem/mayhem-firmware/wiki/). Users are expected to comply with all applicable laws and regulations when using this software and/or hardware.
Please check [Intended-Use-and-Legality](https://github.com/portapack-mayhem/mayhem-firmware/wiki/)
@@ -419,10 +419,10 @@ void AnalogAudioView::on_baseband_bandwidth_changed(uint32_t bandwidth_hz) {
}
void AnalogAudioView::on_modulation_changed(ReceiverModel::Mode modulation) {
waterfall.stop();
baseband::spectrum_streaming_stop();
update_modulation(modulation);
on_show_options_modulation();
waterfall.start();
baseband::spectrum_streaming_start();
}
void AnalogAudioView::remove_options_widget() {
@@ -27,9 +27,6 @@ MorseRadiotxView::MorseRadiotxView(ui::NavigationView& nav)
&chk_trans,
&bandwidth,
&chk_callsgn,
&chk_loop,
&wait_time,
&progressbar,
&txt_last,
&console_text,
&btn_clear,
@@ -72,7 +69,6 @@ MorseRadiotxView::MorseRadiotxView(ui::NavigationView& nav)
options_mode.set_selected_index(current_mode, true);
tone_.set_value(tone, true);
wpm_.set_value(wpm, true);
wait_time.set_value(1, true);
bandwidth.set_value(band, true);
btn_ptt.on_select = [this](Button&) {
@@ -160,14 +156,6 @@ MorseRadiotxView::MorseRadiotxView(ui::NavigationView& nav)
transmitter_model.set_target_frequency(f);
};
};
chk_trans.on_select = [this](Checkbox&, bool v) {
if (v) chk_loop.set_value(false);
};
chk_loop.on_select = [this](Checkbox&, bool v) {
if (v) chk_trans.set_value(false);
};
}
MorseRadiotxView::~MorseRadiotxView() {
@@ -209,15 +197,19 @@ MorseRadiotxView::MorseTimings MorseRadiotxView::calculate_morse_timings(uint32_
void MorseRadiotxView::transmit_morse_message() {
std::string full_message = "";
// cal sign
if (chk_callsgn.value() && !call_sign.empty()) {
full_message = call_sign;
if (!chk_trans.value() && !msg_buffer.empty()) {
full_message += " " + msg_buffer;
}
} else {
if (!chk_trans.value()) full_message = msg_buffer;
}
if (chk_trans.value()) {
if (full_message.empty() && !chk_trans.value()) {
ptt_button_visibility(false);
return;
} else {
full_message = msg_buffer;
if (chk_callsgn.value() && !call_sign.empty()) { // call sign
full_message += " " + call_sign;
}
}
// enable transmit
@@ -227,63 +219,46 @@ void MorseRadiotxView::transmit_morse_message() {
ui_toggle();
}
uint8_t loop_seconds = static_cast<uint8_t>(wait_time.value());
progressbar.set_max(loop_seconds * 2);
do {
for (size_t i = 0; i < full_message.length(); i++) {
if (chThdShouldTerminate()) break;
char c = full_message[i];
std::string s_char(1, c);
// space
if (c == ' ') {
console_text.write(" ");
chThdSleepMilliseconds(current_timings.word_gap);
continue;
}
const char* pattern = morse_decoder_.get_morse_pattern(c);
if (pattern != nullptr) {
txt_last.set(pattern);
// write blue char to console
console_text.write(STR_COLOR_BLUE + s_char);
// Morze (dih/dah) send
for (int j = 0; pattern[j] != '\0'; j++) {
baseband::set_morsetx_key(true);
if (pattern[j] == '.') {
chThdSleepMilliseconds(current_timings.dot_ms);
} else if (pattern[j] == '-') {
chThdSleepMilliseconds(current_timings.dash_ms);
}
if (chThdShouldTerminate()) break;
// pause between signs
baseband::set_morsetx_key(false);
chThdSleepMilliseconds(current_timings.symbol_gap);
}
if (chThdShouldTerminate()) break;
if (current_timings.char_gap > current_timings.symbol_gap) {
chThdSleepMilliseconds(current_timings.char_gap - current_timings.symbol_gap);
}
}
}
for (size_t i = 0; i < full_message.length(); i++) {
if (chThdShouldTerminate()) break;
if (chk_loop.value()) {
char c = full_message[i];
std::string s_char(1, c);
// space
if (c == ' ') {
console_text.write(" ");
for (uint8_t s = 0; s < (loop_seconds * 2); s++) {
if (chThdShouldTerminate()) break;
progressbar.set_value(s + 1);
if (!chk_loop.value()) break;
chThdSleepMilliseconds(500);
}
progressbar.set_value(0);
chThdSleepMilliseconds(current_timings.word_gap);
continue;
}
if (!chk_loop.value()) break;
} while (chk_loop.value() && !chThdShouldTerminate());
const char* pattern = morse_decoder_.get_morse_pattern(c);
if (pattern != nullptr) {
txt_last.set(pattern);
// write blue char to console
console_text.write(STR_COLOR_BLUE + s_char);
// Morze (dih/dah) send
for (int j = 0; pattern[j] != '\0'; j++) {
baseband::set_morsetx_key(true);
if (pattern[j] == '.') {
chThdSleepMilliseconds(current_timings.dot_ms);
} else if (pattern[j] == '-') {
chThdSleepMilliseconds(current_timings.dash_ms);
}
if (chThdShouldTerminate()) break;
// pause between signs
baseband::set_morsetx_key(false);
chThdSleepMilliseconds(current_timings.symbol_gap);
}
if (chThdShouldTerminate()) break;
if (current_timings.char_gap > current_timings.symbol_gap) {
chThdSleepMilliseconds(current_timings.char_gap - current_timings.symbol_gap);
}
}
}
if (chk_trans.value()) ptt_button_visibility(false);
baseband::set_morsetx_key(false);
@@ -381,17 +356,13 @@ void MorseRadiotxView::ui_toggle() {
wpm_.set_style(Theme::getInstance()->fg_dark);
wpm_.set_focusable(false);
btn_message.set_style(Theme::getInstance()->fg_dark);
btn_message.set_focusable(false);
btn_calls.set_style(Theme::getInstance()->fg_dark);
btn_calls.set_focusable(false);
chk_trans.set_style(Theme::getInstance()->fg_dark);
chk_trans.set_focusable(false);
chk_callsgn.set_style(Theme::getInstance()->fg_dark);
chk_callsgn.set_focusable(false);
wait_time.set_style(Theme::getInstance()->fg_dark);
wait_time.set_focusable(false);
bandwidth.set_style(Theme::getInstance()->fg_dark);
bandwidth.set_focusable(false);
chk_callsgn.set_style(Theme::getInstance()->fg_dark);
chk_callsgn.set_focusable(false);
} else {
options_mode.set_style(Theme::getInstance()->bg_darker);
@@ -399,15 +370,11 @@ void MorseRadiotxView::ui_toggle() {
wpm_.set_style(Theme::getInstance()->bg_darker);
wpm_.set_focusable(true);
btn_message.set_style(Theme::getInstance()->bg_darker);
btn_message.set_focusable(true);
btn_calls.set_style(Theme::getInstance()->bg_darker);
btn_calls.set_focusable(true);
chk_trans.set_style(Theme::getInstance()->bg_darker);
chk_trans.set_focusable(true);
chk_callsgn.set_style(Theme::getInstance()->bg_darker);
chk_callsgn.set_focusable(true);
wait_time.set_style(Theme::getInstance()->bg_darker);
wait_time.set_focusable(true);
ptt_button_visibility(true);
tone_.set_style(Theme::getInstance()->bg_darker);
tone_.set_focusable(true);
@@ -118,20 +118,15 @@ class MorseRadiotxView : public ui::View {
{{"AM", 0}, {"FM", 1}, {"DSB", 2}, {"USB", 3}, {"LSB", 4}}};
NumberField tone_{{UI_POS_X(14), UI_POS_Y(0)}, 4, {400, 1400}, 10, ' ', true};
NumberField wpm_{{UI_POS_X(25), UI_POS_Y(0)}, 2, {10, 45}, 1, ' ', true};
NumberField wait_time{{UI_POS_X(10), UI_POS_Y(4)}, 3, {1, 99}, 1, ' ', true}; // wait between tx-es in loop mode (sec)
FloatField bandwidth{{UI_POS_X(6), UI_POS_Y(5)}, 4, {1.0, 16.0}, 0.1, ' ', true, 1};
ProgressBar progressbar{
{UI_POS_X(0), UI_POS_Y(6), screen_width, 16}};
FloatField bandwidth{{UI_POS_X(20), UI_POS_Y(3)}, 4, {1.0, 16.0}, 0.1, ' ', true, 1};
ui::Text txt_msg{{UI_POS_X(0), UI_POS_Y(1), UI_POS_MAXWIDTH, UI_POS_HEIGHT(1)}, "[" + msg_buffer + "] "};
ui::Button btn_message{{UI_POS_X(0), UI_POS_Y(2), UI_POS_WIDTH(11), UI_POS_HEIGHT(1)}, "Message"};
ui::Button btn_calls{{UI_POS_X(0), UI_POS_Y(3), UI_POS_WIDTH(11), UI_POS_HEIGHT(1)}, (call_sign.empty()) ? "call sign?" : call_sign};
ui::Button btn_calls{{UI_POS_X(0), UI_POS_Y(4), UI_POS_WIDTH(11), UI_POS_HEIGHT(1)}, (call_sign.empty()) ? "call sign?" : call_sign};
Checkbox chk_trans{{UI_POS_X(14), UI_POS_Y(2)}, 13, "Manual trans.", true};
Checkbox chk_callsgn{{UI_POS_X(14), UI_POS_Y(3)}, 9, "Call sign", true};
Checkbox chk_loop{{UI_POS_X(14), UI_POS_Y(4)}, 4, "loop", true};
ui::Text txt_last{{UI_POS_X(10), UI_POS_Y(7), UI_POS_WIDTH_REMAINING(10), UI_POS_HEIGHT(1)}, ""};
ui::Console console_text{{UI_POS_X(0), UI_POS_Y(9), UI_POS_MAXWIDTH, UI_POS_HEIGHT_REMAINING(14)}};
Checkbox chk_callsgn{{UI_POS_X(14), UI_POS_Y(4)}, 13, "Call sign", true};
ui::Text txt_last{{UI_POS_X(10), UI_POS_Y(5), UI_POS_WIDTH_REMAINING(10), UI_POS_HEIGHT(1)}, ""};
ui::Console console_text{{UI_POS_X(0), UI_POS_Y(7), UI_POS_MAXWIDTH, UI_POS_HEIGHT_REMAINING(14)}};
ui::Button btn_clear{{UI_POS_X(0), UI_POS_Y_BOTTOM(5), UI_POS_WIDTH(5), UI_POS_HEIGHT(1)}, "CLR"};
ui::Button btn_ptt{{UI_POS_X_CENTER(12), UI_POS_Y_BOTTOM(7), UI_POS_WIDTH(12), UI_POS_HEIGHT(3)}, "PTT"};
@@ -140,11 +135,10 @@ class MorseRadiotxView : public ui::View {
{{UI_POS_X(9), UI_POS_Y(0)}, "Tone:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(18), UI_POS_Y(0)}, "Hz", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(21), UI_POS_Y(0)}, "WPM:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(0), UI_POS_Y(5)}, "BandW:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(10), UI_POS_Y(5)}, "kHz", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(0), UI_POS_Y(4)}, "Wait time: ", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(0), UI_POS_Y(7)}, "Last seq:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(0), UI_POS_Y(8)}, "Sent Message:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(14), UI_POS_Y(3)}, "BandW:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(24), UI_POS_Y(3)}, "kHz", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(0), UI_POS_Y(5)}, "Last seq:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X(0), UI_POS_Y(6)}, "Sent Message:", Theme::getInstance()->fg_light->foreground},
{{UI_POS_X_RIGHT(7), UI_POS_Y_BOTTOM(5)}, "Vol.:", Theme::getInstance()->fg_light->foreground},
};
-2
View File
@@ -361,8 +361,6 @@ void WaterfallView::stop() {
baseband::spectrum_streaming_stop();
running_ = false;
}
this->channel_fifo = nullptr;
this->audio_spectrum_data = nullptr;
}
void WaterfallView::show_audio_spectrum_view(const bool show) {
-6
View File
@@ -173,16 +173,12 @@ class WaterfallView : public View {
MessageHandlerRegistration message_handler_channel_spectrum_config{
Message::ID::ChannelSpectrumConfig,
[this](const Message* const p) {
if (!running_)
return;
const auto message = *reinterpret_cast<const ChannelSpectrumConfigMessage*>(p);
this->channel_fifo = message.fifo;
}};
MessageHandlerRegistration message_handler_audio_spectrum{
Message::ID::AudioSpectrum,
[this](const Message* const p) {
if (!running_)
return;
const auto message = *reinterpret_cast<const AudioSpectrumMessage*>(p);
this->audio_spectrum_data = message.data;
this->audio_spectrum_update = true;
@@ -190,8 +186,6 @@ class WaterfallView : public View {
MessageHandlerRegistration message_handler_frame_sync{
Message::ID::DisplayFrameSync,
[this](const Message* const) {
if (!running_)
return;
if (this->channel_fifo) {
ChannelSpectrum channel_spectrum;
while (channel_fifo->out(channel_spectrum)) {