si-tools: FM configuration improvements
[AGL/meta-agl.git] / meta-agl-bsp / meta-rcar-gen3-adas / recipes-bsp / si-tools / files / si-tools-fm-improvements.patch
1 FM configuration improvements
2
3 Changes include:
4 - Add command-line option for selecting FM band plan.  The default
5   band plan is US / Canada.
6 - Add command-line options for setting FM scanning valid SNR and RSSI
7   thresholds to allow tweaking sensitivity in poor radio environments.
8 - Increased seeking scan timeout to 3 seconds, which seems to improve
9   behavior in poor radio environments where powerful stations may be
10   far apart.
11 - Removed explicit setting of FM_SOFTMUTE_SNR_LIMITS, as it seemed
12   like it might be resulting in odd muting behavior when scanning.
13 - Changed initial FM frequency if not specified to the minimum of the
14   band plan.
15
16 Signed-off-by: Scott Murray <scott.murray@konsulko.com>
17
18 diff --git a/si46xx.h b/si46xx.h
19 index 172ea8b..c32fca4 100644
20 --- a/si46xx.h
21 +++ b/si46xx.h
22 @@ -83,6 +83,7 @@
23  #define SI46XX_PIN_CONFIG_ENABLE 0x0800
24  #define SI46XX_FM_SEEK_BAND_BOTTOM 0x3100
25  #define SI46XX_FM_SEEK_BAND_TOP 0x3101
26 +#define SI46XX_FM_SEEK_FREQUENCY_SPACING 0x3102
27  #define SI46XX_FM_VALID_MAX_TUNE_ERROR 0x3200
28  #define SI46XX_FM_VALID_RSSI_TIME 0x3201
29  #define SI46XX_FM_VALID_RSSI_THRESHOLD 0x3202
30 @@ -150,7 +151,7 @@
31  #define MAX_SERVICES 32
32  #define MAX_COMPONENTS 15
33  
34 -#define TIMEOUT_SEEK   2000    /* mS = 2S */
35 +#define TIMEOUT_SEEK   3000    /* mS = 3S */
36  #define TIMEOUT_TUNE   500     /* mS = .5S */
37  
38  struct dab_service_t{
39 diff --git a/si_ctl.c b/si_ctl.c
40 index 59dfaf2..f168218 100644
41 --- a/si_ctl.c
42 +++ b/si_ctl.c
43 @@ -101,6 +101,26 @@ uint32_t frequency_list_ch[] = {   CHAN_12A,
44                                         CHAN_9D,
45                                         CHAN_8B};
46  
47 +// Structure to describe FM band plans, all values in Hz.
48 +typedef struct {
49 +       char *name;
50 +       uint32_t min;
51 +       uint32_t max;
52 +       uint32_t step;
53 +} fm_band_plan_t;
54 +
55 +static fm_band_plan_t known_fm_band_plans[5] = {
56 +       { .name = "US", .min = 87900000, .max = 107900000, .step = 200000 },
57 +       { .name = "JP", .min = 76000000, .max = 95000000, .step = 100000 },
58 +       { .name = "EU", .min = 87500000, .max = 108000000, .step = 50000 },
59 +       { .name = "ITU-1", .min = 87500000, .max = 108000000, .step = 50000 },
60 +       { .name = "ITU-2", .min = 87900000, .max = 107900000, .step = 50000 }
61 +};
62 +
63 +static unsigned int fm_band_plan;
64 +static int fm_snr_threshold = 128;
65 +static int fm_rssi_threshold = 128;
66 +
67  int init_am(int offset)
68  {
69         int ret;
70 @@ -160,12 +180,32 @@ int init_fm(int offset)
71          * enable I2S output
72          */
73         si46xx_set_property(SI46XX_PIN_CONFIG_ENABLE, 0x0003);
74 -       //si46xx_set_property(SI46XX_FM_VALID_RSSI_THRESHOLD,0x0000);
75 -       //si46xx_set_property(SI46XX_FM_VALID_SNR_THRESHOLD,0x0000);
76 -       si46xx_set_property(SI46XX_FM_SOFTMUTE_SNR_LIMITS, 0x0000); // set the SNR limits for soft mute attenuation
77 +       //si46xx_set_property(SI46XX_FM_SOFTMUTE_SNR_LIMITS, 0x0000); // set the SNR limits for soft mute attenuation
78         si46xx_set_property(SI46XX_FM_TUNE_FE_CFG, 0x0000); // front end switch open
79 -       si46xx_set_property(SI46XX_FM_SEEK_BAND_BOTTOM, 88000 / 10);
80 -       si46xx_set_property(SI46XX_FM_SEEK_BAND_TOP, 108000 / 10);
81 +
82 +       //si46xx_set_property(SI46XX_FM_SEEK_BAND_BOTTOM, 88000 / 10);
83 +       //si46xx_set_property(SI46XX_FM_SEEK_BAND_TOP, 108000 / 10);
84 +       if (verbose)
85 +               fprintf(stderr, "Using FM Bandplan: %s\n", known_fm_band_plans[fm_band_plan].name);
86 +       si46xx_set_property(SI46XX_FM_SEEK_BAND_BOTTOM, known_fm_band_plans[fm_band_plan].min / 10000);
87 +       si46xx_set_property(SI46XX_FM_SEEK_BAND_TOP, known_fm_band_plans[fm_band_plan].max / 10000);
88 +       if (verbose)
89 +               fprintf(stderr, "Using FM band: %d - %d, %d spacing\n",
90 +                       known_fm_band_plans[fm_band_plan].min / 10000,
91 +                       known_fm_band_plans[fm_band_plan].max / 10000,
92 +                       known_fm_band_plans[fm_band_plan].step / 10000);
93 +       si46xx_set_property(SI46XX_FM_SEEK_FREQUENCY_SPACING, known_fm_band_plans[fm_band_plan].step / 10000);
94 +       if (fm_snr_threshold != 128) {
95 +               if (verbose)
96 +                       fprintf(stderr, "Setting FM valid SNR threshold to %d dB\n", fm_snr_threshold);
97 +               si46xx_set_property(SI46XX_FM_VALID_SNR_THRESHOLD, fm_snr_threshold);
98 +       }
99 +       if (fm_rssi_threshold != 128) {
100 +               if (verbose)
101 +                       fprintf(stderr, "Setting FM valid RSSI threshold to %d dB\n", fm_rssi_threshold);
102 +               si46xx_set_property(SI46XX_FM_VALID_RSSI_THRESHOLD, fm_rssi_threshold);
103 +       }
104 +
105         /*
106          * rate
107          */
108 @@ -190,6 +230,7 @@ int init_fm(int offset)
109  
110         return 0;
111  }
112 +
113  int init_dab(int offset)
114  {
115         int ret;
116 @@ -245,6 +286,10 @@ int output_help(char *prog_name)
117         printf("  -l up|down     FM/AM seek next station\n");
118         printf("  -d             FM/AM RSQ status\n");
119         printf("  -m             FM rds status\n");
120 +       printf("Common FM:\n");
121 +       printf("  -p bandplan    FM bandplan (us, jp, eu, itu-1, itu-2\n");
122 +       printf("  -t SNR         FM scan valid SNR threshold (-127 to 127 dB)\n");
123 +       printf("  -u RSSI        FM scan valid RSSI threshold (-127 to 127 dBuV)\n");
124         printf("DAB only:\n");
125         printf("  -e             dab status\n");
126         printf("  -f service     start service of dab service list\n");
127 @@ -354,6 +399,7 @@ int main(int argc, char **argv)
128         int offset = - 1;
129         int mode;
130         int tmp;
131 +       unsigned int i;
132         struct dab_digrad_status_t dab_digrad_status;
133         bool init = false;
134         bool seek_up = false;
135 @@ -374,7 +420,7 @@ int main(int argc, char **argv)
136  
137         optind = 0;
138         while (optind < argc) {
139 -               if ((c = getopt(argc, argv, "a:b:c:def:ghi:j:k:l:mnosv")) != -1) {
140 +               if ((c = getopt(argc, argv, "a:b:c:def:ghi:j:k:l:mnop:st:u:v")) != -1) {
141                         switch(c){
142                         /* init */
143                         case 'a':
144 @@ -422,6 +468,31 @@ int main(int argc, char **argv)
145                         case 'c':
146                                 frequency = atoi(optarg);
147                                 break;
148 +                       /* FM */
149 +                       case 'p':
150 +                               for(i = 0;
151 +                                   i < sizeof(known_fm_band_plans) / sizeof(fm_band_plan_t);
152 +                                   i++) {
153 +                                       if(!strcasecmp(optarg, known_fm_band_plans[i].name)) {
154 +                                               fm_band_plan = i;
155 +                                               break;
156 +                                       }
157 +                               }
158 +                               if(i >= (sizeof(known_fm_band_plans) / sizeof(fm_band_plan_t))) {
159 +                                       printf("Invalid mode: %s\n", optarg);
160 +                                       return -EINVAL;
161 +                               }
162 +                               break;
163 +                       case 't':
164 +                               fm_snr_threshold = atoi(optarg);
165 +                               if(fm_snr_threshold < -128 || fm_snr_threshold > 127)
166 +                                       fm_snr_threshold = 128; // use firmware default
167 +                               break;
168 +                       case 'u':
169 +                               fm_rssi_threshold = atoi(optarg);
170 +                               if(fm_rssi_threshold < -128 || fm_rssi_threshold > 127)
171 +                                       fm_rssi_threshold = 128; // use firmware default
172 +                               break;
173                         /* DAB stuff. TODO: rework */
174                         case 'e':
175                                 si46xx_dab_digrad_status(&dab_digrad_status);
176 @@ -473,7 +544,7 @@ int main(int argc, char **argv)
177                         case SI46XX_MODE_FM:
178                                 ret = init_fm(offset);
179                                 if (frequency < 0)
180 -                                       frequency = 105500;
181 +                                       frequency = known_fm_band_plans[fm_band_plan].min / 1000;
182                         break;
183                         case SI46XX_MODE_AM:
184                                 ret = init_am(offset);