1 /* Conversion of logged cells to KML file */
3 /* (C) 2010 by Andreas Eversberg <jolly@eversberg.eu>
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of the GNU General Public License as published by
9 * the Free Software Foundation; either version 2 of the License, or
10 * (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
22 #include <osmocom/bb/common/osmocom_data.h>
26 extern struct power power
;
27 extern struct sysinfo sysinfo
;
28 extern struct node_power
*node_power_first
;
29 extern struct node_power
**node_power_last_p
;
30 extern struct node_mcc
*node_mcc_first
;
32 struct node_mcc
*get_node_mcc(uint16_t mcc
)
34 struct node_mcc
*node_mcc
;
35 struct node_mcc
**node_mcc_p
= &node_mcc_first
;
37 //printf("add mcc %d\n", mcc);
40 if ((*node_mcc_p
)->mcc
== mcc
)
42 /* insert into list */
43 if ((*node_mcc_p
)->mcc
> mcc
)
45 node_mcc_p
= &((*node_mcc_p
)->next
);
48 //printf("new mcc %d\n", mcc);
49 /* append or insert to list */
50 node_mcc
= calloc(1, sizeof(struct node_mcc
));
54 node_mcc
->next
= *node_mcc_p
;
55 *node_mcc_p
= node_mcc
;
59 struct node_mnc
*get_node_mnc(struct node_mcc
*mcc
, uint16_t mnc
)
61 struct node_mnc
*node_mnc
;
62 struct node_mnc
**node_mnc_p
= &mcc
->mnc
;
66 if ((*node_mnc_p
)->mnc
== mnc
)
68 /* insert into list */
69 if ((*node_mnc_p
)->mnc
> mnc
)
71 node_mnc_p
= &((*node_mnc_p
)->next
);
74 /* append or insert to list */
75 node_mnc
= calloc(1, sizeof(struct node_mnc
));
79 node_mnc
->next
= *node_mnc_p
;
80 *node_mnc_p
= node_mnc
;
84 struct node_lac
*get_node_lac(struct node_mnc
*mnc
, uint16_t lac
)
86 struct node_lac
*node_lac
;
87 struct node_lac
**node_lac_p
= &mnc
->lac
;
91 if ((*node_lac_p
)->lac
== lac
)
93 /* insert into list */
94 if ((*node_lac_p
)->lac
> lac
)
96 node_lac_p
= &((*node_lac_p
)->next
);
99 /* append or insert to list */
100 node_lac
= calloc(1, sizeof(struct node_lac
));
104 node_lac
->next
= *node_lac_p
;
105 *node_lac_p
= node_lac
;
109 struct node_cell
*get_node_cell(struct node_lac
*lac
, uint16_t cellid
)
111 struct node_cell
*node_cell
;
112 struct node_cell
**node_cell_p
= &lac
->cell
;
114 while (*node_cell_p
) {
116 if ((*node_cell_p
)->cellid
== cellid
)
118 /* insert into list */
119 if ((*node_cell_p
)->cellid
> cellid
)
121 node_cell_p
= &((*node_cell_p
)->next
);
124 /* append or insert to list */
125 node_cell
= calloc(1, sizeof(struct node_cell
));
128 node_cell
->meas_last_p
= &node_cell
->meas
;
129 node_cell
->cellid
= cellid
;
130 node_cell
->next
= *node_cell_p
;
131 *node_cell_p
= node_cell
;
135 struct node_meas
*add_node_meas(struct node_cell
*cell
)
137 struct node_meas
*node_meas
;
140 node_meas
= calloc(1, sizeof(struct node_meas
));
143 node_meas
->gmt
= sysinfo
.gmt
;
144 node_meas
->rxlev
= sysinfo
.rxlev
;
145 if (sysinfo
.ta_valid
) {
146 node_meas
->ta_valid
= 1;
147 node_meas
->ta
= sysinfo
.ta
;
149 if (sysinfo
.gps_valid
) {
150 node_meas
->gps_valid
= 1;
151 node_meas
->longitude
= sysinfo
.longitude
;
152 node_meas
->latitude
= sysinfo
.latitude
;
154 *cell
->meas_last_p
= node_meas
;
155 cell
->meas_last_p
= &node_meas
->next
;
159 /* read "<ncc>,<bcc>" */
160 static void read_log_bsic(char *buffer
)
165 /* skip first spaces */
166 while (*buffer
== ' ')
171 while (*p
> ' ' && *p
!= ',')
174 return; /* no value */
176 bsic
= atoi(buffer
) << 3;
180 bsic
|= atoi(buffer
);
185 /* read "<longitude> <latitude>" */
186 static void read_log_pos(char *buffer
, double *longitude
, double *latitude
,
191 /* skip first spaces */
192 while (*buffer
== ' ')
200 return; /* no value after longitude */
202 *longitude
= atof(buffer
);
205 /* skip second spaces */
206 while (*buffer
== ' ')
210 *latitude
= atof(buffer
);
215 /* read "<arfcn> <value> <next value> ...." */
216 static void read_log_power(char *buffer
)
221 /* skip first spaces */
222 while (*buffer
== ' ')
230 return; /* no value after arfcn */
232 arfcn
= atoi(buffer
);
237 if (arfcn
< 0 || arfcn
> 1023)
240 while (*buffer
== ' ')
248 power
.rxlev
[arfcn
] = atoi(buffer
);
252 power
.rxlev
[arfcn
] = atoi(buffer
);
258 /* read "xx xx xx xx xx...." */
259 static void read_log_si(char *buffer
, uint8_t *data
)
264 // printf("%s ", buffer);
265 for (i
= 0; i
< 23; i
++) {
266 while (*buffer
== ' ')
268 if (*buffer
>= '0' && *buffer
<= '9')
269 si
[i
] = (*buffer
- '0') << 4;
270 else if (*buffer
>= 'a' && *buffer
<= 'f')
271 si
[i
] = (*buffer
- 'a' + 10) << 4;
272 else if (*buffer
>= 'A' && *buffer
<= 'F')
273 si
[i
] = (*buffer
- 'A' + 10) << 4;
277 if (*buffer
>= '0' && *buffer
<= '9')
278 si
[i
] += *buffer
- '0';
279 else if (*buffer
>= 'a' && *buffer
<= 'f')
280 si
[i
] += *buffer
- 'a' + 10;
281 else if (*buffer
>= 'A' && *buffer
<= 'F')
282 si
[i
] += *buffer
- 'A' + 10;
286 // printf("%02x ", si[i]);
291 memcpy(data
, si
, 23);
294 /* read next record from log file */
295 int read_log(FILE *infp
)
297 static int type
= LOG_TYPE_NONE
, ret
;
300 memset(&sysinfo
, 0, sizeof(sysinfo
));
301 memset(&power
, 0, sizeof(power
));
302 memset(&power
.rxlev
, -128, sizeof(power
.rxlev
));
305 return LOG_TYPE_NONE
;
307 while (fgets(buffer
, sizeof(buffer
), infp
)) {
308 buffer
[sizeof(buffer
) - 1] = 0;
310 buffer
[strlen(buffer
) - 1] = '\0';
311 if (buffer
[0] == '[') {
312 if (!strcmp(buffer
, "[sysinfo]")) {
314 type
= LOG_TYPE_SYSINFO
;
315 if (ret
!= LOG_TYPE_NONE
)
318 if (!strcmp(buffer
, "[power]")) {
320 type
= LOG_TYPE_POWER
;
321 if (ret
!= LOG_TYPE_NONE
)
324 type
= LOG_TYPE_NONE
;
329 case LOG_TYPE_SYSINFO
:
330 if (!strncmp(buffer
, "arfcn ", 6))
331 sysinfo
.arfcn
= atoi(buffer
+ 6);
332 else if (!strncmp(buffer
, "si1 ", 4))
333 read_log_si(buffer
+ 4, sysinfo
.si1
);
334 else if (!strncmp(buffer
, "si2 ", 4))
335 read_log_si(buffer
+ 4, sysinfo
.si2
);
336 else if (!strncmp(buffer
, "si2bis ", 7))
337 read_log_si(buffer
+ 7, sysinfo
.si2bis
);
338 else if (!strncmp(buffer
, "si2ter ", 7))
339 read_log_si(buffer
+ 7, sysinfo
.si2ter
);
340 else if (!strncmp(buffer
, "si3 ", 4))
341 read_log_si(buffer
+ 4, sysinfo
.si3
);
342 else if (!strncmp(buffer
, "si4 ", 4))
343 read_log_si(buffer
+ 4, sysinfo
.si4
);
344 else if (!strncmp(buffer
, "time ", 5))
345 sysinfo
.gmt
= strtoul(buffer
+ 5, NULL
, 0);
346 else if (!strncmp(buffer
, "position ", 9))
347 read_log_pos(buffer
+ 9, &sysinfo
.longitude
,
348 &sysinfo
.latitude
, &sysinfo
.gps_valid
);
349 else if (!strncmp(buffer
, "rxlev ", 5))
351 strtoul(buffer
+ 5, NULL
, 0);
352 else if (!strncmp(buffer
, "bsic ", 5))
353 read_log_bsic(buffer
+ 5);
354 else if (!strncmp(buffer
, "ta ", 3)) {
355 sysinfo
.ta_valid
= 1;
356 sysinfo
.ta
= atoi(buffer
+ 3);
360 if (!strncmp(buffer
, "arfcn ", 6))
361 read_log_power(buffer
+ 6);
362 else if (!strncmp(buffer
, "time ", 5))
363 power
.gmt
= strtoul(buffer
+ 5, NULL
, 0);
364 else if (!strncmp(buffer
, "position ", 9))
365 read_log_pos(buffer
+ 9, &power
.longitude
,
366 &power
.latitude
, &sysinfo
.gps_valid
);