mirror of
https://github.com/eried/portapack-mayhem.git
synced 2024-12-25 23:39:37 -05:00
Added missing files, ENUMed modulation modes
This commit is contained in:
parent
9b8b8cc83f
commit
3477a2691a
@ -59,11 +59,11 @@ program: $(TARGET).bin modules
|
|||||||
sleep 1s
|
sleep 1s
|
||||||
hackrf_spiflash -w $(TARGET).bin
|
hackrf_spiflash -w $(TARGET).bin
|
||||||
|
|
||||||
modules:
|
modules: $(TARGET_BASEBAND).bin $(TARGET_BASEBAND_TX).bin
|
||||||
$(MAKE_MODULES_FILE) $(MODULES)
|
$(MAKE_MODULES_FILE) $(MODULES)
|
||||||
|
|
||||||
$(TARGET).bin: modules $(MAKE_SPI_IMAGE) $(TARGET_BOOTSTRAP).bin $(TARGET_HACKRF_FIRMWARE).dfu $(TARGET_BASEBAND).bin $(TARGET_BASEBAND_TX).bin $(TARGET_APPLICATION).bin
|
$(TARGET).bin: modules $(MAKE_SPI_IMAGE) $(TARGET_BOOTSTRAP).bin $(TARGET_HACKRF_FIRMWARE).dfu $(TARGET_BASEBAND).bin $(TARGET_BASEBAND_TX).bin $(TARGET_APPLICATION).bin
|
||||||
$(MAKE_SPI_IMAGE) $(TARGET_BOOTSTRAP).bin $(TARGET_HACKRF_FIRMWARE).dfu $(TARGET_BASEBAND).bin $(TARGET_APPLICATION).bin $(TARGET).bin
|
$(MAKE_SPI_IMAGE) $(TARGET_BOOTSTRAP).bin $(TARGET_HACKRF_FIRMWARE).dfu $(TARGET_BASEBAND_TX).bin $(TARGET_APPLICATION).bin $(TARGET).bin
|
||||||
|
|
||||||
$(TARGET_BOOTSTRAP).bin: $(TARGET_BOOTSTRAP).elf
|
$(TARGET_BOOTSTRAP).bin: $(TARGET_BOOTSTRAP).elf
|
||||||
$(CP) -O binary $(TARGET_BOOTSTRAP).elf $(TARGET_BOOTSTRAP).bin
|
$(CP) -O binary $(TARGET_BOOTSTRAP).elf $(TARGET_BOOTSTRAP).bin
|
||||||
|
@ -94,7 +94,7 @@ void m4_switch(const char * hash) {
|
|||||||
|
|
||||||
// Ask M4 to enter loop in RAM
|
// Ask M4 to enter loop in RAM
|
||||||
BasebandConfiguration baseband_switch {
|
BasebandConfiguration baseband_switch {
|
||||||
.mode = 0xFF,
|
.mode = SWITCH,
|
||||||
.sampling_rate = 0,
|
.sampling_rate = 0,
|
||||||
.decimation_factor = 1,
|
.decimation_factor = 1,
|
||||||
};
|
};
|
||||||
|
@ -19,6 +19,8 @@
|
|||||||
* Boston, MA 02110-1301, USA.
|
* Boston, MA 02110-1301, USA.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
//TODO: Enum modulation modes (baseband)
|
||||||
|
//TODO: More gfx, cute icons :)
|
||||||
//TODO: check jammer bandwidths
|
//TODO: check jammer bandwidths
|
||||||
//TODO: GSM channel detector
|
//TODO: GSM channel detector
|
||||||
//TODO: wait_for_switch() in baseband-tx !
|
//TODO: wait_for_switch() in baseband-tx !
|
||||||
@ -27,7 +29,7 @@
|
|||||||
//TODO: Reset baseband if module not found (instead of lockup in RAM loop)
|
//TODO: Reset baseband if module not found (instead of lockup in RAM loop)
|
||||||
//TODO: Module name/filename in modules.hpp to indicate requirement in case it's not found ui_loadmodule
|
//TODO: Module name/filename in modules.hpp to indicate requirement in case it's not found ui_loadmodule
|
||||||
//TODO: LCD backlight PWM
|
//TODO: LCD backlight PWM
|
||||||
//TODO: BUG: Crash after TX stop
|
//TODO: BUG: Crash after TX stop (unregister message !)
|
||||||
//TODO: Check bw setting in LCR TX
|
//TODO: Check bw setting in LCR TX
|
||||||
//TODO: BUG: Crash after PSN entry in RDS TX
|
//TODO: BUG: Crash after PSN entry in RDS TX
|
||||||
//TODO: Dynamically load baseband code depending on mode (disable M4 & interrupts, load, reset)
|
//TODO: Dynamically load baseband code depending on mode (disable M4 & interrupts, load, reset)
|
||||||
|
@ -1,2 +0,0 @@
|
|||||||
const char md5_baseband[16] = {0xce,0x87,0x2b,0x2c,0x9e,0x74,0xe8,0x1c,0x1c,0xe9,0xfc,0xc2,0x40,0xc3,0x32,0xd5,};
|
|
||||||
const char md5_baseband_tx[16] = {0x1b,0xef,0x34,0x50,0x45,0xd7,0xae,0x7c,0xb5,0x4f,0x0c,0x5a,0x80,0xa0,0xbc,0x05,};
|
|
@ -130,7 +130,7 @@ void ReceiverModel::disable() {
|
|||||||
/* TODO: This is a dumb hack to stop baseband from working so hard. */
|
/* TODO: This is a dumb hack to stop baseband from working so hard. */
|
||||||
BasebandConfigurationMessage message {
|
BasebandConfigurationMessage message {
|
||||||
.configuration = {
|
.configuration = {
|
||||||
.mode = -1,
|
.mode = NONE,
|
||||||
.sampling_rate = 0,
|
.sampling_rate = 0,
|
||||||
.decimation_factor = 1,
|
.decimation_factor = 1,
|
||||||
}
|
}
|
||||||
|
@ -81,7 +81,7 @@ private:
|
|||||||
uint32_t baseband_bandwidth_ { max2837::filter::bandwidth_minimum };
|
uint32_t baseband_bandwidth_ { max2837::filter::bandwidth_minimum };
|
||||||
int32_t vga_gain_db_ { 32 };
|
int32_t vga_gain_db_ { 32 };
|
||||||
BasebandConfiguration baseband_configuration {
|
BasebandConfiguration baseband_configuration {
|
||||||
.mode = 1, /* TODO: Enum! */
|
.mode = NONE,
|
||||||
.sampling_rate = 3072000,
|
.sampling_rate = 3072000,
|
||||||
.decimation_factor = 4,
|
.decimation_factor = 4,
|
||||||
};
|
};
|
||||||
|
@ -80,11 +80,11 @@ void TransmitterModel::set_sampling_rate(uint32_t hz) {
|
|||||||
update_baseband_configuration();
|
update_baseband_configuration();
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t TransmitterModel::modulation() const {
|
mode_type TransmitterModel::modulation() const {
|
||||||
return baseband_configuration.mode;
|
return baseband_configuration.mode;
|
||||||
}
|
}
|
||||||
|
|
||||||
void TransmitterModel::set_modulation(int32_t v) {
|
void TransmitterModel::set_modulation(mode_type v) {
|
||||||
baseband_configuration.mode = v;
|
baseband_configuration.mode = v;
|
||||||
update_modulation();
|
update_modulation();
|
||||||
}
|
}
|
||||||
@ -114,7 +114,7 @@ void TransmitterModel::disable() {
|
|||||||
/* TODO: This is a dumb hack to stop baseband from working so hard. */
|
/* TODO: This is a dumb hack to stop baseband from working so hard. */
|
||||||
BasebandConfigurationMessage message {
|
BasebandConfigurationMessage message {
|
||||||
.configuration = {
|
.configuration = {
|
||||||
.mode = -1,
|
.mode = NONE,
|
||||||
.sampling_rate = 0,
|
.sampling_rate = 0,
|
||||||
.decimation_factor = 1,
|
.decimation_factor = 1,
|
||||||
}
|
}
|
||||||
@ -152,6 +152,11 @@ void TransmitterModel::update_modulation() {
|
|||||||
update_baseband_configuration();
|
update_baseband_configuration();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void TransmitterModel::set_baseband_configuration(const BasebandConfiguration config) {
|
||||||
|
baseband_configuration = config;
|
||||||
|
update_baseband_configuration();
|
||||||
|
}
|
||||||
|
|
||||||
void TransmitterModel::update_baseband_configuration() {
|
void TransmitterModel::update_baseband_configuration() {
|
||||||
radio::streaming_disable();
|
radio::streaming_disable();
|
||||||
|
|
||||||
@ -164,3 +169,4 @@ void TransmitterModel::update_baseband_configuration() {
|
|||||||
|
|
||||||
radio::streaming_enable();
|
radio::streaming_enable();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -57,8 +57,8 @@ public:
|
|||||||
uint32_t sampling_rate() const;
|
uint32_t sampling_rate() const;
|
||||||
void set_sampling_rate(uint32_t hz);
|
void set_sampling_rate(uint32_t hz);
|
||||||
|
|
||||||
uint32_t modulation() const;
|
mode_type modulation() const;
|
||||||
void set_modulation(int32_t v);
|
void set_modulation(mode_type v);
|
||||||
|
|
||||||
uint32_t baseband_oversampling() const;
|
uint32_t baseband_oversampling() const;
|
||||||
void set_baseband_oversampling(uint32_t v);
|
void set_baseband_oversampling(uint32_t v);
|
||||||
@ -66,13 +66,15 @@ public:
|
|||||||
void enable();
|
void enable();
|
||||||
void disable();
|
void disable();
|
||||||
|
|
||||||
|
void set_baseband_configuration(const BasebandConfiguration config);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool rf_amp_ { true };
|
bool rf_amp_ { true };
|
||||||
int32_t lna_gain_db_ { 0 };
|
int32_t lna_gain_db_ { 0 };
|
||||||
uint32_t baseband_bandwidth_ { max2837::filter::bandwidth_minimum };
|
uint32_t baseband_bandwidth_ { max2837::filter::bandwidth_minimum };
|
||||||
int32_t vga_gain_db_ { 8 };
|
int32_t vga_gain_db_ { 8 };
|
||||||
BasebandConfiguration baseband_configuration {
|
BasebandConfiguration baseband_configuration {
|
||||||
.mode = 16,
|
.mode = NONE,
|
||||||
.sampling_rate = 2280000,
|
.sampling_rate = 2280000,
|
||||||
.decimation_factor = 1,
|
.decimation_factor = 1,
|
||||||
};
|
};
|
||||||
|
@ -48,7 +48,7 @@ AFSKRXView::AFSKRXView(
|
|||||||
};
|
};
|
||||||
|
|
||||||
receiver_model.set_baseband_configuration({
|
receiver_model.set_baseband_configuration({
|
||||||
.mode = 6,
|
.mode = RX_AFSK,
|
||||||
.sampling_rate = 3072000,
|
.sampling_rate = 3072000,
|
||||||
.decimation_factor = 4,
|
.decimation_factor = 4,
|
||||||
});
|
});
|
||||||
|
@ -46,7 +46,7 @@ void AFSKSetupView::focus() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void AFSKSetupView::paint(Painter& painter) {
|
void AFSKSetupView::paint(Painter& painter) {
|
||||||
|
(void)painter;
|
||||||
}
|
}
|
||||||
|
|
||||||
void AFSKSetupView::updfreq(rf::Frequency f) {
|
void AFSKSetupView::updfreq(rf::Frequency f) {
|
||||||
|
@ -50,7 +50,7 @@ JammerView::~JammerView() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void JammerView::paint(Painter& painter) {
|
void JammerView::paint(Painter& painter) {
|
||||||
|
(void)painter;
|
||||||
}
|
}
|
||||||
|
|
||||||
void JammerView::updfreq(uint8_t id, rf::Frequency f) {
|
void JammerView::updfreq(uint8_t id, rf::Frequency f) {
|
||||||
@ -169,7 +169,7 @@ JammerView::JammerView(
|
|||||||
.foreground = Color::grey(),
|
.foreground = Color::grey(),
|
||||||
};
|
};
|
||||||
|
|
||||||
transmitter_model.set_modulation(18);
|
transmitter_model.set_modulation(TX_JAMMER);
|
||||||
|
|
||||||
add_children({ {
|
add_children({ {
|
||||||
&text_type,
|
&text_type,
|
||||||
|
@ -187,7 +187,7 @@ LCRView::LCRView(
|
|||||||
.foreground = Color::black(),
|
.foreground = Color::black(),
|
||||||
};
|
};
|
||||||
|
|
||||||
transmitter_model.set_modulation(16);
|
transmitter_model.set_modulation(TX_LCR);
|
||||||
transmitter_model.set_tuning_frequency(portapack::persistent_memory::tuned_frequency());
|
transmitter_model.set_tuning_frequency(portapack::persistent_memory::tuned_frequency());
|
||||||
memset(litteral, 0, 5*8);
|
memset(litteral, 0, 5*8);
|
||||||
memset(rgsb, 0, 5);
|
memset(rgsb, 0, 5);
|
||||||
@ -276,8 +276,6 @@ LCRView::LCRView(
|
|||||||
};
|
};
|
||||||
|
|
||||||
button_transmit.on_select = [this,&transmitter_model](Button&){
|
button_transmit.on_select = [this,&transmitter_model](Button&){
|
||||||
uint16_t c;
|
|
||||||
|
|
||||||
auto& message_map = context().message_map();
|
auto& message_map = context().message_map();
|
||||||
|
|
||||||
make_frame();
|
make_frame();
|
||||||
|
@ -41,7 +41,7 @@ void LoadModuleView::focus() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void LoadModuleView::paint(Painter& painter) {
|
void LoadModuleView::paint(Painter& painter) {
|
||||||
|
(void)painter;
|
||||||
}
|
}
|
||||||
|
|
||||||
void LoadModuleView::on_hide() {
|
void LoadModuleView::on_hide() {
|
||||||
@ -53,7 +53,8 @@ void LoadModuleView::on_show() {
|
|||||||
auto& message_map = context().message_map();
|
auto& message_map = context().message_map();
|
||||||
message_map.register_handler(Message::ID::ReadyForSwitch,
|
message_map.register_handler(Message::ID::ReadyForSwitch,
|
||||||
[this](Message* const p) {
|
[this](Message* const p) {
|
||||||
const auto message = static_cast<const ReadyForSwitchMessage*>(p);
|
(void)p;
|
||||||
|
// const auto message = static_cast<const ReadyForSwitchMessage*>(p);
|
||||||
if (m4_load_image()) {
|
if (m4_load_image()) {
|
||||||
text_info.set("Module loaded :)");
|
text_info.set("Module loaded :)");
|
||||||
_mod_loaded = true;
|
_mod_loaded = true;
|
||||||
|
@ -195,6 +195,7 @@ BMPView::BMPView(NavigationView& nav) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void BMPView::paint(Painter& painter) {
|
void BMPView::paint(Painter& painter) {
|
||||||
|
(void)painter;
|
||||||
portapack::display.drawBMP({(240-185)/2, 0}, splash_bmp);
|
portapack::display.drawBMP({(240-185)/2, 0}, splash_bmp);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -456,7 +456,7 @@ ReceiverView::ReceiverView(
|
|||||||
options_modulation.set_by_value(receiver_model.modulation());
|
options_modulation.set_by_value(receiver_model.modulation());
|
||||||
options_modulation.on_change = [this](size_t n, OptionsField::value_t v) {
|
options_modulation.on_change = [this](size_t n, OptionsField::value_t v) {
|
||||||
(void)n;
|
(void)n;
|
||||||
this->on_modulation_changed(v);
|
this->on_modulation_changed((mode_type)v);
|
||||||
};
|
};
|
||||||
/*
|
/*
|
||||||
options_baseband_oversampling.set_by_value(receiver_model.baseband_oversampling());
|
options_baseband_oversampling.set_by_value(receiver_model.baseband_oversampling());
|
||||||
@ -625,7 +625,7 @@ void ReceiverView::on_vga_changed(int32_t v_db) {
|
|||||||
receiver_model.set_vga(v_db);
|
receiver_model.set_vga(v_db);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ReceiverView::on_modulation_changed(int32_t modulation) {
|
void ReceiverView::on_modulation_changed(mode_type modulation) {
|
||||||
/* TODO: This is TERRIBLE!!! */
|
/* TODO: This is TERRIBLE!!! */
|
||||||
switch(modulation) {
|
switch(modulation) {
|
||||||
case 3:
|
case 3:
|
||||||
|
@ -411,13 +411,12 @@ private:
|
|||||||
{ 19 * 8, 1 * 16 },
|
{ 19 * 8, 1 * 16 },
|
||||||
4,
|
4,
|
||||||
{
|
{
|
||||||
// TODO: Put ordinals in here...
|
{ " AM ", RX_NBAM_AUDIO },
|
||||||
{ " AM ", 0 },
|
{ "NFM ", RX_NBFM_AUDIO },
|
||||||
{ "NFM ", 1 },
|
{ "WFM ", RX_WBFM_AUDIO },
|
||||||
{ "WFM ", 2 },
|
{ "AIS ", RX_AIS },
|
||||||
{ "AIS ", 3 },
|
{ "TPMS", RX_TPMS },
|
||||||
{ "TPMS", 5 },
|
{ "SPEC", RX_WBSPECTRUM },
|
||||||
{ "SPEC", 4 },
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
/*
|
/*
|
||||||
@ -464,7 +463,7 @@ private:
|
|||||||
void on_rf_amp_changed(bool v);
|
void on_rf_amp_changed(bool v);
|
||||||
void on_lna_changed(int32_t v_db);
|
void on_lna_changed(int32_t v_db);
|
||||||
void on_vga_changed(int32_t v_db);
|
void on_vga_changed(int32_t v_db);
|
||||||
void on_modulation_changed(int32_t modulation);
|
void on_modulation_changed(mode_type modulation);
|
||||||
void on_show_options_frequency();
|
void on_show_options_frequency();
|
||||||
void on_show_options_rf_gain();
|
void on_show_options_rf_gain();
|
||||||
void on_frequency_step_changed(rf::Frequency f);
|
void on_frequency_step_changed(rf::Frequency f);
|
||||||
|
144
firmware/application/ui_sigfrx.cpp
Normal file
144
firmware/application/ui_sigfrx.cpp
Normal file
@ -0,0 +1,144 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2015 Jared Boone, ShareBrained Technology, Inc.
|
||||||
|
*
|
||||||
|
* This file is part of PortaPack.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation; either version 2, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; see the file COPYING. If not, write to
|
||||||
|
* the Free Software Foundation, Inc., 51 Franklin Street,
|
||||||
|
* Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "ui_sigfrx.hpp"
|
||||||
|
#include "ui_receiver.hpp"
|
||||||
|
|
||||||
|
#include "ch.h"
|
||||||
|
#include "evtimer.h"
|
||||||
|
|
||||||
|
#include "ff.h"
|
||||||
|
#include "hackrf_gpio.hpp"
|
||||||
|
#include "portapack.hpp"
|
||||||
|
#include "radio.hpp"
|
||||||
|
//#include "fox_bmp.hpp"
|
||||||
|
|
||||||
|
#include "hackrf_hal.hpp"
|
||||||
|
#include "portapack_shared_memory.hpp"
|
||||||
|
#include "portapack_persistent_memory.hpp"
|
||||||
|
|
||||||
|
#include <cstring>
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
using namespace hackrf::one;
|
||||||
|
|
||||||
|
namespace ui {
|
||||||
|
|
||||||
|
void SIGFRXView::focus() {
|
||||||
|
button_exit.focus();
|
||||||
|
}
|
||||||
|
|
||||||
|
SIGFRXView::~SIGFRXView() {
|
||||||
|
receiver_model.disable();
|
||||||
|
}
|
||||||
|
|
||||||
|
void SIGFRXView::paint(Painter& painter) {
|
||||||
|
uint8_t i, xp;
|
||||||
|
|
||||||
|
//portapack::display.drawBMP({0, 302-160}, fox_bmp);
|
||||||
|
portapack::display.fill_rectangle({0,16,240,160-16}, ui::Color::white());
|
||||||
|
for (i = 0; i < 6; i++) {
|
||||||
|
xp = sigfrx_marks[i*3];
|
||||||
|
painter.draw_string({ (ui::Coord)sigfrx_marks[(i*3)+1], 144-20 }, style_white, to_string_dec_uint(sigfrx_marks[(i*3)+2]) );
|
||||||
|
portapack::display.draw_line({xp, 144-4}, {xp, 144}, ui::Color::black());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void SIGFRXView::on_channel_spectrum(const ChannelSpectrum& spectrum) {
|
||||||
|
portapack::display.fill_rectangle({0, 144, 240, 4},ui::Color::white());
|
||||||
|
|
||||||
|
uint8_t xmax = 0, imax = 0;
|
||||||
|
size_t i;
|
||||||
|
|
||||||
|
for (i=0; i<120; i++) {
|
||||||
|
if (spectrum.db[i] > xmax) {
|
||||||
|
xmax = spectrum.db[i];
|
||||||
|
imax = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for (i=136; i<256; i++) {
|
||||||
|
if (spectrum.db[i-16] > xmax) {
|
||||||
|
xmax = spectrum.db[i-16];
|
||||||
|
imax = i-16;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((imax >= last_channel-2) && (imax <= last_channel+2)) {
|
||||||
|
if (detect_counter >= 5) {
|
||||||
|
// Latched !
|
||||||
|
} else {
|
||||||
|
detect_counter++;
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (detect_counter >= 5) text_channel.set("... ");
|
||||||
|
detect_counter = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
last_channel = imax;
|
||||||
|
|
||||||
|
portapack::display.fill_rectangle({(ui::Coord)(imax-2), 144, 4, 4}, ui::Color::red());
|
||||||
|
}
|
||||||
|
|
||||||
|
void SIGFRXView::on_show() {
|
||||||
|
context().message_map().register_handler(Message::ID::ChannelSpectrum,
|
||||||
|
[this](const Message* const p) {
|
||||||
|
this->on_channel_spectrum(reinterpret_cast<const ChannelSpectrumMessage*>(p)->spectrum);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
SIGFRXView::SIGFRXView(
|
||||||
|
NavigationView& nav,
|
||||||
|
ReceiverModel& receiver_model
|
||||||
|
) : receiver_model(receiver_model)
|
||||||
|
{
|
||||||
|
receiver_model.set_baseband_configuration({
|
||||||
|
.mode = RX_SIGFOX,
|
||||||
|
.sampling_rate = 3072000,
|
||||||
|
.decimation_factor = 4,
|
||||||
|
});
|
||||||
|
receiver_model.set_baseband_bandwidth(1750000);
|
||||||
|
|
||||||
|
receiver_model.set_tuning_frequency(868110000);
|
||||||
|
|
||||||
|
receiver_model.set_lna(0);
|
||||||
|
receiver_model.set_vga(0);
|
||||||
|
|
||||||
|
add_children({ {
|
||||||
|
&text_type,
|
||||||
|
&text_channel,
|
||||||
|
&text_data,
|
||||||
|
&button_exit
|
||||||
|
} });
|
||||||
|
|
||||||
|
text_type.set_style(&style_white);
|
||||||
|
text_channel.set_style(&style_white);
|
||||||
|
text_data.set_style(&style_white);
|
||||||
|
|
||||||
|
button_exit.on_select = [&nav](Button&){
|
||||||
|
nav.pop();
|
||||||
|
};
|
||||||
|
|
||||||
|
receiver_model.enable();
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
} /* namespace ui */
|
87
firmware/application/ui_sigfrx.hpp
Normal file
87
firmware/application/ui_sigfrx.hpp
Normal file
@ -0,0 +1,87 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2015 Jared Boone, ShareBrained Technology, Inc.
|
||||||
|
*
|
||||||
|
* This file is part of PortaPack.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation; either version 2, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; see the file COPYING. If not, write to
|
||||||
|
* the Free Software Foundation, Inc., 51 Franklin Street,
|
||||||
|
* Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "ui.hpp"
|
||||||
|
#include "ui_widget.hpp"
|
||||||
|
#include "ui_painter.hpp"
|
||||||
|
#include "ui_menu.hpp"
|
||||||
|
#include "ui_navigation.hpp"
|
||||||
|
#include "ui_font_fixed_8x16.hpp"
|
||||||
|
#include "clock_manager.hpp"
|
||||||
|
#include "message.hpp"
|
||||||
|
#include "rf_path.hpp"
|
||||||
|
#include "max2837.hpp"
|
||||||
|
#include "volume.hpp"
|
||||||
|
#include "receiver_model.hpp"
|
||||||
|
|
||||||
|
namespace ui {
|
||||||
|
|
||||||
|
class SIGFRXView : public View {
|
||||||
|
public:
|
||||||
|
SIGFRXView(NavigationView& nav, ReceiverModel& receiver_model);
|
||||||
|
~SIGFRXView();
|
||||||
|
void on_channel_spectrum(const ChannelSpectrum& spectrum);
|
||||||
|
|
||||||
|
void on_show() override;
|
||||||
|
void focus() override;
|
||||||
|
void paint(Painter& painter) override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
ReceiverModel& receiver_model;
|
||||||
|
|
||||||
|
uint8_t last_channel;
|
||||||
|
uint8_t detect_counter = 0;
|
||||||
|
|
||||||
|
const Style style_white {
|
||||||
|
.font = font::fixed_8x16,
|
||||||
|
.background = Color::white(),
|
||||||
|
.foreground = Color::black()
|
||||||
|
};
|
||||||
|
|
||||||
|
const uint16_t sigfrx_marks[18] = {
|
||||||
|
10, 8, 0,
|
||||||
|
60, 52, 90,
|
||||||
|
119, 95, 180,
|
||||||
|
121, 122, 220,
|
||||||
|
179, 171, 310,
|
||||||
|
230, 214, 400 };
|
||||||
|
|
||||||
|
Text text_type {
|
||||||
|
{ 1 * 8, 1 * 16, 28 * 8, 16 },
|
||||||
|
"SIGFOX interceptor. Yap !"
|
||||||
|
};
|
||||||
|
|
||||||
|
Text text_channel {
|
||||||
|
{ 1 * 8, 3 * 16, 28 * 8, 16 },
|
||||||
|
"PL: "
|
||||||
|
};
|
||||||
|
Text text_data {
|
||||||
|
{ 1 * 8, 4 * 16, 28 * 8, 16 },
|
||||||
|
"??: "
|
||||||
|
};
|
||||||
|
|
||||||
|
Button button_exit {
|
||||||
|
{ 22 * 8, 160 - 32, 56, 32 },
|
||||||
|
"Exit"
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
} /* namespace ui */
|
@ -50,7 +50,7 @@ WhistleView::~WhistleView() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void WhistleView::paint(Painter& painter) {
|
void WhistleView::paint(Painter& painter) {
|
||||||
|
(void)painter;
|
||||||
}
|
}
|
||||||
|
|
||||||
void WhistleView::whistle_th(void *arg) {
|
void WhistleView::whistle_th(void *arg) {
|
||||||
@ -72,7 +72,7 @@ WhistleView::WhistleView(
|
|||||||
msg_t mbox_buffer[3];
|
msg_t mbox_buffer[3];
|
||||||
chMBInit(&mbox, mbox_buffer, 3);
|
chMBInit(&mbox, mbox_buffer, 3);
|
||||||
|
|
||||||
transmitter_model.set_modulation(17);
|
transmitter_model.set_modulation(TX_TONE);
|
||||||
transmitter_model.set_tuning_frequency(portapack::persistent_memory::tuned_frequency());
|
transmitter_model.set_tuning_frequency(portapack::persistent_memory::tuned_frequency());
|
||||||
|
|
||||||
add_children({ {
|
add_children({ {
|
||||||
|
@ -49,7 +49,7 @@ XylosView::~XylosView() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void XylosView::paint(Painter& painter) {
|
void XylosView::paint(Painter& painter) {
|
||||||
|
(void)painter;
|
||||||
}
|
}
|
||||||
|
|
||||||
void XylosView::upd_message() {
|
void XylosView::upd_message() {
|
||||||
@ -96,7 +96,37 @@ void XylosView::upd_message() {
|
|||||||
|
|
||||||
ccirmessage[20] = 0;
|
ccirmessage[20] = 0;
|
||||||
|
|
||||||
|
// Display as text
|
||||||
text_debug.set(ccirmessage);
|
text_debug.set(ccirmessage);
|
||||||
|
|
||||||
|
// ASCII to baseband frequency LUT index
|
||||||
|
for (c=0; c<20; c++) {
|
||||||
|
if (ccirmessage[c] > '9')
|
||||||
|
ccirmessage[c] -= 0x37;
|
||||||
|
else
|
||||||
|
ccirmessage[c] -= 0x30;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void XylosView::journuit() {
|
||||||
|
uint8_t sr;
|
||||||
|
|
||||||
|
chThdSleepMilliseconds(1000);
|
||||||
|
|
||||||
|
// Invert relay states
|
||||||
|
sr = options_ra.selected_index();
|
||||||
|
if (sr > 0) options_ra.set_selected_index(sr ^ 3);
|
||||||
|
sr = options_rb.selected_index();
|
||||||
|
if (sr > 0) options_rb.set_selected_index(sr ^ 3);
|
||||||
|
sr = options_rc.selected_index();
|
||||||
|
if (sr > 0) options_rc.set_selected_index(sr ^ 3);
|
||||||
|
|
||||||
|
upd_message();
|
||||||
|
|
||||||
|
portapack::audio_codec.set_headphone_volume(volume_t::decibel(90 - 99) + wolfson::wm8731::headphone_gain_range.max);
|
||||||
|
shared_memory.xylos_transmit_done = false;
|
||||||
|
memcpy(shared_memory.xylosdata, ccirmessage, 21);
|
||||||
|
transmitter_model.enable();
|
||||||
}
|
}
|
||||||
|
|
||||||
XylosView::XylosView(
|
XylosView::XylosView(
|
||||||
@ -116,7 +146,13 @@ XylosView::XylosView(
|
|||||||
.foreground = Color::black(),
|
.foreground = Color::black(),
|
||||||
};
|
};
|
||||||
|
|
||||||
transmitter_model.set_modulation(19);
|
transmitter_model.set_baseband_configuration({
|
||||||
|
.mode = TX_XYLOS,
|
||||||
|
.sampling_rate = 1536000,
|
||||||
|
.decimation_factor = 1,
|
||||||
|
});
|
||||||
|
|
||||||
|
transmitter_model.set_modulation(TX_XYLOS); // Useless ?
|
||||||
|
|
||||||
add_children({ {
|
add_children({ {
|
||||||
&text_title,
|
&text_title,
|
||||||
@ -141,6 +177,7 @@ XylosView::XylosView(
|
|||||||
&text_progress,
|
&text_progress,
|
||||||
&text_debug,
|
&text_debug,
|
||||||
&button_transmit,
|
&button_transmit,
|
||||||
|
&checkbox_cligno,
|
||||||
&button_exit
|
&button_exit
|
||||||
} });
|
} });
|
||||||
|
|
||||||
@ -170,9 +207,17 @@ XylosView::XylosView(
|
|||||||
XylosView::upd_message();
|
XylosView::upd_message();
|
||||||
};
|
};
|
||||||
checkbox_wcsubfamily.on_select = [this](Checkbox&) {
|
checkbox_wcsubfamily.on_select = [this](Checkbox&) {
|
||||||
|
if (checkbox_wcsubfamily.value() == true)
|
||||||
|
subfamily_code.hidden(true);
|
||||||
|
else
|
||||||
|
subfamily_code.hidden(false);
|
||||||
XylosView::upd_message();
|
XylosView::upd_message();
|
||||||
};
|
};
|
||||||
checkbox_wcid.on_select = [this](Checkbox&) {
|
checkbox_wcid.on_select = [this](Checkbox&) {
|
||||||
|
if (checkbox_wcid.value() == true)
|
||||||
|
receiver_code.hidden(true);
|
||||||
|
else
|
||||||
|
receiver_code.hidden(false);
|
||||||
XylosView::upd_message();
|
XylosView::upd_message();
|
||||||
};
|
};
|
||||||
options_ra.on_change = [this](size_t n, OptionsField::value_t v) {
|
options_ra.on_change = [this](size_t n, OptionsField::value_t v) {
|
||||||
@ -207,14 +252,19 @@ XylosView::XylosView(
|
|||||||
char progress[21];
|
char progress[21];
|
||||||
const auto message = static_cast<const TXDoneMessage*>(p);
|
const auto message = static_cast<const TXDoneMessage*>(p);
|
||||||
if (message->n == 25) {
|
if (message->n == 25) {
|
||||||
|
portapack::audio_codec.set_headphone_volume(volume_t::decibel(0 - 99) + wolfson::wm8731::headphone_gain_range.max);
|
||||||
transmitter_model.disable();
|
transmitter_model.disable();
|
||||||
for (c=0;c<20;c++)
|
for (c=0;c<20;c++)
|
||||||
progress[c] = ' ';
|
progress[c] = ' ';
|
||||||
progress[20] = 0;
|
progress[20] = 0;
|
||||||
text_progress.set(progress);
|
text_progress.set(progress);
|
||||||
|
if (checkbox_cligno.value() == false) {
|
||||||
txing = false;
|
txing = false;
|
||||||
button_transmit.set_style(&style_val);
|
button_transmit.set_style(&style_val);
|
||||||
button_transmit.set_text("START");
|
button_transmit.set_text("START");
|
||||||
|
} else {
|
||||||
|
journuit();
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
for (c=0;c<message->n;c++)
|
for (c=0;c<message->n;c++)
|
||||||
progress[c] = ' ';
|
progress[c] = ' ';
|
||||||
@ -228,7 +278,9 @@ XylosView::XylosView(
|
|||||||
shared_memory.xylos_transmit_done = false;
|
shared_memory.xylos_transmit_done = false;
|
||||||
memcpy(shared_memory.xylosdata, ccirmessage, 21);
|
memcpy(shared_memory.xylosdata, ccirmessage, 21);
|
||||||
|
|
||||||
transmitter_model.set_tuning_frequency(87700000); //xylos_freqs[options_freq.selected_index()]);
|
transmitter_model.set_tuning_frequency(xylos_freqs[options_freq.selected_index()]);
|
||||||
|
|
||||||
|
portapack::audio_codec.set_headphone_volume(volume_t::decibel(90 - 99) + wolfson::wm8731::headphone_gain_range.max);
|
||||||
|
|
||||||
txing = true;
|
txing = true;
|
||||||
button_transmit.set_style(&style_cancel);
|
button_transmit.set_style(&style_cancel);
|
||||||
|
@ -38,6 +38,7 @@ class XylosView : public View {
|
|||||||
public:
|
public:
|
||||||
XylosView(NavigationView& nav, TransmitterModel& transmitter_model);
|
XylosView(NavigationView& nav, TransmitterModel& transmitter_model);
|
||||||
~XylosView();
|
~XylosView();
|
||||||
|
void journuit();
|
||||||
|
|
||||||
void upd_message();
|
void upd_message();
|
||||||
void focus() override;
|
void focus() override;
|
||||||
@ -45,7 +46,7 @@ public:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
bool txing = false;
|
bool txing = false;
|
||||||
const rf::Frequency xylos_freqs[6] = { 31325000, 31387500, 31437500, 31475000, 31687500, 31975000 };
|
const rf::Frequency xylos_freqs[7] = { 31325000, 31387500, 31437500, 31475000, 31687500, 31975000, 87000000 };
|
||||||
char ccirmessage[21];
|
char ccirmessage[21];
|
||||||
|
|
||||||
TransmitterModel& transmitter_model;
|
TransmitterModel& transmitter_model;
|
||||||
@ -117,14 +118,15 @@ private:
|
|||||||
};
|
};
|
||||||
OptionsField options_freq {
|
OptionsField options_freq {
|
||||||
{ 16 * 8, 9 * 16 },
|
{ 16 * 8, 9 * 16 },
|
||||||
6,
|
7,
|
||||||
{
|
{
|
||||||
{ "31.3250", 0 },
|
{ "31.3250", 0 },
|
||||||
{ "31.3875", 1 },
|
{ "31.3875", 1 },
|
||||||
{ "31.4375", 2 },
|
{ "31.4375", 2 },
|
||||||
{ "31.4750", 3 },
|
{ "31.4750", 3 },
|
||||||
{ "31.6875", 4 },
|
{ "31.6875", 4 },
|
||||||
{ "31.9750", 5 }
|
{ "31.9750", 5 },
|
||||||
|
{ "TEST 87", 6 }
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -182,6 +184,11 @@ private:
|
|||||||
"START"
|
"START"
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Checkbox checkbox_cligno {
|
||||||
|
{ 96, 16 * 16 + 4},
|
||||||
|
"J/N"
|
||||||
|
};
|
||||||
|
|
||||||
Button button_exit {
|
Button button_exit {
|
||||||
{ 21 * 8, 16 * 16, 64, 32 },
|
{ 21 * 8, 16 * 16, 64, 32 },
|
||||||
"Exit"
|
"Exit"
|
||||||
|
Binary file not shown.
@ -121,7 +121,7 @@ constexpr gpdma::channel::Config config_rx() {
|
|||||||
|
|
||||||
/* TODO: Clean up terminology around "buffer", "transfer", "samples" */
|
/* TODO: Clean up terminology around "buffer", "transfer", "samples" */
|
||||||
|
|
||||||
constexpr size_t buffer_samples_log2n = 7;
|
constexpr size_t buffer_samples_log2n = 8; // Bumped to 8, to allow filling at 750Hz
|
||||||
constexpr size_t buffer_samples = (1 << buffer_samples_log2n);
|
constexpr size_t buffer_samples = (1 << buffer_samples_log2n);
|
||||||
constexpr size_t transfers_per_buffer_log2n = 2;
|
constexpr size_t transfers_per_buffer_log2n = 2;
|
||||||
constexpr size_t transfers_per_buffer = (1 << transfers_per_buffer_log2n);
|
constexpr size_t transfers_per_buffer = (1 << transfers_per_buffer_log2n);
|
||||||
|
@ -38,6 +38,8 @@
|
|||||||
|
|
||||||
#include "touch_dma.hpp"
|
#include "touch_dma.hpp"
|
||||||
|
|
||||||
|
#include "modules.h"
|
||||||
|
|
||||||
#include "dsp_decimate.hpp"
|
#include "dsp_decimate.hpp"
|
||||||
#include "dsp_demodulate.hpp"
|
#include "dsp_demodulate.hpp"
|
||||||
#include "dsp_fft.hpp"
|
#include "dsp_fft.hpp"
|
||||||
@ -469,6 +471,23 @@ private:
|
|||||||
const auto baseband_buffer =
|
const auto baseband_buffer =
|
||||||
new std::array<baseband::sample_t, 8192>();
|
new std::array<baseband::sample_t, 8192>();
|
||||||
|
|
||||||
|
char ram_loop[32];
|
||||||
|
typedef int (*fn_ptr)(void);
|
||||||
|
fn_ptr loop_ptr;
|
||||||
|
|
||||||
|
void ram_loop_fn(void) {
|
||||||
|
while(1) {}
|
||||||
|
}
|
||||||
|
|
||||||
|
void wait_for_switch(void) {
|
||||||
|
memcpy(&ram_loop[0], reinterpret_cast<char*>(&ram_loop_fn), 32);
|
||||||
|
loop_ptr = reinterpret_cast<fn_ptr>(&ram_loop[0]);
|
||||||
|
ReadyForSwitchMessage message;
|
||||||
|
shared_memory.application_queue.push(message);
|
||||||
|
(*loop_ptr)();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
int main(void) {
|
int main(void) {
|
||||||
init();
|
init();
|
||||||
|
|
||||||
@ -494,31 +513,34 @@ int main(void) {
|
|||||||
delete old_p;
|
delete old_p;
|
||||||
|
|
||||||
switch(message->configuration.mode) {
|
switch(message->configuration.mode) {
|
||||||
case 15:
|
case TX_RDS:
|
||||||
direction = baseband::Direction::Transmit;
|
direction = baseband::Direction::Transmit;
|
||||||
baseband_thread.baseband_processor = new RDSProcessor();
|
baseband_thread.baseband_processor = new RDSProcessor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 16:
|
case TX_LCR:
|
||||||
direction = baseband::Direction::Transmit;
|
direction = baseband::Direction::Transmit;
|
||||||
baseband_thread.baseband_processor = new LCRFSKProcessor();
|
baseband_thread.baseband_processor = new LCRFSKProcessor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 17:
|
case TX_TONE:
|
||||||
direction = baseband::Direction::Transmit;
|
direction = baseband::Direction::Transmit;
|
||||||
baseband_thread.baseband_processor = new ToneProcessor();
|
baseband_thread.baseband_processor = new ToneProcessor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 18:
|
case TX_JAMMER:
|
||||||
direction = baseband::Direction::Transmit;
|
direction = baseband::Direction::Transmit;
|
||||||
baseband_thread.baseband_processor = new JammerProcessor();
|
baseband_thread.baseband_processor = new JammerProcessor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 19:
|
case TX_XYLOS:
|
||||||
direction = baseband::Direction::Transmit;
|
direction = baseband::Direction::Transmit;
|
||||||
baseband_thread.baseband_processor = new XylosProcessor();
|
baseband_thread.baseband_processor = new XylosProcessor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case 0xFF:
|
||||||
|
wait_for_switch();
|
||||||
|
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
|
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
|
||||||
|
* Copyright (C) 2016 Furrtek
|
||||||
*
|
*
|
||||||
* This file is part of PortaPack.
|
* This file is part of PortaPack.
|
||||||
*
|
*
|
||||||
@ -27,28 +28,30 @@
|
|||||||
|
|
||||||
void XylosProcessor::execute(buffer_c8_t buffer) {
|
void XylosProcessor::execute(buffer_c8_t buffer) {
|
||||||
|
|
||||||
|
// This is called at 1536000/2048 = 750Hz
|
||||||
|
|
||||||
|
ai = 0;
|
||||||
|
|
||||||
for (size_t i = 0; i<buffer.count; i++) {
|
for (size_t i = 0; i<buffer.count; i++) {
|
||||||
//Sample generation 2.28M/10 = 228kHz
|
|
||||||
|
// Sample generation rate: 1536000/10 = 153kHz
|
||||||
if (s >= 9) {
|
if (s >= 9) {
|
||||||
s = 0;
|
s = 0;
|
||||||
|
|
||||||
if (sample_count >= CCIR_TONELENGTH) {
|
if (sample_count >= CCIR_TONELENGTH) {
|
||||||
if (shared_memory.xylos_transmit_done == false) {
|
if (shared_memory.xylos_transmit_done == false) {
|
||||||
message.n = byte_pos; // Progress
|
message.n = byte_pos; // Inform UI about progress (just as eye candy)
|
||||||
shared_memory.application_queue.push(message);
|
shared_memory.application_queue.push(message);
|
||||||
digit = shared_memory.xylosdata[byte_pos++];
|
digit = shared_memory.xylosdata[byte_pos++];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!digit) {
|
if (!digit) {
|
||||||
message.n = 25; // Done code
|
message.n = 25; // End of message code
|
||||||
shared_memory.xylos_transmit_done = true;
|
shared_memory.xylos_transmit_done = true;
|
||||||
shared_memory.application_queue.push(message);
|
shared_memory.application_queue.push(message);
|
||||||
digit = 0;
|
digit = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (digit > '9') digit -= 7;
|
|
||||||
digit -= 0x30;
|
|
||||||
|
|
||||||
sample_count = 0;
|
sample_count = 0;
|
||||||
} else {
|
} else {
|
||||||
sample_count++;
|
sample_count++;
|
||||||
@ -61,8 +64,16 @@ void XylosProcessor::execute(buffer_c8_t buffer) {
|
|||||||
|
|
||||||
sample = (sine_table_f32[(aphase & 0x03FF0000)>>18]*255);
|
sample = (sine_table_f32[(aphase & 0x03FF0000)>>18]*255);
|
||||||
|
|
||||||
|
// Audio preview sample generation: 1536000/48000 = 32
|
||||||
|
if (as >= 31) {
|
||||||
|
as = 0;
|
||||||
|
preview_audio_buffer.p[ai++] = sample * 128;
|
||||||
|
} else {
|
||||||
|
as++;
|
||||||
|
}
|
||||||
|
|
||||||
//FM
|
//FM
|
||||||
frq = sample * 160; // 20kHz wide (?)
|
frq = sample * 300; // ~10kHz wide
|
||||||
|
|
||||||
phase = (phase + frq);
|
phase = (phase + frq);
|
||||||
sphase = phase + (256<<16);
|
sphase = phase + (256<<16);
|
||||||
@ -72,4 +83,6 @@ void XylosProcessor::execute(buffer_c8_t buffer) {
|
|||||||
|
|
||||||
buffer.p[i] = {(int8_t)re,(int8_t)im};
|
buffer.p[i] = {(int8_t)re,(int8_t)im};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fill_audio_buffer(preview_audio_buffer);
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
|
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
|
||||||
|
* Copyright (C) 2016 Furrtek
|
||||||
*
|
*
|
||||||
* This file is part of PortaPack.
|
* This file is part of PortaPack.
|
||||||
*
|
*
|
||||||
@ -24,35 +25,42 @@
|
|||||||
|
|
||||||
#include "baseband_processor.hpp"
|
#include "baseband_processor.hpp"
|
||||||
|
|
||||||
#define CCIR_TONELENGTH 22800
|
#define CCIR_TONELENGTH 15360-1 // 1536000/10/10
|
||||||
#define PHASEV 294.34
|
#define PHASEV 436.91 // (65536*1024)/1536000*10
|
||||||
|
|
||||||
class XylosProcessor : public BasebandProcessor {
|
class XylosProcessor : public BasebandProcessor {
|
||||||
public:
|
public:
|
||||||
void execute(buffer_c8_t buffer) override;
|
void execute(buffer_c8_t buffer) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
int16_t audio_data[64];
|
||||||
|
|
||||||
|
const buffer_s16_t preview_audio_buffer {
|
||||||
|
audio_data,
|
||||||
|
sizeof(int16_t)*64
|
||||||
|
};
|
||||||
|
|
||||||
uint32_t ccir_phases[16] = {
|
uint32_t ccir_phases[16] = {
|
||||||
1981*PHASEV,
|
(uint32_t)(1981*PHASEV),
|
||||||
1124*PHASEV,
|
(uint32_t)(1124*PHASEV),
|
||||||
1197*PHASEV,
|
(uint32_t)(1197*PHASEV),
|
||||||
1275*PHASEV,
|
(uint32_t)(1275*PHASEV),
|
||||||
1358*PHASEV,
|
(uint32_t)(1358*PHASEV),
|
||||||
1446*PHASEV,
|
(uint32_t)(1446*PHASEV),
|
||||||
1540*PHASEV,
|
(uint32_t)(1540*PHASEV),
|
||||||
1640*PHASEV,
|
(uint32_t)(1640*PHASEV),
|
||||||
1747*PHASEV,
|
(uint32_t)(1747*PHASEV),
|
||||||
1860*PHASEV,
|
(uint32_t)(1860*PHASEV),
|
||||||
2400*PHASEV,
|
(uint32_t)(2400*PHASEV),
|
||||||
930*PHASEV,
|
(uint32_t)(930*PHASEV),
|
||||||
2247*PHASEV,
|
(uint32_t)(2247*PHASEV),
|
||||||
991*PHASEV,
|
(uint32_t)(991*PHASEV),
|
||||||
2110*PHASEV,
|
(uint32_t)(2110*PHASEV),
|
||||||
1055*PHASEV
|
(uint32_t)(1055*PHASEV)
|
||||||
};
|
};
|
||||||
|
|
||||||
int8_t re, im;
|
int8_t re, im;
|
||||||
uint8_t s;
|
uint8_t s, as = 0, ai;
|
||||||
uint8_t byte_pos = 0;
|
uint8_t byte_pos = 0;
|
||||||
uint8_t digit = 0;
|
uint8_t digit = 0;
|
||||||
uint32_t sample_count = CCIR_TONELENGTH;
|
uint32_t sample_count = CCIR_TONELENGTH;
|
||||||
|
Binary file not shown.
@ -41,6 +41,8 @@
|
|||||||
|
|
||||||
#include "touch_dma.hpp"
|
#include "touch_dma.hpp"
|
||||||
|
|
||||||
|
#include "modules.h"
|
||||||
|
|
||||||
#include "dsp_decimate.hpp"
|
#include "dsp_decimate.hpp"
|
||||||
#include "dsp_demodulate.hpp"
|
#include "dsp_demodulate.hpp"
|
||||||
#include "dsp_fft.hpp"
|
#include "dsp_fft.hpp"
|
||||||
@ -57,9 +59,9 @@
|
|||||||
#include "proc_am_audio.hpp"
|
#include "proc_am_audio.hpp"
|
||||||
#include "proc_nfm_audio.hpp"
|
#include "proc_nfm_audio.hpp"
|
||||||
#include "proc_wfm_audio.hpp"
|
#include "proc_wfm_audio.hpp"
|
||||||
//#include "proc_ais.hpp"
|
#include "proc_ais.hpp"
|
||||||
#include "proc_wideband_spectrum.hpp"
|
#include "proc_wideband_spectrum.hpp"
|
||||||
//#include "proc_tpms.hpp"
|
#include "proc_tpms.hpp"
|
||||||
#include "proc_afskrx.hpp"
|
#include "proc_afskrx.hpp"
|
||||||
#include "proc_sigfrx.hpp"
|
#include "proc_sigfrx.hpp"
|
||||||
|
|
||||||
@ -390,46 +392,46 @@ int main(void) {
|
|||||||
delete old_p;
|
delete old_p;
|
||||||
|
|
||||||
switch(message->configuration.mode) {
|
switch(message->configuration.mode) {
|
||||||
case 0:
|
case RX_NBAM_AUDIO:
|
||||||
direction = baseband::Direction::Receive;
|
direction = baseband::Direction::Receive;
|
||||||
baseband_thread.baseband_processor = new NarrowbandAMAudio();
|
baseband_thread.baseband_processor = new NarrowbandAMAudio();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 1:
|
case RX_NBFM_AUDIO:
|
||||||
direction = baseband::Direction::Receive;
|
direction = baseband::Direction::Receive;
|
||||||
baseband_thread.baseband_processor = new NarrowbandFMAudio();
|
baseband_thread.baseband_processor = new NarrowbandFMAudio();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 2:
|
case RX_WBFM_AUDIO:
|
||||||
baseband_thread.baseband_processor = new WidebandFMAudio();
|
baseband_thread.baseband_processor = new WidebandFMAudio();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
/*case 3:
|
case RX_AIS:
|
||||||
direction = baseband::Direction::Receive;
|
direction = baseband::Direction::Receive;
|
||||||
baseband_thread.baseband_processor = new AISProcessor();
|
baseband_thread.baseband_processor = new AISProcessor();
|
||||||
break;*/
|
break;
|
||||||
|
|
||||||
case 4:
|
case RX_WBSPECTRUM:
|
||||||
direction = baseband::Direction::Receive;
|
direction = baseband::Direction::Receive;
|
||||||
baseband_thread.baseband_processor = new WidebandSpectrum();
|
baseband_thread.baseband_processor = new WidebandSpectrum();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
/*case 5:
|
case RX_TPMS:
|
||||||
direction = baseband::Direction::Receive;
|
direction = baseband::Direction::Receive;
|
||||||
baseband_thread.baseband_processor = new TPMSProcessor();
|
baseband_thread.baseband_processor = new TPMSProcessor();
|
||||||
break;*/
|
break;
|
||||||
|
|
||||||
case 6:
|
case RX_AFSK:
|
||||||
direction = baseband::Direction::Receive;
|
direction = baseband::Direction::Receive;
|
||||||
baseband_thread.baseband_processor = new AFSKRXProcessor();
|
baseband_thread.baseband_processor = new AFSKRXProcessor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 7:
|
case RX_SIGFOX:
|
||||||
direction = baseband::Direction::Receive;
|
direction = baseband::Direction::Receive;
|
||||||
baseband_thread.baseband_processor = new SIGFRXProcessor();
|
baseband_thread.baseband_processor = new SIGFRXProcessor();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 0xFF:
|
case SWITCH:
|
||||||
wait_for_switch();
|
wait_for_switch();
|
||||||
|
|
||||||
default:
|
default:
|
||||||
|
69
firmware/baseband/proc_sigfrx.cpp
Normal file
69
firmware/baseband/proc_sigfrx.cpp
Normal file
@ -0,0 +1,69 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
|
||||||
|
*
|
||||||
|
* This file is part of PortaPack.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation; either version 2, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; see the file COPYING. If not, write to
|
||||||
|
* the Free Software Foundation, Inc., 51 Franklin Street,
|
||||||
|
* Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "proc_sigfrx.hpp"
|
||||||
|
|
||||||
|
#include <cstdint>
|
||||||
|
#include <cstddef>
|
||||||
|
|
||||||
|
void SIGFRXProcessor::execute(buffer_c8_t buffer) {
|
||||||
|
/* Called every 2048/3072000 second -- 1500Hz. */
|
||||||
|
|
||||||
|
auto decimator_out = decimator.execute(buffer);
|
||||||
|
|
||||||
|
const buffer_c16_t work_baseband_buffer {
|
||||||
|
(complex16_t*)decimator_out.p,
|
||||||
|
sizeof(*decimator_out.p) * decimator_out.count
|
||||||
|
};
|
||||||
|
|
||||||
|
/* 192kHz complex<int16_t>[64]
|
||||||
|
* -> 96kHz int16_t[32] */
|
||||||
|
//auto channel = channel_filter.execute(decimator_out, work_baseband_buffer);
|
||||||
|
|
||||||
|
// TODO: Feed channel_stats post-decimation data?
|
||||||
|
feed_channel_spectrum(
|
||||||
|
decimator_out,
|
||||||
|
41000, //decimator_out.sampling_rate * channel_filter_taps.pass_frequency_normalized,
|
||||||
|
70000 //decimator_out.sampling_rate * channel_filter_taps.stop_frequency_normalized
|
||||||
|
);
|
||||||
|
|
||||||
|
/*const buffer_s16_t work_audio_buffer {
|
||||||
|
(int16_t*)decimator_out.p,
|
||||||
|
sizeof(*decimator_out.p) * decimator_out.count
|
||||||
|
};
|
||||||
|
*
|
||||||
|
auto audio = demod.execute(channel, work_audio_buffer);
|
||||||
|
|
||||||
|
static uint64_t audio_present_history = 0;
|
||||||
|
const auto audio_present_now = squelch.execute(audio);
|
||||||
|
audio_present_history = (audio_present_history << 1) | (audio_present_now ? 1 : 0);
|
||||||
|
const bool audio_present = (audio_present_history != 0);
|
||||||
|
|
||||||
|
if( !audio_present ) {
|
||||||
|
// Zero audio buffer.
|
||||||
|
for(size_t i=0; i<audio.count; i++) {
|
||||||
|
audio.p[i] = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
audio_hpf.execute_in_place(audio);
|
||||||
|
fill_audio_buffer(audio);*/
|
||||||
|
}
|
54
firmware/baseband/proc_sigfrx.hpp
Normal file
54
firmware/baseband/proc_sigfrx.hpp
Normal file
@ -0,0 +1,54 @@
|
|||||||
|
/*
|
||||||
|
* Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc.
|
||||||
|
*
|
||||||
|
* This file is part of PortaPack.
|
||||||
|
*
|
||||||
|
* This program is free software; you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation; either version 2, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; see the file COPYING. If not, write to
|
||||||
|
* the Free Software Foundation, Inc., 51 Franklin Street,
|
||||||
|
* Boston, MA 02110-1301, USA.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __PROC_SIGFRX_H__
|
||||||
|
#define __PROC_SIGFRX_H__
|
||||||
|
|
||||||
|
#include "baseband_processor.hpp"
|
||||||
|
|
||||||
|
#include "channel_decimator.hpp"
|
||||||
|
#include "dsp_decimate.hpp"
|
||||||
|
#include "dsp_demodulate.hpp"
|
||||||
|
#include "dsp_fir_taps.hpp"
|
||||||
|
#include "dsp_iir.hpp"
|
||||||
|
#include "dsp_iir_config.hpp"
|
||||||
|
#include "dsp_squelch.hpp"
|
||||||
|
|
||||||
|
class SIGFRXProcessor : public BasebandProcessor {
|
||||||
|
public:
|
||||||
|
SIGFRXProcessor() {
|
||||||
|
decimator.set_decimation_factor(ChannelDecimator::DecimationFactor::By16);
|
||||||
|
//channel_filter.configure(channel_filter_taps.taps, 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void execute(buffer_c8_t buffer) override;
|
||||||
|
|
||||||
|
private:
|
||||||
|
ChannelDecimator decimator;
|
||||||
|
//const fir_taps_real<64>& channel_filter_taps = taps_64_lp_410_700_tfilter; //taps_64_lp_104_140_tfilter
|
||||||
|
//dsp::decimate::FIRAndDecimateComplex channel_filter;
|
||||||
|
dsp::demodulate::FM demod { 48000, 7500 };
|
||||||
|
|
||||||
|
IIRBiquadFilter audio_hpf { audio_hpf_config };
|
||||||
|
FMSquelch squelch;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
@ -159,13 +159,33 @@ public:
|
|||||||
AudioStatistics statistics;
|
AudioStatistics statistics;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
RX_NBAM_AUDIO = 0,
|
||||||
|
RX_NBFM_AUDIO,
|
||||||
|
RX_WBFM_AUDIO,
|
||||||
|
RX_AIS,
|
||||||
|
RX_WBSPECTRUM,
|
||||||
|
RX_TPMS,
|
||||||
|
RX_AFSK,
|
||||||
|
RX_SIGFOX,
|
||||||
|
|
||||||
|
TX_RDS,
|
||||||
|
TX_LCR,
|
||||||
|
TX_TONE,
|
||||||
|
TX_JAMMER,
|
||||||
|
TX_XYLOS,
|
||||||
|
|
||||||
|
NONE,
|
||||||
|
SWITCH = 0xFF
|
||||||
|
} mode_type;
|
||||||
|
|
||||||
struct BasebandConfiguration {
|
struct BasebandConfiguration {
|
||||||
int32_t mode;
|
mode_type mode;
|
||||||
uint32_t sampling_rate;
|
uint32_t sampling_rate;
|
||||||
size_t decimation_factor;
|
size_t decimation_factor;
|
||||||
|
|
||||||
constexpr BasebandConfiguration(
|
constexpr BasebandConfiguration(
|
||||||
int32_t mode = -1,
|
mode_type mode = NONE,
|
||||||
uint32_t sampling_rate = 0,
|
uint32_t sampling_rate = 0,
|
||||||
size_t decimation_factor = 1
|
size_t decimation_factor = 1
|
||||||
) : mode { mode },
|
) : mode { mode },
|
||||||
|
2
firmware/common/modules.h
Normal file
2
firmware/common/modules.h
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
const char md5_baseband[16] = {0x20,0xb7,0x1a,0x68,0x28,0xda,0xc9,0xb8,0x01,0xb0,0xbd,0x68,0x0d,0xd5,0xd6,0xa7,};
|
||||||
|
const char md5_baseband_tx[16] = {0xe5,0x29,0xb9,0xf0,0x81,0x50,0x45,0x69,0x24,0xaf,0xdd,0x4e,0xdb,0xaf,0xd8,0x97,};
|
Binary file not shown.
@ -1,9 +1,7 @@
|
|||||||
#!/usr/bin/env python
|
#!/usr/bin/env python
|
||||||
|
|
||||||
#
|
#
|
||||||
# Copyright (C) 2015 Jared Boone, ShareBrained Technology, Inc.
|
# Copyright (C) 2016 Furrtek
|
||||||
#
|
|
||||||
# This file is part of PortaPack.
|
|
||||||
#
|
#
|
||||||
# This program is free software; you can redistribute it and/or modify
|
# This program is free software; you can redistribute it and/or modify
|
||||||
# it under the terms of the GNU General Public License as published by
|
# it under the terms of the GNU General Public License as published by
|
||||||
@ -89,4 +87,4 @@ for args in sys.argv:
|
|||||||
md5sum += '0x' + format(byte, '02x') + ','
|
md5sum += '0x' + format(byte, '02x') + ','
|
||||||
h_data += 'const char md5_' + args.replace('-','_') + '[16] = {' + md5sum + '};\n'
|
h_data += 'const char md5_' + args.replace('-','_') + '[16] = {' + md5sum + '};\n'
|
||||||
|
|
||||||
write_file(h_data, 'application/modules.h')
|
write_file(h_data, 'common/modules.h')
|
||||||
|
Loading…
Reference in New Issue
Block a user