kopia lustrzana https://github.com/jamescoxon/dl-fldigi
Waterfall race condition
* Some methods in waterfall are being called before a modem has been instantiated. Possibly due to threads being assigned to separate cpu processors. This cannot happen on h/w with a single cpu thread implementation.pull/1/head
rodzic
35a6486a2b
commit
f7ea783c0f
|
@ -204,6 +204,7 @@ void WFdisp::initMarkers() {
|
|||
// draw a marker of specified width and colour centred at freq and clrM
|
||||
inline void WFdisp::makeMarker_(int width, const RGB* color, int freq, const RGB* clrMin, RGB* clrM, const RGB* clrMax)
|
||||
{
|
||||
if (!active_modem) return;
|
||||
trx_mode marker_mode = active_modem->get_mode();
|
||||
if (marker_mode == MODE_RTTY) {
|
||||
// rtty has two bandwidth indicators on the waterfall
|
||||
|
@ -340,7 +341,6 @@ void WFdisp::makeMarker()
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
void WFdisp::makeScale() {
|
||||
uchar *gmap = scaleimage;
|
||||
int hwidth = step / 2;
|
||||
|
@ -629,7 +629,7 @@ void WFdisp::sig_data( double *sig, int len, int sr )
|
|||
|
||||
update_freq:
|
||||
static char szFrequency[14];
|
||||
if (rfc != 0) { // use a boolean for the waterfall
|
||||
if (active_modem && rfc != 0) { // use a boolean for the waterfall
|
||||
int cwoffset = 0;
|
||||
int rttyoffset = 0;
|
||||
trx_mode mode = active_modem->get_mode();
|
||||
|
@ -857,7 +857,7 @@ case Step: for (int row = 0; row < image_height; row++) { \
|
|||
}
|
||||
#undef UPD_LOOP
|
||||
|
||||
if (progdefaults.UseBWTracks) {
|
||||
if (active_modem && progdefaults.UseBWTracks) {
|
||||
int bw_lo = bandwidth / 2;
|
||||
int bw_hi = bandwidth / 2;
|
||||
trx_mode mode = active_modem->get_mode();
|
||||
|
@ -922,7 +922,8 @@ void WFdisp::drawcolorWF() {
|
|||
|
||||
update_waterfall();
|
||||
|
||||
if (wantcursor && (progdefaults.UseCursorLines || progdefaults.UseCursorCenterLine) ) {
|
||||
if (active_modem && wantcursor &&
|
||||
(progdefaults.UseCursorLines || progdefaults.UseCursorCenterLine) ) {
|
||||
trx_mode mode = active_modem->get_mode();
|
||||
int bw_lo = bandwidth / 2;
|
||||
int bw_hi = bandwidth / 2;
|
||||
|
@ -960,45 +961,6 @@ void WFdisp::drawcolorWF() {
|
|||
drawScale();
|
||||
}
|
||||
|
||||
/*
|
||||
// following method is not used in versions > 3.12
|
||||
void WFdisp::drawgrayWF() {
|
||||
uchar *pixmap = (uchar*)fft_img;
|
||||
|
||||
update_waterfall();
|
||||
|
||||
if (wantcursor && (progdefaults.UseCursorLines || progdefaults.UseCursorCenterLine) ) {
|
||||
trx_mode mode = active_modem->get_mode();
|
||||
int bw_lo = bandwidth / 2;
|
||||
int bw_hi = bandwidth / 2;
|
||||
if (mode >= MODE_MT63_500S && mode <= MODE_MT63_2000L)
|
||||
bw_hi = bw_hi * 31 / 32;
|
||||
RGBI *pos0 = (fft_img + cursorpos);
|
||||
RGBI *pos1 = (fft_img + cursorpos - bw_lo/step);
|
||||
RGBI *pos2 = (fft_img + cursorpos + bw_hi/step);
|
||||
if (pos1 >= fft_img && pos2 < fft_img + disp_width)
|
||||
for (int y = 0; y < image_height; y ++) {
|
||||
if (progdefaults.UseCursorLines)
|
||||
*pos1 = *pos2 = progdefaults.cursorLineRGBI;
|
||||
if (progdefaults.UseCursorCenterLine)
|
||||
*pos0 = progdefaults.cursorCenterRGBI;
|
||||
pos0 += disp_width;
|
||||
pos1 += disp_width;
|
||||
pos2 += disp_width;
|
||||
}
|
||||
}
|
||||
|
||||
fl_color(FL_BLACK);
|
||||
fl_rectf(x(), y(), w(), WFSCALE + WFMARKER + WFTEXT + image_height);
|
||||
|
||||
fl_draw_image_mono(
|
||||
pixmap + 3,
|
||||
x(), y() + WFSCALE + WFMARKER + WFTEXT,
|
||||
disp_width, image_height,
|
||||
sizeof(RGBI), disp_width * sizeof(RGBI));
|
||||
drawScale();
|
||||
}
|
||||
*/
|
||||
void WFdisp::drawspectrum() {
|
||||
int sig;
|
||||
int ynext,
|
||||
|
@ -1040,7 +1002,8 @@ void WFdisp::drawspectrum() {
|
|||
pos2 += IMAGE_WIDTH/step;
|
||||
}
|
||||
}
|
||||
if (wantcursor && (progdefaults.UseCursorLines || progdefaults.UseCursorCenterLine)) {
|
||||
if (active_modem && wantcursor &&
|
||||
(progdefaults.UseCursorLines || progdefaults.UseCursorCenterLine)) {
|
||||
trx_mode mode = active_modem->get_mode();
|
||||
int bw_lo = bandwidth / 2;
|
||||
int bw_hi = bandwidth / 2;
|
||||
|
@ -1153,13 +1116,14 @@ void carrier_cb(Fl_Widget *w, void *v) {
|
|||
int selfreq = (int) cntr->value();
|
||||
if (selfreq > progdefaults.HighFreqCutoff) selfreq = progdefaults.HighFreqCutoff - wf->wfdisp->Bandwidth() / 2;
|
||||
stopMacroTimer();
|
||||
active_modem->set_freq(selfreq);
|
||||
if (active_modem) active_modem->set_freq(selfreq);
|
||||
wf->wfdisp->carrier(selfreq);
|
||||
restoreFocus();
|
||||
}
|
||||
|
||||
void do_qsy(bool dir)
|
||||
{
|
||||
if (!active_modem) return;
|
||||
static vector<qrg_mode_t> qsy_stack;
|
||||
qrg_mode_t m;
|
||||
|
||||
|
@ -1234,6 +1198,7 @@ void rate_cb(Fl_Widget *w, void *v) {
|
|||
|
||||
void xmtrcv_cb(Fl_Widget *w, void *vi)
|
||||
{
|
||||
if (!active_modem) return;
|
||||
FL_LOCK_D();
|
||||
Fl_Light_Button *b = (Fl_Light_Button *)w;
|
||||
int v = b->value();
|
||||
|
@ -1267,6 +1232,7 @@ void xmtrcv_cb(Fl_Widget *w, void *vi)
|
|||
|
||||
void xmtlock_cb(Fl_Widget *w, void *vi)
|
||||
{
|
||||
if (!active_modem) return;
|
||||
FL_LOCK_D();
|
||||
Fl_Light_Button *b = (Fl_Light_Button *)w;
|
||||
int v = b->value();
|
||||
|
@ -1325,7 +1291,9 @@ void ampspan_cb(Fl_Widget *w, void *v) {
|
|||
restoreFocus();
|
||||
}
|
||||
|
||||
void btnRev_cb(Fl_Widget *w, void *v) {
|
||||
void btnRev_cb(Fl_Widget *w, void *v)
|
||||
{
|
||||
if (!active_modem) return;
|
||||
FL_LOCK_D();
|
||||
waterfall *wf = (waterfall *)w->parent();
|
||||
Fl_Light_Button *b = (Fl_Light_Button *)w;
|
||||
|
@ -1339,6 +1307,7 @@ void btnRev_cb(Fl_Widget *w, void *v) {
|
|||
|
||||
void btnMem_cb(Fl_Widget *, void *menu_event)
|
||||
{
|
||||
if (!active_modem) return;
|
||||
static std::vector<qrg_mode_t> qrg_list;
|
||||
enum { SELECT, APPEND, REPLACE, REMOVE, CLEAR };
|
||||
int op = SELECT, elem = 0;
|
||||
|
@ -1432,6 +1401,7 @@ void btnMem_cb(Fl_Widget *, void *menu_event)
|
|||
}
|
||||
|
||||
void waterfall::opmode() {
|
||||
if (!active_modem) return;
|
||||
int val = (int)active_modem->get_bandwidth();
|
||||
|
||||
wfdisp->carrier((int)CLAMP(
|
||||
|
@ -1513,7 +1483,7 @@ int waterfall::Carrier()
|
|||
|
||||
void waterfall::Carrier(int f)
|
||||
{
|
||||
active_modem->set_freq(f);
|
||||
if (active_modem) active_modem->set_freq(f);
|
||||
}
|
||||
|
||||
void waterfall::rfcarrier(long long cf) {
|
||||
|
@ -1542,7 +1512,7 @@ void waterfall::USB(bool b) {
|
|||
if (wfdisp->USB() == b)
|
||||
return;
|
||||
wfdisp->USB(b);
|
||||
active_modem->set_reverse(reverse);
|
||||
if (active_modem) active_modem->set_reverse(reverse);
|
||||
REQ(&viewer_redraw);
|
||||
}
|
||||
|
||||
|
@ -1769,7 +1739,7 @@ int waterfall::handle(int event)
|
|||
|
||||
// this does not belong here, but we don't have access to this widget's
|
||||
// handle method (or its parent's)
|
||||
if (Fl::event_inside(MODEstatus)) {
|
||||
if (active_modem && Fl::event_inside(MODEstatus)) {
|
||||
trx_mode mode = active_modem->get_mode();
|
||||
for (;;) {
|
||||
mode = WCLAMP(mode + d, 0, NUM_MODES - 1);
|
||||
|
@ -1809,7 +1779,7 @@ static void hide_cursor(void *w)
|
|||
|
||||
void waterfall::insert_text(bool check)
|
||||
{
|
||||
if (check) {
|
||||
if (active_modem && check) {
|
||||
qrg_mode_t m;
|
||||
m.rfcarrier = wf->rfcarrier();
|
||||
m.carrier = active_modem->get_freq();
|
||||
|
@ -1836,6 +1806,7 @@ void waterfall::insert_text(bool check)
|
|||
|
||||
static void find_signal_text(void)
|
||||
{
|
||||
if (!active_modem) return;
|
||||
int freq = active_modem->get_freq();
|
||||
trx_mode mode = active_modem->get_mode();
|
||||
|
||||
|
@ -1924,7 +1895,7 @@ int WFdisp::handle(int event)
|
|||
if (!USB())
|
||||
newrfc = -newrfc;
|
||||
newrfc += rfcarrier();
|
||||
qsy(newrfc, active_modem->get_freq());
|
||||
qsy(newrfc, active_modem ? active_modem->get_freq() : 1500);
|
||||
pxpos = xpos;
|
||||
return 1;
|
||||
}
|
||||
|
@ -1942,14 +1913,16 @@ int WFdisp::handle(int event)
|
|||
if (progdefaults.WaterfallHistoryDefault)
|
||||
bHistory = true;
|
||||
newcarrier = cursorFreq(xpos);
|
||||
newcarrier = (int)CLAMP(
|
||||
newcarrier,
|
||||
progdefaults.LowFreqCutoff + active_modem->get_bandwidth() / 2,
|
||||
progdefaults.HighFreqCutoff - active_modem->get_bandwidth() / 2);
|
||||
active_modem->set_freq(newcarrier);
|
||||
viewer_paste_freq(newcarrier);
|
||||
if (!(Fl::event_state() & FL_SHIFT))
|
||||
active_modem->set_sigsearch(SIGSEARCH);
|
||||
if (active_modem) {
|
||||
newcarrier = (int)CLAMP(
|
||||
newcarrier,
|
||||
progdefaults.LowFreqCutoff + active_modem->get_bandwidth() / 2,
|
||||
progdefaults.HighFreqCutoff - active_modem->get_bandwidth() / 2);
|
||||
active_modem->set_freq(newcarrier);
|
||||
viewer_paste_freq(newcarrier);
|
||||
if (!(Fl::event_state() & FL_SHIFT))
|
||||
active_modem->set_sigsearch(SIGSEARCH);
|
||||
}
|
||||
redrawCursor();
|
||||
restoreFocus();
|
||||
break;
|
||||
|
@ -1968,7 +1941,7 @@ int WFdisp::handle(int event)
|
|||
switch (eb = Fl::event_button()) {
|
||||
case FL_RIGHT_MOUSE:
|
||||
tmp_carrier = false;
|
||||
active_modem->set_freq(oldcarrier);
|
||||
if (active_modem) active_modem->set_freq(oldcarrier);
|
||||
redrawCursor();
|
||||
restoreFocus();
|
||||
// fall through
|
||||
|
@ -2026,11 +1999,13 @@ int WFdisp::handle(int event)
|
|||
case FL_Left: case FL_Right:
|
||||
if (k == FL_Left)
|
||||
d = -d;
|
||||
oldcarrier = newcarrier = (int)CLAMP(
|
||||
carrier() + d,
|
||||
progdefaults.LowFreqCutoff + active_modem->get_bandwidth() / 2,
|
||||
progdefaults.HighFreqCutoff - active_modem->get_bandwidth() / 2);
|
||||
active_modem->set_freq(newcarrier);
|
||||
if (active_modem) {
|
||||
oldcarrier = newcarrier = (int)CLAMP(
|
||||
carrier() + d,
|
||||
progdefaults.LowFreqCutoff + active_modem->get_bandwidth() / 2,
|
||||
progdefaults.HighFreqCutoff - active_modem->get_bandwidth() / 2);
|
||||
active_modem->set_freq(newcarrier);
|
||||
}
|
||||
redrawCursor();
|
||||
break;
|
||||
case FL_Tab:
|
||||
|
@ -2081,30 +2056,32 @@ void waterfall::handle_mouse_wheel(int what, int d)
|
|||
return;
|
||||
case WF_AFC_BW:
|
||||
{
|
||||
trx_mode m = active_modem->get_mode();
|
||||
if (m >= MODE_PSK_FIRST && m <= MODE_PSK_LAST)
|
||||
val = mailserver ? cntServerOffset : cntSearchRange;
|
||||
else if (m >= MODE_HELL_FIRST && m <= MODE_HELL_LAST)
|
||||
val = sldrHellBW;
|
||||
else if (m >= MODE_HELL_FIRST && m <= MODE_HELL_LAST) {
|
||||
val = sldrHellBW;
|
||||
msg_label = "BW";
|
||||
if (active_modem) {
|
||||
trx_mode m = active_modem->get_mode();
|
||||
if (m >= MODE_PSK_FIRST && m <= MODE_PSK_LAST) {
|
||||
val = mailserver ? cntServerOffset : cntSearchRange;
|
||||
msg_label = "Srch Rng";
|
||||
}
|
||||
else if (m >= MODE_HELL_FIRST && m <= MODE_HELL_LAST) {
|
||||
val = sldrHellBW;
|
||||
msg_label = "BW";
|
||||
}
|
||||
else if (m == MODE_CW) {
|
||||
val = sldrCWbandwidth;
|
||||
msg_label = "BW";
|
||||
}
|
||||
else
|
||||
return;
|
||||
msg_fmt = "%s: %2.0f Hz";
|
||||
}
|
||||
else if (m == MODE_CW) {
|
||||
val = sldrCWbandwidth;
|
||||
msg_label = "BW";
|
||||
}
|
||||
else
|
||||
return;
|
||||
msg_fmt = "%s = %2.0f Hz";
|
||||
msg_label = val->label();
|
||||
break;
|
||||
}
|
||||
case WF_SIGNAL_SEARCH:
|
||||
if (d > 0)
|
||||
active_modem->searchDown();
|
||||
else
|
||||
active_modem->searchUp();
|
||||
if (d > 0) {
|
||||
if (active_modem) active_modem->searchDown();
|
||||
} else {
|
||||
if (active_modem) active_modem->searchUp();
|
||||
}
|
||||
return;
|
||||
case WF_SQUELCH:
|
||||
val = sldrSquelch;
|
||||
|
@ -2128,7 +2105,7 @@ void waterfall::handle_mouse_wheel(int what, int d)
|
|||
val->do_callback();
|
||||
progdefaults.changed = changed_save;
|
||||
if (val == cntServerOffset || val == cntSearchRange)
|
||||
active_modem->set_sigsearch(SIGSEARCH);
|
||||
if (active_modem) active_modem->set_sigsearch(SIGSEARCH);
|
||||
else if (val == sldrSquelch) // sldrSquelch gives focus to TransmitText
|
||||
take_focus();
|
||||
|
||||
|
|
Ładowanie…
Reference in New Issue