252812816e23ff077d1e209be69310ed3e450a50
[osmocom-bb.git] / src / host / layer23 / src / mobile / support.c
1 /*
2  * (C) 2010 by Andreas Eversberg <jolly@eversberg.eu>
3  *
4  * All Rights Reserved
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License along
17  * with this program; if not, write to the Free Software Foundation, Inc.,
18  * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19  *
20  */
21
22 #include <stdio.h>
23 #include <stdint.h>
24 #include <string.h>
25
26 #include <osmocom/bb/common/osmocom_data.h>
27
28 void gsm_support_init(struct osmocom_ms *ms)
29 {
30         struct gsm_support *sup = &ms->support;
31         int i;
32
33         memset(sup, 0, sizeof(*sup));
34         sup->ms = ms;
35
36         /* rf power capability */
37         sup->class_900 = 4; /* CLASS 4: Handheld 2W */
38         sup->class_dcs = 1; /* CLASS 1: Handheld 1W */
39         /* controlled early classmark sending */
40         sup->es_ind = 0; /* no */
41         /* revision level */
42         sup->rev_lev = 1; /* phase 2 mobile station */
43         /* support of VGCS */
44         sup->vgcs = 0; /* no */
45         /* support of VBS */
46         sup->vbs = 0; /* no */
47         /* support of SMS */
48         sup->sms_ptp = 1; /* yes */
49         /* screening indicator */
50         sup->ss_ind = 1; /* phase 2 error handling */
51         /* pseudo synchronised capability */
52         sup->ps_cap = 0; /* no */
53         /* CM service prompt */
54         sup->cmsp = 0; /* no */
55         /* solsa support */
56         sup->solsa = 0; /* no */
57         /* location service support */
58         sup->lcsva = 0; /* no */
59         sup->loc_serv = 0; /* no */
60         /* codec supprot */
61         sup->a5_1 = 1;
62         sup->a5_2 = 1;
63         sup->a5_3 = 0;
64         sup->a5_4 = 0;
65         sup->a5_5 = 0;
66         sup->a5_6 = 0;
67         sup->a5_7 = 0;
68         /* radio support */
69         sup->p_gsm = 1; /* P-GSM */
70         sup->e_gsm = 1; /* E-GSM */
71         sup->r_gsm = 1; /* R-GSM */
72         sup->dcs = 1;
73         /* set supported frequencies */
74         if (sup->p_gsm)
75                 for(i = 1; i <= 124; i++)
76                         sup->freq_map[i >> 3] |= (1 << (i & 7));
77         if (sup->dcs)
78                 for(i = 512; i <= 885; i++)
79                         sup->freq_map[i >> 3] |= (1 << (i & 7));
80         if (sup->e_gsm) {
81                 for(i = 975; i <= 1023; i++)
82                         sup->freq_map[i >> 3] |= (1 << (i & 7));
83                 sup->freq_map[0] |= 1;
84         }
85         if (sup->r_gsm)
86                 for(i = 955; i <= 974; i++)
87                         sup->freq_map[i >> 3] |= (1 << (i & 7));
88         /* multi slot support */
89         sup->ms_sup = 0; /* no */
90         /* ucs2 treatment */
91         sup->ucs2_treat = 0; /* default */
92         /* support extended measurements */
93         sup->ext_meas = 0; /* no */
94         /* support switched measurement capability */
95         sup->meas_cap = 0; /* no */
96         //sup->sms_val = ;
97         //sup->sm_val = ;
98
99         /* radio */
100         sup->ch_cap = GSM_CAP_SDCCH_TCHF;
101         sup->min_rxlev_db = -100; // TODO
102         sup->sync_to = 6; /* how long to wait sync (0.9 s) */
103         sup->scan_to = 4; /* how long to wait for all sysinfos (>=4 s) */
104         sup->dsc_max = 90; /* the specs defines 90 */
105
106         /* codec */
107         sup->full_v1 = 1;
108         sup->full_v2 = 1;
109         sup->full_v3 = 0;
110         sup->half_v1 = 1;
111         sup->half_v3 = 0;
112 }
113
114 /* (3.2.1) maximum channels to scan within each band */
115 struct gsm_support_scan_max gsm_sup_smax[] = {
116         { 259, 293, 15, 0 }, /* GSM 450 */
117         { 306, 340, 15, 0 }, /* GSM 480 */
118         { 438, 511, 25, 0 },
119         { 128, 251, 30, 0 }, 
120         { 955, 124, 30, 0 }, /* P,E,R GSM */
121         { 512, 885, 40, 0 }, /* DCS 1800 */
122         { 0, 0, 0, 0 }
123 };
124
125 #define SUP_SET(item) \
126         ((sup->item) ? ((set->item) ? "yes" : "disabled") : "no")
127 /* dump support */
128 void gsm_support_dump(struct osmocom_ms *ms,
129                         void (*print)(void *, const char *, ...), void *priv)
130 {
131         struct gsm_support *sup = &ms->support;
132         struct gsm_settings *set = &ms->settings;
133
134         print(priv, "Supported features of MS '%s':\n", sup->ms->name);
135         print(priv, " Phase %d mobile station\n", sup->rev_lev + 1);
136         print(priv, " R-GSM       : %s\n", SUP_SET(r_gsm));
137         print(priv, " E-GSM       : %s\n", SUP_SET(e_gsm));
138         print(priv, " P-GSM       : %s\n", SUP_SET(p_gsm));
139         print(priv, " GSM900 Class: %d\n", set->class_900);
140         print(priv, " DCS 1800    : %s\n", SUP_SET(dcs));
141         print(priv, " DCS Class   : %d\n", set->class_dcs);
142         print(priv, " CECS        : %s\n", (sup->es_ind) ? "yes" : "no");
143         print(priv, " VGCS        : %s\n", (sup->vgcs) ? "yes" : "no");
144         print(priv, " VBS         : %s\n", (sup->vbs) ? "yes" : "no");
145         print(priv, " SMS         : %s\n", SUP_SET(sms_ptp));
146         print(priv, " SS_IND      : %s\n", (sup->ss_ind) ? "yes" : "no");
147         print(priv, " PS_CAP      : %s\n", (sup->ps_cap) ? "yes" : "no");
148         print(priv, " CMSP        : %s\n", (sup->cmsp) ? "yes" : "no");
149         print(priv, " SoLSA       : %s\n", (sup->solsa) ? "yes" : "no");
150         print(priv, " LCSVA       : %s\n", (sup->lcsva) ? "yes" : "no");
151         print(priv, " LOC_SERV    : %s\n", (sup->loc_serv) ? "yes" : "no");
152         print(priv, " A5/1        : %s\n", SUP_SET(a5_1));
153         print(priv, " A5/2        : %s\n", SUP_SET(a5_2));
154         print(priv, " A5/3        : %s\n", SUP_SET(a5_3));
155         print(priv, " A5/4        : %s\n", SUP_SET(a5_4));
156         print(priv, " A5/5        : %s\n", SUP_SET(a5_5));
157         print(priv, " A5/6        : %s\n", SUP_SET(a5_6));
158         print(priv, " A5/7        : %s\n", SUP_SET(a5_7));
159         print(priv, " A5/1        : %s\n", SUP_SET(a5_1));
160         switch (set->ch_cap) {
161                 case GSM_CAP_SDCCH:
162                 print(priv, " Channels    : SDCCH only\n");
163                 break;
164                 case GSM_CAP_SDCCH_TCHF:
165                 print(priv, " Channels    : SDCCH + TCH/F\n");
166                 break;
167                 case GSM_CAP_SDCCH_TCHF_TCHH:
168                 print(priv, " Channels    : SDCCH + TCH/F + TCH/H\n");
169                 break;
170         }
171         print(priv, " Full-Rate V1: %s\n", SUP_SET(full_v1));
172         print(priv, " Full-Rate V2: %s\n", SUP_SET(full_v2));
173         print(priv, " Full-Rate V3: %s\n", SUP_SET(full_v3));
174         print(priv, " Half-Rate V1: %s\n", SUP_SET(half_v1));
175         print(priv, " Half-Rate V3: %s\n", SUP_SET(half_v3));
176         print(priv, " Min RXLEV   : %d\n", set->min_rxlev_db);
177 }
178