A-Netz: Option to set gain of paging tones

This commit is contained in:
Andreas Eversberg
2017-01-08 11:22:24 +01:00
parent d28467c125
commit bf0abd627d
6 changed files with 46 additions and 29 deletions

View File

@@ -287,12 +287,20 @@ If the phone does not indicate an incoming call, increase the volume of the tran
Also be sure that you are actually dialing the right number, so the base station generates the correct paging tones for your phone. Also be sure that you are actually dialing the right number, so the base station generates the correct paging tones for your phone.
</p> </p>
<p>
As there is no emphasis, a transmitter with pre-emphasis will drastically lower the paging tones.
If you cannot disable pre-emphasis on the transmitter, try to raise the gain of the paging tones.
Add command "-V 12" to increase gain.
The frequency deviation of all 4 tones should be around 11 kHz.
</p>
<p> <p>
Instead of transmitting all 4 tones at once, they can be transmitted after each other. Instead of transmitting all 4 tones at once, they can be transmitted after each other.
Each tone is plays for a short time. Each tone is plays for a short time.
After the last tone has been played, base station starts again with the first tone. After the last tone has been played, base station starts again with the first tone.
My phone also responds to a call, even if the tones cycle rather than sent simultaneously. My phone also responds to a call, even if the tones cycle rather than sent simultaneously.
In this case the deviation level of each tone is two times higher (+6 dB). (The level transmitted is two times lower (-6 dB) than the peak level of 4 simultaneous tones. This may help transmitters with deviation limiters to make the phone ring.) In this case the deviation level of each tone is four times higher (+12 dB).
This may help transmitters with deviation limiters to make the phone ring.)
Add command line option "-P 100" to send each tone for 100 milliseconds. Add command line option "-P 100" to send each tone for 100 milliseconds.
Try something between 50-200 milliseconds, if the phone still doesn't ring. Try something between 50-200 milliseconds, if the phone still doesn't ring.
Be sure to check: Does your transmitter has enough frequency deviation (15 KHz is suggested)? Do you really send the correct number of your phone, check the frequencies of your phone and use "-D 0" option to see what 4 frequencies the base station actually transmits. Be sure to check: Does your transmitter has enough frequency deviation (15 KHz is suggested)? Do you really send the correct number of your phone, check the frequencies of your phone and use "-D 0" option to see what 4 frequencies the base station actually transmits.

View File

@@ -168,7 +168,7 @@ static void anetz_timeout(struct timer *timer);
static void anetz_go_idle(anetz_t *anetz); static void anetz_go_idle(anetz_t *anetz);
/* Create transceiver instance and link to a list. */ /* Create transceiver instance and link to a list. */
int anetz_create(int kanal, const char *audiodev, int samplerate, double rx_gain, int page_sequence, int pre_emphasis, int de_emphasis, const char *write_rx_wave, const char *write_tx_wave, const char *read_rx_wave, int loopback, double loss_volume) int anetz_create(int kanal, const char *audiodev, int samplerate, double rx_gain, double page_gain, int page_sequence, int pre_emphasis, int de_emphasis, const char *write_rx_wave, const char *write_tx_wave, const char *read_rx_wave, int loopback, double loss_volume)
{ {
anetz_t *anetz; anetz_t *anetz;
int rc; int rc;
@@ -194,7 +194,7 @@ int anetz_create(int kanal, const char *audiodev, int samplerate, double rx_gain
} }
/* init audio processing */ /* init audio processing */
rc = dsp_init_sender(anetz, page_sequence); rc = dsp_init_sender(anetz, page_gain, page_sequence);
if (rc < 0) { if (rc < 0) {
PDEBUG(DANETZ, DEBUG_ERROR, "Failed to init signal processing!\n"); PDEBUG(DANETZ, DEBUG_ERROR, "Failed to init signal processing!\n");
goto error; goto error;

View File

@@ -34,6 +34,7 @@ typedef struct anetz {
int tone_count; /* how long has that tone been detected */ int tone_count; /* how long has that tone been detected */
double tone_phaseshift256; /* how much the phase of sine wave changes per sample */ double tone_phaseshift256; /* how much the phase of sine wave changes per sample */
double tone_phase256; /* current phase */ double tone_phase256; /* current phase */
double page_gain; /* factor to raise the paging tones */
int page_sequence; /* if set, use paging tones in sequence rather than parallel */ int page_sequence; /* if set, use paging tones in sequence rather than parallel */
double paging_phaseshift256[4];/* how much the phase of sine wave changes per sample */ double paging_phaseshift256[4];/* how much the phase of sine wave changes per sample */
double paging_phase256[4]; /* current phase */ double paging_phase256[4]; /* current phase */
@@ -45,7 +46,7 @@ typedef struct anetz {
double anetz_kanal2freq(int kanal, int unterband); double anetz_kanal2freq(int kanal, int unterband);
int anetz_init(void); int anetz_init(void);
int anetz_create(int kanal, const char *audiodev, int samplerate, double rx_gain, int page_sequence, int pre_emphasis, int de_emphasis, const char *write_rx_wave, const char *write_tx_wave, const char *read_rx_wave, int loopback, double loss_volume); int anetz_create(int kanal, const char *audiodev, int samplerate, double rx_gain, double page_gain, int page_sequence, int pre_emphasis, int de_emphasis, const char *write_rx_wave, const char *write_tx_wave, const char *read_rx_wave, int loopback, double loss_volume);
void anetz_destroy(sender_t *sender); void anetz_destroy(sender_t *sender);
void anetz_loss_indication(anetz_t *anetz); void anetz_loss_indication(anetz_t *anetz);
void anetz_receive_tone(anetz_t *anetz, int bit); void anetz_receive_tone(anetz_t *anetz, int bit);

View File

@@ -37,8 +37,6 @@
/* signaling */ /* signaling */
#define BANDWIDTH 15000.0 /* maximum bandwidth */ #define BANDWIDTH 15000.0 /* maximum bandwidth */
#define TX_PEAK_TONE 8192.0 /* peak amplitude for all tones */ #define TX_PEAK_TONE 8192.0 /* peak amplitude for all tones */
#warning FIXME: only with emphasis, use seperate option for volume, override by sdr
#define TX_PEAK_PAGE 32766.0 /* peak amplitude paging tone */
#define CHUNK_DURATION 0.010 /* 10 ms */ #define CHUNK_DURATION 0.010 /* 10 ms */
// FIXME: how long until we detect a tone? // FIXME: how long until we detect a tone?
@@ -56,7 +54,6 @@ static double fsk_tones[2] = {
/* table for fast sine generation */ /* table for fast sine generation */
int dsp_sine_tone[256]; int dsp_sine_tone[256];
int dsp_sine_page[256];
/* global init for audio processing */ /* global init for audio processing */
void dsp_init(void) void dsp_init(void)
@@ -68,22 +65,16 @@ void dsp_init(void)
for (i = 0; i < 256; i++) { for (i = 0; i < 256; i++) {
s = sin((double)i / 256.0 * 2.0 * PI); s = sin((double)i / 256.0 * 2.0 * PI);
dsp_sine_tone[i] = (int)(s * TX_PEAK_TONE); dsp_sine_tone[i] = (int)(s * TX_PEAK_TONE);
s = cos((double)i / 256.0 * 2.0 * PI);
dsp_sine_page[i] = (int)(s * TX_PEAK_PAGE);
} }
if (TX_PEAK_TONE > 32767.0) { if (TX_PEAK_TONE > 32767.0) {
fprintf(stderr, "TX_PEAK_TONE definition too high, please fix!\n"); fprintf(stderr, "TX_PEAK_TONE definition too high, please fix!\n");
abort(); abort();
} }
if (TX_PEAK_PAGE > 32767.0) {
fprintf(stderr, "TX_PEAK_PAGE definition too high, please fix!\n");
abort();
}
} }
/* Init transceiver instance. */ /* Init transceiver instance. */
int dsp_init_sender(anetz_t *anetz, int page_sequence) int dsp_init_sender(anetz_t *anetz, double page_gain, int page_sequence)
{ {
int16_t *spl; int16_t *spl;
double coeff; double coeff;
@@ -96,6 +87,11 @@ int dsp_init_sender(anetz_t *anetz, int page_sequence)
anetz->sender.bandwidth = BANDWIDTH; anetz->sender.bandwidth = BANDWIDTH;
anetz->sender.sample_deviation = 11000.0 / (double)TX_PEAK_TONE; anetz->sender.sample_deviation = 11000.0 / (double)TX_PEAK_TONE;
anetz->page_gain = page_gain;
if (page_gain * TX_PEAK_TONE > 32767.0) {
page_gain = 32767.0 / TX_PEAK_TONE;
PDEBUG_CHAN(DDSP, DEBUG_NOTICE, "Highest possible gain of paging tones is %.1f dB.\n", log10(page_gain) * 20);
}
anetz->page_sequence = page_sequence; anetz->page_sequence = page_sequence;
audio_init_loss(&anetz->sender.loss, LOSS_INTERVAL, anetz->sender.loss_volume, LOSS_TIME); audio_init_loss(&anetz->sender.loss, LOSS_INTERVAL, anetz->sender.loss_volume, LOSS_TIME);
@@ -245,12 +241,12 @@ void dsp_set_paging(anetz_t *anetz, double *freq)
} }
/* Generate audio stream of 4 simultanious paging tones. Keep phase for next call of function. /* Generate audio stream of 4 simultanious paging tones. Keep phase for next call of function.
* Use TX_PEAK_PAGE for all tones, which gives peak of (TX_PEAK_PAGE / 4) for each individual tone. */ * Use TX_PEAK_TONE*page_gain for all tones, which gives peak of 1/4th for each individual tone. */
static void fsk_paging_tone(anetz_t *anetz, int16_t *samples, int length) static void fsk_paging_tone(anetz_t *anetz, int16_t *samples, int length)
{ {
double phaseshift[4], phase[4]; double phaseshift[4], phase[4];
int i; int i;
int32_t sample; double sample;
for (i = 0; i < 4; i++) { for (i = 0; i < 4; i++) {
phaseshift[i] = anetz->paging_phaseshift256[i]; phaseshift[i] = anetz->paging_phaseshift256[i];
@@ -258,11 +254,11 @@ static void fsk_paging_tone(anetz_t *anetz, int16_t *samples, int length)
} }
for (i = 0; i < length; i++) { for (i = 0; i < length; i++) {
sample = (int32_t)dsp_sine_page[((uint8_t)phase[0]) & 0xff] sample = (int32_t)dsp_sine_tone[((uint8_t)phase[0]) & 0xff]
+ (int32_t)dsp_sine_page[((uint8_t)phase[1]) & 0xff] + (int32_t)dsp_sine_tone[((uint8_t)phase[1]) & 0xff]
+ (int32_t)dsp_sine_page[((uint8_t)phase[2]) & 0xff] + (int32_t)dsp_sine_tone[((uint8_t)phase[2]) & 0xff]
+ (int32_t)dsp_sine_page[((uint8_t)phase[3]) & 0xff]; + (int32_t)dsp_sine_tone[((uint8_t)phase[3]) & 0xff];
*samples++ = sample >> 2; *samples++ = sample / 4.0 * anetz->page_gain;
phase[0] += phaseshift[0]; phase[0] += phaseshift[0];
phase[1] += phaseshift[1]; phase[1] += phaseshift[1];
phase[2] += phaseshift[2]; phase[2] += phaseshift[2];
@@ -281,7 +277,7 @@ static void fsk_paging_tone(anetz_t *anetz, int16_t *samples, int length)
/* Generate audio stream of 4 sequenced paging tones. Keep phase for next call /* Generate audio stream of 4 sequenced paging tones. Keep phase for next call
* of function. * of function.
* *
* Use TX_PEAK_PAGE / 2 for each tone, that is twice as much peak per tone. * Use TX_PEAK_PAGE for each tone, that is four times higher per tone.
* *
* Click removal when changing tones that have individual phase: * Click removal when changing tones that have individual phase:
* When tone changes to next tone, a transition of 2ms is performed. The last * When tone changes to next tone, a transition of 2ms is performed. The last
@@ -304,12 +300,12 @@ static void fsk_paging_tone_sequence(anetz_t *anetz, int16_t *samples, int lengt
while (length) { while (length) {
/* use tone, but during transition of tones, keep phase 0 degrees (high level) until next tone reaches 0 degrees (high level) */ /* use tone, but during transition of tones, keep phase 0 degrees (high level) until next tone reaches 0 degrees (high level) */
if (!transition) if (!transition)
*samples++ = dsp_sine_page[((uint8_t)phase[tone]) & 0xff] >> 1; *samples++ = dsp_sine_tone[((uint8_t)phase[tone]) & 0xff] * anetz->page_gain;
else { else {
/* fade between old an new tone */ /* fade between old an new tone */
*samples++ *samples++
= (double)dsp_sine_page[((uint8_t)phase[(tone - 1) & 3]) & 0xff] * (double)(transition - count) / (double)transition / 2.0 = (double)dsp_sine_tone[((uint8_t)phase[(tone - 1) & 3]) & 0xff] * (double)(transition - count) / (double)transition / 2.0 * anetz->page_gain
+ (double)dsp_sine_page[((uint8_t)phase[tone]) & 0xff] * (double)count / (double)transition / 2.0; + (double)dsp_sine_tone[((uint8_t)phase[tone]) & 0xff] * (double)count / (double)transition / 2.0 * anetz->page_gain;
} }
phase[0] += phaseshift[0]; phase[0] += phaseshift[0];
phase[1] += phaseshift[1]; phase[1] += phaseshift[1];

View File

@@ -1,6 +1,6 @@
void dsp_init(void); void dsp_init(void);
int dsp_init_sender(anetz_t *anetz, int page_seqeuence); int dsp_init_sender(anetz_t *anetz, double page_gain, int page_seqeuence);
void dsp_cleanup_sender(anetz_t *anetz); void dsp_cleanup_sender(anetz_t *anetz);
void dsp_set_paging(anetz_t *anetz, double *freq); void dsp_set_paging(anetz_t *anetz, double *freq);
void anetz_set_dsp_mode(anetz_t *anetz, enum dsp_mode mode, int detect_reset); void anetz_set_dsp_mode(anetz_t *anetz, enum dsp_mode mode, int detect_reset);

View File

@@ -22,6 +22,7 @@
#include <getopt.h> #include <getopt.h>
#include <stdlib.h> #include <stdlib.h>
#include <string.h> #include <string.h>
#include <math.h>
#include "../common/main.h" #include "../common/main.h"
#include "../common/debug.h" #include "../common/debug.h"
#include "../common/timer.h" #include "../common/timer.h"
@@ -35,17 +36,21 @@
#include "image.h" #include "image.h"
/* settings */ /* settings */
double page_gain = 1;
int page_sequence = 0; int page_sequence = 0;
double lossdetect = 0; double lossdetect = 0;
void print_help(const char *arg0) void print_help(const char *arg0)
{ {
print_help_common(arg0, ""); print_help_common(arg0, "[-V 12] ");
/* - - */ /* - - */
printf(" -G --geo <lat>,<lon>\n"); printf(" -G --geo <lat>,<lon>\n");
printf(" Give your coordinates of your location, to find closest base station.\n"); printf(" Give your coordinates of your location, to find closest base station.\n");
printf(" (e.g. '--geo 51.186959,7.080194') Or use '--geo list' to get a list of\n"); printf(" (e.g. '--geo 51.186959,7.080194') Or use '--geo list' to get a list of\n");
printf(" all base station locations.\n"); printf(" all base station locations.\n");
printf(" -V --page-gain <dB>\n");
printf(" Raise the gain of paging tones to compensate loss due to pre-emphasis\n");
printf(" of the transmitter. (If you can't disable it.)\n");
printf(" -P --page-sequence 0 | <ms>\n"); printf(" -P --page-sequence 0 | <ms>\n");
printf(" Cycle paging tones, rather than sending simultaniously. Try 100.\n"); printf(" Cycle paging tones, rather than sending simultaniously. Try 100.\n");
printf(" (default = '%d')\n", page_sequence); printf(" (default = '%d')\n", page_sequence);
@@ -61,15 +66,17 @@ static int handle_options(int argc, char **argv)
{ {
int skip_args = 0; int skip_args = 0;
char *p; char *p;
double gain_db;
static struct option long_options_special[] = { static struct option long_options_special[] = {
{"geo", 1, 0, 'G'}, {"geo", 1, 0, 'G'},
{"page-gain", 1, 0, 'V'},
{"page-sequence", 1, 0, 'P'}, {"page-sequence", 1, 0, 'P'},
{"loss", 1, 0, 'L'}, {"loss", 1, 0, 'L'},
{0, 0, 0, 0} {0, 0, 0, 0}
}; };
set_options_common("G:P:L:", long_options_special); set_options_common("G:V:P:L:", long_options_special);
while (1) { while (1) {
int option_index = 0, c; int option_index = 0, c;
@@ -92,6 +99,11 @@ static int handle_options(int argc, char **argv)
fprintf(stderr, "Invalid geo parameter\n"); fprintf(stderr, "Invalid geo parameter\n");
exit(0); exit(0);
break; break;
case 'V':
gain_db = atof(optarg);
page_gain = pow(10, gain_db / 20.0);
skip_args += 2;
break;
case 'P': case 'P':
page_sequence = atoi(optarg); page_sequence = atoi(optarg);
skip_args += 2; skip_args += 2;
@@ -171,7 +183,7 @@ int main(int argc, char *argv[])
/* create transceiver instance */ /* create transceiver instance */
for (i = 0; i < num_kanal; i++) { for (i = 0; i < num_kanal; i++) {
rc = anetz_create(kanal[i], audiodev[i], samplerate, rx_gain, page_sequence, do_pre_emphasis, do_de_emphasis, write_rx_wave, write_tx_wave, read_rx_wave, loopback, lossdetect / 100.0); rc = anetz_create(kanal[i], audiodev[i], samplerate, rx_gain, page_gain, page_sequence, do_pre_emphasis, do_de_emphasis, write_rx_wave, write_tx_wave, read_rx_wave, loopback, lossdetect / 100.0);
if (rc < 0) { if (rc < 0) {
fprintf(stderr, "Failed to create \"Sender\" instance. Quitting!\n"); fprintf(stderr, "Failed to create \"Sender\" instance. Quitting!\n");
goto fail; goto fail;