1 /* Copyright (c) 2011-2015, 2018-2020 The Linux Foundation. All rights reserved.
2 *
3 * Redistribution and use in source and binary forms, with or without
4 * modification, are permitted provided that the following conditions are
5 * met:
6 * * Redistributions of source code must retain the above copyright
7 * notice, this list of conditions and the following disclaimer.
8 * * Redistributions in binary form must reproduce the above
9 * copyright notice, this list of conditions and the following
10 * disclaimer in the documentation and/or other materials provided
11 * with the distribution.
12 * * Neither the name of The Linux Foundation, nor the names of its
13 * contributors may be used to endorse or promote products derived
14 * from this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED
17 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
18 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT
19 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS
20 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
23 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
24 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
25 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
26 * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 *
28 */
29
30 #define LOG_NDEBUG 0
31 #define LOG_TAG "LocSvc_utils_cfg"
32
33 #include <stdio.h>
34 #include <stdlib.h>
35 #include <pthread.h>
36 #include <string.h>
37 #include <ctype.h>
38 #include <unistd.h>
39 #include <time.h>
40 #include <grp.h>
41 #include <errno.h>
42 #include <loc_cfg.h>
43 #include <loc_pla.h>
44 #include <loc_target.h>
45 #include <loc_misc_utils.h>
46 #ifdef USE_GLIB
47 #include <glib.h>
48 #endif
49 #include "log_util.h"
50
51 /*=============================================================================
52 *
53 * GLOBAL DATA DECLARATION
54 *
55 *============================================================================*/
56
57 /* Parameter data */
58 static uint32_t DEBUG_LEVEL = 0xff;
59 static uint32_t TIMESTAMP = 0;
60 static uint32_t DATUM_TYPE = 0;
61 static bool sVendorEnhanced = true;
62 static uint32_t sLogBufferEnabled = 0;
63
64 /* Parameter spec table */
65 static const loc_param_s_type loc_param_table[] =
66 {
67 {"DEBUG_LEVEL", &DEBUG_LEVEL, NULL, 'n'},
68 {"TIMESTAMP", &TIMESTAMP, NULL, 'n'},
69 {"DATUM_TYPE", &DATUM_TYPE, NULL, 'n'},
70 {"LOG_BUFFER_ENABLED", &sLogBufferEnabled, NULL, 'n'},
71 };
72 static const int loc_param_num = sizeof(loc_param_table) / sizeof(loc_param_s_type);
73
74 typedef struct loc_param_v_type
75 {
76 char* param_name;
77 char* param_str_value;
78 int param_int_value;
79 double param_double_value;
80 }loc_param_v_type;
81
82 // Reference below arrays wherever needed to avoid duplicating
83 // same conf path string over and again in location code.
84 const char LOC_PATH_GPS_CONF[] = LOC_PATH_GPS_CONF_STR;
85 const char LOC_PATH_IZAT_CONF[] = LOC_PATH_IZAT_CONF_STR;
86 const char LOC_PATH_FLP_CONF[] = LOC_PATH_FLP_CONF_STR;
87 const char LOC_PATH_LOWI_CONF[] = LOC_PATH_LOWI_CONF_STR;
88 const char LOC_PATH_SAP_CONF[] = LOC_PATH_SAP_CONF_STR;
89 const char LOC_PATH_APDR_CONF[] = LOC_PATH_APDR_CONF_STR;
90 const char LOC_PATH_XTWIFI_CONF[] = LOC_PATH_XTWIFI_CONF_STR;
91 const char LOC_PATH_QUIPC_CONF[] = LOC_PATH_QUIPC_CONF_STR;
92 const char LOC_PATH_ANT_CORR[] = LOC_PATH_ANT_CORR_STR;
93 const char LOC_PATH_SLIM_CONF[] = LOC_PATH_SLIM_CONF_STR;
94 const char LOC_PATH_VPE_CONF[] = LOC_PATH_VPE_CONF_STR;
95
isVendorEnhanced()96 bool isVendorEnhanced() {
97 return sVendorEnhanced;
98 }
setVendorEnhanced(bool vendorEnhanced)99 void setVendorEnhanced(bool vendorEnhanced) {
100 sVendorEnhanced = vendorEnhanced;
101 }
102
103 /*===========================================================================
104 FUNCTION loc_get_datum_type
105
106 DESCRIPTION
107 get datum type
108
109 PARAMETERS:
110 N/A
111
112 DEPENDENCIES
113 N/A
114
115 RETURN VALUE
116 DATUM TYPE
117
118 SIDE EFFECTS
119 N/A
120 ===========================================================================*/
loc_get_datum_type()121 int loc_get_datum_type()
122 {
123 return DATUM_TYPE;
124 }
125
126 /*===========================================================================
127 FUNCTION loc_set_config_entry
128
129 DESCRIPTION
130 Potentially sets a given configuration table entry based on the passed in
131 configuration value. This is done by using a string comparison of the
132 parameter names and those found in the configuration file.
133
134 PARAMETERS:
135 config_entry: configuration entry in the table to possibly set
136 config_value: value to store in the entry if the parameter names match
137
138 DEPENDENCIES
139 N/A
140
141 RETURN VALUE
142 None
143
144 SIDE EFFECTS
145 N/A
146 ===========================================================================*/
loc_set_config_entry(const loc_param_s_type * config_entry,loc_param_v_type * config_value,uint16_t string_len=LOC_MAX_PARAM_STRING)147 int loc_set_config_entry(const loc_param_s_type* config_entry,
148 loc_param_v_type* config_value,
149 uint16_t string_len = LOC_MAX_PARAM_STRING)
150 {
151 int ret=-1;
152 if(NULL == config_entry || NULL == config_value)
153 {
154 LOC_LOGE("%s: INVALID config entry or parameter", __FUNCTION__);
155 return ret;
156 }
157
158 if (strcmp(config_entry->param_name, config_value->param_name) == 0 &&
159 config_entry->param_ptr)
160 {
161 switch (config_entry->param_type)
162 {
163 case 's':
164 if (strcmp(config_value->param_str_value, "NULL") == 0)
165 {
166 *((char*)config_entry->param_ptr) = '\0';
167 }
168 else {
169 strlcpy((char*) config_entry->param_ptr,
170 config_value->param_str_value,
171 string_len);
172 }
173 /* Log INI values */
174 LOC_LOGD("%s: PARAM %s = %s", __FUNCTION__,
175 config_entry->param_name, (char*)config_entry->param_ptr);
176
177 if(NULL != config_entry->param_set)
178 {
179 *(config_entry->param_set) = 1;
180 }
181 ret = 0;
182 break;
183 case 'n':
184 *((int *)config_entry->param_ptr) = config_value->param_int_value;
185 /* Log INI values */
186 LOC_LOGD("%s: PARAM %s = %d", __FUNCTION__,
187 config_entry->param_name, config_value->param_int_value);
188
189 if(NULL != config_entry->param_set)
190 {
191 *(config_entry->param_set) = 1;
192 }
193 ret = 0;
194 break;
195 case 'f':
196 *((double *)config_entry->param_ptr) = config_value->param_double_value;
197 /* Log INI values */
198 LOC_LOGD("%s: PARAM %s = %f", __FUNCTION__,
199 config_entry->param_name, config_value->param_double_value);
200
201 if(NULL != config_entry->param_set)
202 {
203 *(config_entry->param_set) = 1;
204 }
205 ret = 0;
206 break;
207 default:
208 LOC_LOGE("%s: PARAM %s parameter type must be n, f, or s",
209 __FUNCTION__, config_entry->param_name);
210 }
211 }
212 return ret;
213 }
214
215 /*===========================================================================
216 FUNCTION loc_fill_conf_item
217
218 DESCRIPTION
219 Takes a line of configuration item and sets defined values based on
220 the passed in configuration table. This table maps strings to values to
221 set along with the type of each of these values.
222
223 PARAMETERS:
224 input_buf : buffer contanis config item
225 config_table: table definition of strings to places to store information
226 table_length: length of the configuration table
227
228 DEPENDENCIES
229 N/A
230
231 RETURN VALUE
232 0: Number of records in the config_table filled with input_buf
233
234 SIDE EFFECTS
235 N/A
236 ===========================================================================*/
loc_fill_conf_item(char * input_buf,const loc_param_s_type * config_table,uint32_t table_length,uint16_t string_len=LOC_MAX_PARAM_STRING)237 int loc_fill_conf_item(char* input_buf,
238 const loc_param_s_type* config_table,
239 uint32_t table_length, uint16_t string_len = LOC_MAX_PARAM_STRING)
240 {
241 int ret = 0;
242
243 if (input_buf && config_table) {
244 char *lasts;
245 loc_param_v_type config_value;
246 memset(&config_value, 0, sizeof(config_value));
247
248 /* Separate variable and value */
249 config_value.param_name = strtok_r(input_buf, "=", &lasts);
250 /* skip lines that do not contain "=" */
251 if (config_value.param_name) {
252 config_value.param_str_value = strtok_r(NULL, "\0", &lasts);
253
254 /* skip lines that do not contain two operands */
255 if (config_value.param_str_value) {
256 /* Trim leading and trailing spaces */
257 loc_util_trim_space(config_value.param_name);
258 loc_util_trim_space(config_value.param_str_value);
259
260 /* Parse numerical value */
261 if ((strlen(config_value.param_str_value) >=3) &&
262 (config_value.param_str_value[0] == '0') &&
263 (tolower(config_value.param_str_value[1]) == 'x'))
264 {
265 /* hex */
266 config_value.param_int_value = (int) strtol(&config_value.param_str_value[2],
267 (char**) NULL, 16);
268 }
269 else {
270 config_value.param_double_value = (double) atof(config_value.param_str_value); /* float */
271 config_value.param_int_value = atoi(config_value.param_str_value); /* dec */
272 }
273
274 for(uint32_t i = 0; NULL != config_table && i < table_length; i++)
275 {
276 if(!loc_set_config_entry(&config_table[i], &config_value, string_len)) {
277 ret += 1;
278 }
279 }
280 }
281 }
282 }
283
284 return ret;
285 }
286
287 /*===========================================================================
288 FUNCTION loc_read_conf_r_long (repetitive)
289
290 DESCRIPTION
291 Reads the specified configuration file and sets defined values based on
292 the passed in configuration table. This table maps strings to values to
293 set along with the type of each of these values.
294 The difference between this and loc_read_conf is that this function returns
295 the file pointer position at the end of filling a config table. Also, it
296 reads a fixed number of parameters at a time which is equal to the length
297 of the configuration table. This functionality enables the caller to
298 repeatedly call the function to read data from the same file.
299
300 PARAMETERS:
301 conf_fp : file pointer
302 config_table: table definition of strings to places to store information
303 table_length: length of the configuration table
304
305 DEPENDENCIES
306 N/A
307
308 RETURN VALUE
309 0: Table filled successfully
310 1: No more parameters to read
311 -1: Error filling table
312
313 SIDE EFFECTS
314 N/A
315 ===========================================================================*/
loc_read_conf_r_long(FILE * conf_fp,const loc_param_s_type * config_table,uint32_t table_length,uint16_t string_len)316 int loc_read_conf_r_long(FILE *conf_fp, const loc_param_s_type* config_table,
317 uint32_t table_length, uint16_t string_len)
318 {
319 int ret=0;
320 char input_buf[string_len]; /* declare a char array */
321 unsigned int num_params=table_length;
322
323 if(conf_fp == NULL) {
324 LOC_LOGE("%s:%d]: ERROR: File pointer is NULL\n", __func__, __LINE__);
325 ret = -1;
326 goto err;
327 }
328
329 /* Clear all validity bits */
330 for(uint32_t i = 0; NULL != config_table && i < table_length; i++)
331 {
332 if(NULL != config_table[i].param_set)
333 {
334 *(config_table[i].param_set) = 0;
335 }
336 }
337
338 LOC_LOGD("%s:%d]: num_params: %d\n", __func__, __LINE__, num_params);
339 while(num_params)
340 {
341 if(!fgets(input_buf, string_len, conf_fp)) {
342 LOC_LOGD("%s:%d]: fgets returned NULL\n", __func__, __LINE__);
343 break;
344 }
345
346 num_params -= loc_fill_conf_item(input_buf, config_table, table_length, string_len);
347 }
348
349 err:
350 return ret;
351 }
352
353 /*===========================================================================
354 FUNCTION loc_udpate_conf_long
355
356 DESCRIPTION
357 Parses the passed in buffer for configuration items, and update the table
358 that is also passed in.
359
360 Reads the specified configuration file and sets defined values based on
361 the passed in configuration table. This table maps strings to values to
362 set along with the type of each of these values.
363
364 PARAMETERS:
365 conf_data: configuration items in bufferas a string
366 length: strlen(conf_data)
367 config_table: table definition of strings to places to store information
368 table_length: length of the configuration table
369
370 DEPENDENCIES
371 N/A
372
373 RETURN VALUE
374 number of the records in the table that is updated at time of return.
375
376 SIDE EFFECTS
377 N/A
378 ===========================================================================*/
loc_update_conf_long(const char * conf_data,int32_t length,const loc_param_s_type * config_table,uint32_t table_length,uint16_t string_len)379 int loc_update_conf_long(const char* conf_data, int32_t length,
380 const loc_param_s_type* config_table,
381 uint32_t table_length, uint16_t string_len)
382 {
383 int ret = -1;
384
385 if (conf_data && length && config_table && table_length) {
386 // make a copy, so we do not tokenize the original data
387 char* conf_copy = (char*)malloc(length+1);
388
389 if (conf_copy != NULL)
390 {
391 memcpy(conf_copy, conf_data, length);
392 // we hard NULL the end of string to be safe
393 conf_copy[length] = 0;
394
395 // start with one record off
396 uint32_t num_params = table_length - 1;
397 char* saveptr = NULL;
398 char* input_buf = strtok_r(conf_copy, "\n", &saveptr);
399 ret = 0;
400
401 LOC_LOGD("%s:%d]: num_params: %d\n", __func__, __LINE__, num_params);
402 while(num_params && input_buf) {
403 ret++;
404 num_params -=
405 loc_fill_conf_item(input_buf, config_table, table_length, string_len);
406 input_buf = strtok_r(NULL, "\n", &saveptr);
407 }
408 free(conf_copy);
409 }
410 }
411
412 return ret;
413 }
414
415 /*===========================================================================
416 FUNCTION loc_read_conf_long
417
418 DESCRIPTION
419 Reads the specified configuration file and sets defined values based on
420 the passed in configuration table. This table maps strings to values to
421 set along with the type of each of these values.
422
423 PARAMETERS:
424 conf_file_name: configuration file to read
425 config_table: table definition of strings to places to store information
426 table_length: length of the configuration table
427
428 DEPENDENCIES
429 N/A
430
431 RETURN VALUE
432 None
433
434 SIDE EFFECTS
435 N/A
436 ===========================================================================*/
loc_read_conf_long(const char * conf_file_name,const loc_param_s_type * config_table,uint32_t table_length,uint16_t string_len)437 void loc_read_conf_long(const char* conf_file_name, const loc_param_s_type* config_table,
438 uint32_t table_length, uint16_t string_len)
439 {
440 FILE *conf_fp = NULL;
441
442 log_buffer_init(false);
443 if((conf_fp = fopen(conf_file_name, "r")) != NULL)
444 {
445 LOC_LOGD("%s: using %s", __FUNCTION__, conf_file_name);
446 if(table_length && config_table) {
447 loc_read_conf_r_long(conf_fp, config_table, table_length, string_len);
448 rewind(conf_fp);
449 }
450 loc_read_conf_r_long(conf_fp, loc_param_table, loc_param_num, string_len);
451 fclose(conf_fp);
452 }
453 /* Initialize logging mechanism with parsed data */
454 loc_logger_init(DEBUG_LEVEL, TIMESTAMP);
455 log_buffer_init(sLogBufferEnabled);
456 log_tag_level_map_init();
457 }
458
459 /*=============================================================================
460 *
461 * Define and Structures for Parsing Location Process Configuration File
462 *
463 *============================================================================*/
464 #define MAX_NUM_STRINGS 20
465
466 //We can have 8 masks for now
467 #define CONFIG_MASK_TARGET_ALL 0X01
468 #define CONFIG_MASK_TARGET_FOUND 0X02
469 #define CONFIG_MASK_TARGET_CHECK 0X03
470 #define CONFIG_MASK_BASEBAND_ALL 0X04
471 #define CONFIG_MASK_BASEBAND_FOUND 0X08
472 #define CONFIG_MASK_BASEBAND_CHECK 0x0c
473 #define CONFIG_MASK_AUTOPLATFORM_ALL 0x10
474 #define CONFIG_MASK_AUTOPLATFORM_FOUND 0x20
475 #define CONFIG_MASK_AUTOPLATFORM_CHECK 0x30
476 #define CONFIG_MASK_SOCID_ALL 0x40
477 #define CONFIG_MASK_SOCID_FOUND 0x80
478 #define CONFIG_MASK_SOCID_CHECK 0xc0
479
480 #define LOC_FEATURE_MASK_GTP_WIFI_BASIC 0x01
481 #define LOC_FEATURE_MASK_GTP_WIFI_PREMIUM 0X02
482 #define LOC_FEATURE_MASK_GTP_CELL_BASIC 0X04
483 #define LOC_FEATURE_MASK_GTP_CELL_PREMIUM 0X08
484 #define LOC_FEATURE_MASK_SAP_BASIC 0x40
485 #define LOC_FEATURE_MASK_SAP_PREMIUM 0X80
486 #define LOC_FEATURE_MASK_GTP_WAA_BASIC 0X100
487 #define LOC_FEATURE_MASK_GTP_MODEM_CELL_BASIC 0X400
488 #define LOC_FEATURE_MASK_ODCPI 0x1000
489 #define LOC_FEATURE_MASK_FREE_WIFI_SCAN_INJECT 0x2000
490 #define LOC_FEATURE_MASK_SUPL_WIFI 0x4000
491 #define LOC_FEATURE_MASK_WIFI_SUPPLICANT_INFO 0x8000
492
493 typedef struct {
494 char proc_name[LOC_MAX_PARAM_STRING];
495 char proc_argument[LOC_MAX_PARAM_STRING];
496 char proc_status[LOC_MAX_PARAM_STRING];
497 char group_list[LOC_MAX_PARAM_STRING];
498 unsigned int premium_feature;
499 unsigned int loc_feature_mask;
500 char platform_list[LOC_MAX_PARAM_STRING];
501 char baseband[LOC_MAX_PARAM_STRING];
502 char low_ram_targets[LOC_MAX_PARAM_STRING];
503 char soc_id_list[LOC_MAX_PARAM_STRING];
504 unsigned int sglte_target;
505 char feature_gtp_mode[LOC_MAX_PARAM_STRING];
506 char feature_gtp_waa[LOC_MAX_PARAM_STRING];
507 char feature_sap[LOC_MAX_PARAM_STRING];
508 char feature_odcpi[LOC_MAX_PARAM_STRING];
509 char feature_free_wifi_scan_inject[LOC_MAX_PARAM_STRING];
510 char feature_supl_wifi[LOC_MAX_PARAM_STRING];
511 char feature_wifi_supplicant_info[LOC_MAX_PARAM_STRING];
512 char auto_platform[LOC_MAX_PARAM_STRING];
513 unsigned int vendor_enhanced_process;
514 } loc_launcher_conf;
515
516 /* process configuration parameters */
517 static loc_launcher_conf conf;
518
519 /* gps.conf Parameter spec table */
520 static const loc_param_s_type gps_conf_parameter_table[] = {
521 {"SGLTE_TARGET", &conf.sglte_target, NULL, 'n'},
522 };
523
524 /* location feature conf, e.g.: izat.conf feature mode table*/
525 static const loc_param_s_type loc_feature_conf_table[] = {
526 {"GTP_MODE", &conf.feature_gtp_mode, NULL, 's'},
527 {"GTP_WAA", &conf.feature_gtp_waa, NULL, 's'},
528 {"SAP", &conf.feature_sap, NULL, 's'},
529 {"ODCPI", &conf.feature_odcpi, NULL, 's'},
530 {"FREE_WIFI_SCAN_INJECT", &conf.feature_free_wifi_scan_inject, NULL, 's'},
531 {"SUPL_WIFI", &conf.feature_supl_wifi, NULL, 's'},
532 {"WIFI_SUPPLICANT_INFO", &conf.feature_wifi_supplicant_info, NULL, 's'},
533 };
534
535 /* location process conf, e.g.: izat.conf Parameter spec table */
536 static const loc_param_s_type loc_process_conf_parameter_table[] = {
537 {"PROCESS_NAME", &conf.proc_name, NULL, 's'},
538 {"PROCESS_ARGUMENT", &conf.proc_argument, NULL, 's'},
539 {"PROCESS_STATE", &conf.proc_status, NULL, 's'},
540 {"PROCESS_GROUPS", &conf.group_list, NULL, 's'},
541 {"PREMIUM_FEATURE", &conf.premium_feature, NULL, 'n'},
542 {"IZAT_FEATURE_MASK", &conf.loc_feature_mask, NULL, 'n'},
543 {"PLATFORMS", &conf.platform_list, NULL, 's'},
544 {"SOC_IDS", &conf.soc_id_list, NULL, 's'},
545 {"BASEBAND", &conf.baseband, NULL, 's'},
546 {"LOW_RAM_TARGETS", &conf.low_ram_targets, NULL, 's'},
547 {"HARDWARE_TYPE", &conf.auto_platform, NULL, 's'},
548 {"VENDOR_ENHANCED_PROCESS", &conf.vendor_enhanced_process, NULL, 'n'},
549 };
550
551 /*===========================================================================
552 FUNCTION loc_read_process_conf
553
554 DESCRIPTION
555 Parse the specified conf file and return info for the processes defined.
556 The format of the file should conform with izat.conf.
557
558 PARAMETERS:
559 conf_file_name: configuration file to read
560 process_count_ptr: pointer to store number of processes defined in the conf file.
561 process_info_table_ptr: pointer to store the process info table.
562
563 DEPENDENCIES
564 The file must be in izat.conf format.
565
566 RETURN VALUE
567 0: success
568 none-zero: failure
569
570 SIDE EFFECTS
571 N/A
572
573 NOTES:
574 On success, memory pointed by (*process_info_table_ptr) must be freed.
575 ===========================================================================*/
loc_read_process_conf(const char * conf_file_name,uint32_t * process_count_ptr,loc_process_info_s_type ** process_info_table_ptr)576 int loc_read_process_conf(const char* conf_file_name, uint32_t * process_count_ptr,
577 loc_process_info_s_type** process_info_table_ptr) {
578 loc_process_info_s_type *child_proc = nullptr;
579 volatile int i=0;
580 unsigned int j=0;
581 gid_t gid_list[LOC_PROCESS_MAX_NUM_GROUPS];
582 char *split_strings[MAX_NUM_STRINGS];
583 int name_length=0, group_list_length=0, platform_length=0, baseband_length=0, ngroups=0, ret=0;
584 int auto_platform_length = 0, soc_id_list_length=0;
585 int group_index=0, nstrings=0, status_length=0;
586 FILE* conf_fp = nullptr;
587 char platform_name[PROPERTY_VALUE_MAX], baseband_name[PROPERTY_VALUE_MAX];
588 int low_ram_target=0;
589 char autoplatform_name[PROPERTY_VALUE_MAX], socid_value[PROPERTY_VALUE_MAX];
590 unsigned int loc_service_mask=0;
591 unsigned char config_mask = 0;
592 unsigned char proc_list_length=0;
593 int gtp_cell_ap_enabled = 0;
594 char arg_gtp_waa[LOC_PROCESS_MAX_ARG_STR_LENGTH] = "--";
595 char arg_gtp_modem_cell[LOC_PROCESS_MAX_ARG_STR_LENGTH] = "--";
596 char arg_gtp_wifi[LOC_PROCESS_MAX_ARG_STR_LENGTH] = "--";
597 char arg_sap[LOC_PROCESS_MAX_ARG_STR_LENGTH] = "--";
598 char arg_disabled[LOC_PROCESS_MAX_ARG_STR_LENGTH] = LOC_FEATURE_MODE_DISABLED;
599 char arg_basic[LOC_PROCESS_MAX_ARG_STR_LENGTH] = LOC_FEATURE_MODE_BASIC;
600 char arg_premium[LOC_PROCESS_MAX_ARG_STR_LENGTH] = LOC_FEATURE_MODE_PREMIUM;
601
602 if (process_count_ptr == NULL || process_info_table_ptr == NULL) {
603 return -1;
604 }
605
606 //Read gps.conf and fill parameter table
607 UTIL_READ_CONF(LOC_PATH_GPS_CONF, gps_conf_parameter_table);
608
609 //Form argument strings
610 strlcat(arg_gtp_waa, LOC_FEATURE_GTP_WAA, LOC_PROCESS_MAX_ARG_STR_LENGTH-3);
611 strlcat(arg_gtp_modem_cell, LOC_FEATURE_GTP_MODEM_CELL, LOC_PROCESS_MAX_ARG_STR_LENGTH-3);
612 strlcat(arg_gtp_wifi, LOC_FEATURE_GTP_WIFI, LOC_PROCESS_MAX_ARG_STR_LENGTH-3);
613 strlcat(arg_sap, LOC_FEATURE_SAP, LOC_PROCESS_MAX_ARG_STR_LENGTH-3);
614
615 //Get platform name from ro.board.platform property
616 loc_get_platform_name(platform_name, sizeof(platform_name));
617 //Get baseband name from ro.baseband property
618 loc_get_target_baseband(baseband_name, sizeof(baseband_name));
619 //Identify if this is an automotive platform
620 loc_get_auto_platform_name(autoplatform_name,sizeof(autoplatform_name));
621 //Identify if this is a low ram target from ro.config.low_ram property
622 low_ram_target = loc_identify_low_ram_target();
623 // Get the soc-id for this device.
624 loc_get_device_soc_id(socid_value, sizeof(socid_value));
625
626 UTIL_READ_CONF(conf_file_name, loc_feature_conf_table);
627
628 //Set service mask for GTP_MODE
629 if (strcmp(conf.feature_gtp_mode, "DISABLED") == 0) {
630 LOC_LOGD("%s:%d]: GTP MODE DISABLED", __func__, __LINE__);
631 }
632 else if (strcmp(conf.feature_gtp_mode, "LEGACY_WWAN") == 0) {
633 LOC_LOGD("%s:%d]: Setting GTP MODE to mode: LEGACY_WWAN", __func__, __LINE__);
634 loc_service_mask |= LOC_FEATURE_MASK_GTP_MODEM_CELL_BASIC;
635 }
636 else if (strcmp(conf.feature_gtp_mode, "SDK") == 0) {
637 LOC_LOGD("%s:%d]: Setting GTP MODE to mode: SDK", __func__, __LINE__);
638 loc_service_mask |= LOC_FEATURE_MASK_GTP_WIFI_BASIC;
639 }
640 else if (strcmp(conf.feature_gtp_mode, "SDK_WIFI") == 0) {
641 LOC_LOGD("%s:%d]: Setting GTP MODE to mode: SDK", __func__, __LINE__);
642 loc_service_mask |= LOC_FEATURE_MASK_GTP_WIFI_BASIC;
643 }
644 //conf file has a garbage value
645 else {
646 LOC_LOGE("%s:%d]: Unrecognized value for GTP MODE Mode."\
647 " Setting GTP WIFI to default mode: DISABLED", __func__, __LINE__);
648 }
649 //Set service mask for GTP_WAA
650 if (strcmp(conf.feature_gtp_waa, "BASIC") == 0) {
651 LOC_LOGD("%s:%d]: Setting GTP WAA to mode: BASIC", __func__, __LINE__);
652 loc_service_mask |= LOC_FEATURE_MASK_GTP_WAA_BASIC;
653 }
654 else if (strcmp(conf.feature_gtp_waa, "DISABLED") == 0) {
655 LOC_LOGD("%s:%d]: GTP WAA DISABLED", __func__, __LINE__);
656 }
657 //conf file has a garbage value
658 else {
659 LOC_LOGE("%s:%d]: Unrecognized value for GTP WAA Mode."\
660 " Setting GTP WAA to default mode: DISABLED", __func__, __LINE__);
661 }
662
663 //Set service mask for SAP
664 if(strcmp(conf.feature_sap, "PREMIUM") == 0 ||
665 strcmp(conf.feature_sap, "PREMIUM_ENV_AIDING") == 0) {
666 LOC_LOGD("%s:%d]: Setting SAP to mode: PREMIUM", __func__, __LINE__);
667 loc_service_mask |= LOC_FEATURE_MASK_SAP_PREMIUM;
668 }
669 else if (strcmp(conf.feature_sap, "BASIC") == 0) {
670 LOC_LOGD("%s:%d]: Setting SAP to mode: BASIC", __func__, __LINE__);
671 loc_service_mask |= LOC_FEATURE_MASK_SAP_BASIC;
672 }
673 else if (strcmp(conf.feature_sap, "MODEM_DEFAULT") == 0) {
674 LOC_LOGD("%s:%d]: Setting SAP to mode: MODEM_DEFAULT", __func__, __LINE__);
675 loc_service_mask |= LOC_FEATURE_MASK_SAP_BASIC;
676 }
677 else if (strcmp(conf.feature_sap, "DISABLED") == 0) {
678 #ifdef USE_GLIB
679 /* Enable slim_daemon even when SAP is set to DISABLED*/
680 loc_service_mask |= LOC_FEATURE_MASK_SAP_BASIC;
681 #else
682 LOC_LOGD("%s:%d]: Setting SAP to mode: DISABLED", __func__, __LINE__);
683 #endif
684 }
685 else {
686 LOC_LOGE("%s:%d]: Unrecognized value for SAP Mode."\
687 " Setting SAP to default mode: BASIC", __func__, __LINE__);
688 loc_service_mask |= LOC_FEATURE_MASK_SAP_BASIC;
689 }
690
691 // Set service mask for ODCPI
692 if (strcmp(conf.feature_odcpi, "BASIC") == 0) {
693 LOC_LOGD("%s:%d]: Setting ODCPI to mode: BASIC", __func__, __LINE__);
694 loc_service_mask |= LOC_FEATURE_MASK_ODCPI;
695 }
696 else if (strcmp(conf.feature_odcpi, "DISABLED") == 0) {
697 LOC_LOGD("%s:%d]: Setting ODCPI to mode: DISABLED", __func__, __LINE__);
698 }
699 else if (strcmp(conf.feature_odcpi, "PREMIUM") == 0) {
700 LOC_LOGD("%s:%d]: Unrecognized value for ODCPI mode."\
701 "Setting ODCPI to default mode: BASIC", __func__, __LINE__);
702 loc_service_mask |= LOC_FEATURE_MASK_ODCPI;
703 }
704
705 // Set service mask for FREE_WIFI_SCAN_INJECT
706 if (strcmp(conf.feature_free_wifi_scan_inject, "BASIC") == 0) {
707 LOC_LOGD("%s:%d]: Setting FREE_WIFI_SCAN_INJECT to mode: BASIC", __func__, __LINE__);
708 loc_service_mask |= LOC_FEATURE_MASK_FREE_WIFI_SCAN_INJECT;
709 }
710 else if (strcmp(conf.feature_free_wifi_scan_inject, "DISABLED") == 0) {
711 LOC_LOGD("%s:%d]: Setting FREE_WIFI_SCAN_INJECT to mode: DISABLED", __func__, __LINE__);
712 }
713 else if (strcmp(conf.feature_free_wifi_scan_inject, "PREMIUM") == 0) {
714 LOC_LOGD("%s:%d]: Unrecognized value for FREE_WIFI_SCAN_INJECT mode."\
715 "Setting FREE_WIFI_SCAN_INJECT to default mode: BASIC", __func__, __LINE__);
716 loc_service_mask |= LOC_FEATURE_MASK_FREE_WIFI_SCAN_INJECT;
717 }
718
719 // Set service mask for SUPL_WIFI
720 if (strcmp(conf.feature_supl_wifi, "BASIC") == 0) {
721 LOC_LOGD("%s:%d]: Setting SUPL_WIFI to mode: BASIC", __func__, __LINE__);
722 loc_service_mask |= LOC_FEATURE_MASK_SUPL_WIFI;
723 }
724 else if (strcmp(conf.feature_supl_wifi, "DISABLED") == 0) {
725 LOC_LOGD("%s:%d]: Setting SUPL_WIFI to mode: DISABLED", __func__, __LINE__);
726 }
727 else if (strcmp(conf.feature_supl_wifi, "PREMIUM") == 0) {
728 LOC_LOGD("%s:%d]: Unrecognized value for SUPL_WIFI mode."\
729 "Setting SUPL_WIFI to default mode: BASIC", __func__, __LINE__);
730 loc_service_mask |= LOC_FEATURE_MASK_SUPL_WIFI;
731 }
732
733 // Set service mask for WIFI_SUPPLICANT_INFO
734 if (strcmp(conf.feature_wifi_supplicant_info, "BASIC") == 0) {
735 LOC_LOGD("%s:%d]: Setting WIFI_SUPPLICANT_INFO to mode: BASIC", __func__, __LINE__);
736 loc_service_mask |= LOC_FEATURE_MASK_WIFI_SUPPLICANT_INFO;
737 }
738 else if (strcmp(conf.feature_wifi_supplicant_info, "DISABLED") == 0) {
739 LOC_LOGD("%s:%d]: Setting WIFI_SUPPLICANT_INFO to mode: DISABLED", __func__, __LINE__);
740 }
741 else if (strcmp(conf.feature_wifi_supplicant_info, "PREMIUM") == 0) {
742 LOC_LOGD("%s:%d]: Unrecognized value for WIFI_SUPPLICANT_INFO mode."\
743 "Setting LOC_FEATURE_MASK_WIFI_SUPPLICANT_INFO to default mode: BASIC", __func__, __LINE__);
744 loc_service_mask |= LOC_FEATURE_MASK_WIFI_SUPPLICANT_INFO;
745 }
746
747 LOC_LOGD("%s:%d]: loc_service_mask: %x\n", __func__, __LINE__, loc_service_mask);
748
749 if((conf_fp = fopen(conf_file_name, "r")) == NULL) {
750 LOC_LOGE("%s:%d]: Error opening %s %s\n", __func__,
751 __LINE__, conf_file_name, strerror(errno));
752 ret = -1;
753 goto err;
754 }
755
756 //Parse through the file to find out how many processes are to be launched
757 proc_list_length = 0;
758 do {
759 conf.proc_name[0] = 0;
760 //Here note that the 3rd parameter is passed as 1.
761 //This is so that only the first parameter in the table which is "PROCESS_NAME"
762 //is read. We do not want to read the entire block of parameters at this time
763 //since we are only counting the number of processes to launch.
764 //Therefore, only counting the occurrences of PROCESS_NAME parameter
765 //should suffice
766 if(loc_read_conf_r(conf_fp, loc_process_conf_parameter_table, 1)) {
767 LOC_LOGE("%s:%d]: Unable to read conf file. Failing\n", __func__, __LINE__);
768 ret = -1;
769 goto err;
770 }
771 name_length=(int)strlen(conf.proc_name);
772 if(name_length) {
773 proc_list_length++;
774 LOC_LOGD("Process name:%s", conf.proc_name);
775 }
776 } while(name_length);
777 LOC_LOGD("Process cnt = %d", proc_list_length);
778
779 child_proc = (loc_process_info_s_type *)calloc(proc_list_length, sizeof(loc_process_info_s_type));
780 if(child_proc == NULL) {
781 LOC_LOGE("%s:%d]: ERROR: Malloc returned NULL\n", __func__, __LINE__);
782 ret = -1;
783 goto err;
784 }
785
786 //Move file descriptor to the beginning of the file
787 //so that the parameters can be read
788 rewind(conf_fp);
789
790 for(j=0; j<proc_list_length; j++) {
791 //Set defaults for all the child process structs
792 child_proc[j].proc_status = DISABLED;
793 memset(child_proc[j].group_list, 0, sizeof(child_proc[j].group_list));
794 config_mask=0;
795 if(loc_read_conf_r(conf_fp, loc_process_conf_parameter_table,
796 sizeof(loc_process_conf_parameter_table)/sizeof(loc_process_conf_parameter_table[0]))) {
797 LOC_LOGE("%s:%d]: Unable to read conf file. Failing\n", __func__, __LINE__);
798 ret = -1;
799 goto err;
800 }
801
802 name_length=(int)strlen(conf.proc_name);
803 group_list_length=(int)strlen(conf.group_list);
804 platform_length = (int)strlen(conf.platform_list);
805 baseband_length = (int)strlen(conf.baseband);
806 status_length = (int)strlen(conf.proc_status);
807 auto_platform_length = (int)strlen(conf.auto_platform);
808 soc_id_list_length = (int)strlen(conf.soc_id_list);
809
810 if(!name_length || !group_list_length || !platform_length ||
811 !baseband_length || !status_length || !auto_platform_length || !soc_id_list_length) {
812 LOC_LOGE("%s:%d]: Error: i: %d; One of the parameters not specified in conf file",
813 __func__, __LINE__, i);
814 continue;
815 }
816
817 if (!isVendorEnhanced() && (conf.vendor_enhanced_process != 0)) {
818 LOC_LOGD("%s:%d]: Process %s is disabled via vendor enhanced process check",
819 __func__, __LINE__, conf.proc_name);
820 child_proc[j].proc_status = DISABLED_VIA_VENDOR_ENHANCED_CHECK;
821 continue;
822 }
823
824 if (strcmp(conf.proc_status, "DISABLED") == 0) {
825 LOC_LOGD("%s:%d]: Process %s is disabled in conf file",
826 __func__, __LINE__, conf.proc_name);
827 child_proc[j].proc_status = DISABLED_FROM_CONF;
828 continue;
829 }
830 else if (strcmp(conf.proc_status, "ENABLED") == 0) {
831 LOC_LOGD("%s:%d]: Process %s is enabled in conf file",
832 __func__, __LINE__, conf.proc_name);
833 }
834
835 //Since strlcpy copies length-1 characters, we add 1 to name_length
836 if((name_length+1) > LOC_MAX_PARAM_STRING) {
837 LOC_LOGE("%s:%d]: i: %d; Length of name parameter too long. Max length: %d",
838 __func__, __LINE__, i, LOC_MAX_PARAM_STRING);
839 continue;
840 }
841 strlcpy(child_proc[j].name[0], conf.proc_name, sizeof (child_proc[j].name[0]));
842
843 child_proc[j].num_groups = 0;
844 ngroups = loc_util_split_string(conf.group_list, split_strings, MAX_NUM_STRINGS, ' ');
845 for(i=0; i<ngroups; i++) {
846 struct group* grp = getgrnam(split_strings[i]);
847 if (grp) {
848 child_proc[j].group_list[child_proc[j].num_groups] = grp->gr_gid;
849 child_proc[j].num_groups++;
850 LOC_LOGd("Group %s = %d", split_strings[i], grp->gr_gid);
851 }
852 }
853
854 nstrings = loc_util_split_string(conf.platform_list, split_strings, MAX_NUM_STRINGS, ' ');
855 if (strcmp("all", split_strings[0]) == 0) {
856 if (nstrings == 1 || (nstrings == 2 && (strcmp("exclude", split_strings[1]) == 0))) {
857 LOC_LOGD("%s:%d]: Enabled for all targets\n", __func__, __LINE__);
858 config_mask |= CONFIG_MASK_TARGET_ALL;
859 }
860 else if (nstrings > 2 && (strcmp("exclude", split_strings[1]) == 0)) {
861 config_mask |= CONFIG_MASK_TARGET_FOUND;
862 for (i=2; i<nstrings; i++) {
863 if (strcmp(platform_name, split_strings[i]) == 0) {
864 LOC_LOGD("%s:%d]: Disabled platform %s\n", __func__, __LINE__, platform_name);
865 config_mask &= ~CONFIG_MASK_TARGET_FOUND;
866 break;
867 }
868 }
869 }
870 }
871 else {
872 for(i=0; i<nstrings; i++) {
873 if (strcmp(platform_name, split_strings[i]) == 0) {
874 LOC_LOGD("%s:%d]: Matched platform: %s\n",
875 __func__, __LINE__, split_strings[i]);
876 config_mask |= CONFIG_MASK_TARGET_FOUND;
877 break;
878 }
879 }
880 }
881
882 // SOC Id's check
883 nstrings = loc_util_split_string(conf.soc_id_list, split_strings, MAX_NUM_STRINGS, ' ');
884 if (strcmp("all", split_strings[0]) == 0) {
885 if (nstrings == 1 || (nstrings == 2 && (strcmp("exclude", split_strings[1]) == 0))) {
886 LOC_LOGd("Enabled for all SOC ids\n");
887 config_mask |= CONFIG_MASK_SOCID_ALL;
888 }
889 else if (nstrings > 2 && (strcmp("exclude", split_strings[1]) == 0)) {
890 config_mask |= CONFIG_MASK_SOCID_FOUND;
891 for (i = 2; i < nstrings; i++) {
892 if (strcmp(socid_value, split_strings[i]) == 0) {
893 LOC_LOGd("Disabled for SOC id %s\n", socid_value);
894 config_mask &= ~CONFIG_MASK_SOCID_FOUND;
895 break;
896 }
897 }
898 }
899 }
900 else {
901 for (i = 0; i < nstrings; i++) {
902 if (strcmp(socid_value, split_strings[i]) == 0) {
903 LOC_LOGd("Matched SOC id : %s\n", split_strings[i]);
904 config_mask |= CONFIG_MASK_SOCID_FOUND;
905 break;
906 }
907 }
908 }
909
910 nstrings = loc_util_split_string(conf.baseband, split_strings, MAX_NUM_STRINGS, ' ');
911 if (strcmp("all", split_strings[0]) == 0) {
912 if (nstrings == 1 || (nstrings == 2 && (strcmp("exclude", split_strings[1]) == 0))) {
913 LOC_LOGD("%s:%d]: Enabled for all basebands\n", __func__, __LINE__);
914 config_mask |= CONFIG_MASK_BASEBAND_ALL;
915 }
916 else if (nstrings > 2 && (strcmp("exclude", split_strings[1]) == 0)) {
917 config_mask |= CONFIG_MASK_BASEBAND_FOUND;
918 for (i=2; i<nstrings; i++) {
919 if (strcmp(baseband_name, split_strings[i]) == 0) {
920 LOC_LOGD("%s:%d]: Disabled band %s\n", __func__, __LINE__, baseband_name);
921 config_mask &= ~CONFIG_MASK_BASEBAND_FOUND;
922 break;
923 }
924 }
925 }
926 }
927 else {
928 for(i=0; i<nstrings; i++) {
929 if (strcmp(baseband_name, split_strings[i]) == 0) {
930 LOC_LOGD("%s:%d]: Matched baseband: %s\n",
931 __func__, __LINE__, split_strings[i]);
932 config_mask |= CONFIG_MASK_BASEBAND_FOUND;
933 break;
934 }
935 //Since ro.baseband is not a reliable source for detecting sglte
936 //the alternative is to read the SGLTE_TARGET parameter from gps.conf
937 //this parameter is read into conf_sglte_target
938 else if((strcmp("sglte", split_strings[i]) == 0 ) && conf.sglte_target) {
939 LOC_LOGD("%s:%d]: Matched baseband SGLTE\n", __func__, __LINE__);
940 config_mask |= CONFIG_MASK_BASEBAND_FOUND;
941 break;
942 }
943 }
944 }
945
946 nstrings = loc_util_split_string(conf.auto_platform, split_strings, MAX_NUM_STRINGS, ' ');
947 if (strcmp("all", split_strings[0]) == 0) {
948 LOC_LOGD("%s:%d]: Enabled for all auto platforms\n", __func__, __LINE__);
949 config_mask |= CONFIG_MASK_AUTOPLATFORM_ALL;
950 }
951 else {
952 for(i=0; i<nstrings; i++) {
953 if (strcmp(autoplatform_name, split_strings[i]) == 0) {
954 LOC_LOGD("%s:%d]: Matched auto platform: %s\n",
955 __func__, __LINE__, split_strings[i]);
956 config_mask |= CONFIG_MASK_AUTOPLATFORM_FOUND;
957 break;
958 }
959 }
960 }
961
962 nstrings = loc_util_split_string(conf.low_ram_targets, split_strings, MAX_NUM_STRINGS, ' ');
963 if (!strcmp("DISABLED", split_strings[0]) && low_ram_target) {
964 LOC_LOGd("Disabled for low ram targets\n");
965 child_proc[j].proc_status = DISABLED;
966 continue;
967 }
968
969 if((config_mask & CONFIG_MASK_TARGET_CHECK) &&
970 (config_mask & CONFIG_MASK_BASEBAND_CHECK) &&
971 (config_mask & CONFIG_MASK_AUTOPLATFORM_CHECK) &&
972 (config_mask & CONFIG_MASK_SOCID_CHECK) &&
973 (child_proc[j].proc_status != DISABLED_FROM_CONF) &&
974 (child_proc[j].proc_status != DISABLED_VIA_VENDOR_ENHANCED_CHECK)) {
975
976 //Set args
977 //The first argument passed through argv is usually the name of the
978 //binary when started from commandline.
979 //getopt() seems to ignore this first argument and hence we assign it
980 //to the process name for consistency with command line args
981 i = 0;
982 char* temp_arg = ('/' == child_proc[j].name[0][0]) ?
983 (strrchr(child_proc[j].name[0], '/') + 1) : child_proc[j].name[0];
984 strlcpy (child_proc[j].args[i++], temp_arg, sizeof (child_proc[j].args[0]));
985
986 if(conf.premium_feature) {
987 if(conf.loc_feature_mask & loc_service_mask) {
988 LOC_LOGD("%s:%d]: Enabled. %s has service mask: %x\n",
989 __func__, __LINE__, child_proc[j].name[0], conf.loc_feature_mask);
990 child_proc[j].proc_status = ENABLED;
991
992 if(conf.loc_feature_mask &
993 (LOC_FEATURE_MASK_GTP_WIFI_BASIC | LOC_FEATURE_MASK_GTP_WIFI_PREMIUM)) {
994 if(loc_service_mask & LOC_FEATURE_MASK_GTP_WIFI_BASIC) {
995 strlcpy(child_proc[j].args[i++], arg_gtp_wifi,
996 LOC_PROCESS_MAX_ARG_STR_LENGTH);
997 strlcpy(child_proc[j].args[i++], arg_basic,
998 LOC_PROCESS_MAX_ARG_STR_LENGTH);
999 }
1000 else if(loc_service_mask & LOC_FEATURE_MASK_GTP_WIFI_PREMIUM) {
1001 strlcpy(child_proc[j].args[i++], arg_gtp_wifi,
1002 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1003 strlcpy(child_proc[j].args[i++], arg_premium,
1004 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1005 }
1006 else
1007 {
1008 strlcpy(child_proc[j].args[i++], arg_gtp_wifi,
1009 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1010 strlcpy(child_proc[j].args[i++], arg_disabled,
1011 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1012 }
1013 }
1014 if(conf.loc_feature_mask &
1015 (LOC_FEATURE_MASK_GTP_CELL_BASIC | LOC_FEATURE_MASK_GTP_CELL_PREMIUM )) {
1016 if(loc_service_mask & LOC_FEATURE_MASK_GTP_MODEM_CELL_BASIC) {
1017 strlcpy(child_proc[j].args[i++], arg_gtp_modem_cell,
1018 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1019 strlcpy(child_proc[j].args[i++], arg_basic,
1020 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1021 }
1022 else {
1023 strlcpy(child_proc[j].args[i++], arg_gtp_modem_cell,
1024 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1025 strlcpy(child_proc[j].args[i++], arg_disabled,
1026 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1027 }
1028 }
1029 if(conf.loc_feature_mask &
1030 (LOC_FEATURE_MASK_SAP_BASIC | LOC_FEATURE_MASK_SAP_PREMIUM)) {
1031 if(loc_service_mask & LOC_FEATURE_MASK_SAP_BASIC) {
1032 strlcpy(child_proc[j].args[i++], arg_sap,
1033 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1034 strlcpy(child_proc[j].args[i++], arg_basic,
1035 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1036 }
1037 else if(loc_service_mask & LOC_FEATURE_MASK_SAP_PREMIUM) {
1038 strlcpy(child_proc[j].args[i++], arg_sap,
1039 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1040 strlcpy(child_proc[j].args[i++], arg_premium,
1041 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1042 }
1043 else
1044 {
1045 strlcpy(child_proc[j].args[i++], arg_sap,
1046 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1047 strlcpy(child_proc[j].args[i++], arg_disabled,
1048 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1049 }
1050 }
1051
1052 if(conf.loc_feature_mask & LOC_FEATURE_MASK_GTP_WAA_BASIC) {
1053 if(loc_service_mask & LOC_FEATURE_MASK_GTP_WAA_BASIC) {
1054 strlcpy(child_proc[j].args[i++], arg_gtp_waa,
1055 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1056 strlcpy(child_proc[j].args[i++], arg_basic,
1057 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1058 }
1059 else
1060 {
1061 strlcpy(child_proc[j].args[i++], arg_gtp_waa,
1062 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1063 strlcpy(child_proc[j].args[i++], arg_disabled,
1064 LOC_PROCESS_MAX_ARG_STR_LENGTH);
1065 }
1066 }
1067 IF_LOC_LOGD {
1068 LOC_LOGD("%s:%d]: %s args\n", __func__, __LINE__, child_proc[j].name[0]);
1069 for(unsigned int k=0; k<LOC_PROCESS_MAX_NUM_ARGS; k++) {
1070 if(child_proc[j].args[k][0] != '\0') {
1071 LOC_LOGD("%s:%d]: k: %d, %s\n", __func__, __LINE__, k,
1072 child_proc[j].args[k]);
1073 }
1074 }
1075 LOC_LOGD("%s:%d]: \n", __func__, __LINE__);
1076 }
1077 }
1078 else {
1079 LOC_LOGD("%s:%d]: Disabled. %s has service mask: %x \n",
1080 __func__, __LINE__, child_proc[j].name[0], conf.loc_feature_mask);
1081 }
1082 }
1083 else {
1084 LOC_LOGD("%s:%d]: %s not a premium feature. Enabled\n",
1085 __func__, __LINE__, child_proc[j].name[0]);
1086 child_proc[j].proc_status = ENABLED;
1087 }
1088
1089 /*Fill up the remaining arguments from configuration file*/
1090 LOC_LOGD("%s] Parsing Process_Arguments from Configuration: %s \n",
1091 __func__, conf.proc_argument);
1092 if(0 != conf.proc_argument[0])
1093 {
1094 /**************************************
1095 ** conf_proc_argument is shared by all the programs getting launched,
1096 ** hence copy to process specific argument string and parse the same.
1097 ***************************************/
1098 strlcpy(child_proc[j].argumentString, conf.proc_argument,
1099 sizeof(child_proc[j].argumentString));
1100 char *temp_args[LOC_PROCESS_MAX_NUM_ARGS];
1101 memset (temp_args, 0, sizeof (temp_args));
1102 loc_util_split_string(child_proc[j].argumentString, &temp_args[i],
1103 (LOC_PROCESS_MAX_NUM_ARGS - i), ' ');
1104 // copy argument from the pointer to the memory
1105 for (unsigned int index = i; index < LOC_PROCESS_MAX_NUM_ARGS; index++) {
1106 if (temp_args[index] == NULL) {
1107 break;
1108 }
1109 strlcpy (child_proc[j].args[index], temp_args[index],
1110 sizeof (child_proc[j].args[index]));
1111 }
1112 }
1113 }
1114 else {
1115 LOC_LOGD("%s:%d]: Process %s is disabled\n",
1116 __func__, __LINE__, child_proc[j].name[0]);
1117 }
1118 }
1119
1120 err:
1121 if (conf_fp) {
1122 fclose(conf_fp);
1123 }
1124 if (ret != 0) {
1125 LOC_LOGE("%s:%d]: ret: %d", __func__, __LINE__, ret);
1126 if (child_proc) {
1127 free (child_proc);
1128 child_proc = nullptr;
1129 }
1130 *process_count_ptr = 0;
1131 *process_info_table_ptr = nullptr;
1132
1133 }
1134 else {
1135 *process_count_ptr = proc_list_length;
1136 *process_info_table_ptr = child_proc;
1137 }
1138
1139 return ret;
1140 }
1141