blob: aa57ed31cde50b52a5e0ac958047b62064c97b52 [file] [log] [blame]
lhe3922f92024-11-05 02:40:56 -08001#include <stdio.h>
2#include <sys/types.h>
3#include <sys/socket.h>
4#include <arpa/inet.h>
5#include <string.h>
6#include <unistd.h>
7#include <binder/Parcel.h>
8#include <log/log.h>
9#include <cutils/jstring.h>
10#include <pthread.h>
11#include <sys/socket.h>
12#include <netinet/in.h>
13#include <arpa/inet.h>
14#include <errno.h>
15#include <include/lynq_uci.h>
16#include <lynq_misc/lynq_misc.h>
17#include <stdlib.h>
18#include <fcntl.h>
19#include <assert.h>
20#include "lynq_sdk_ready.h"
21
22#define LOG_TAG "LYNQ_SDK_READY"
23#define DEST_PORT 8088
24#define LYNQ_BRODCAST_PORT 8086
25
26#define SDK_READY_PORT 8157
27#define DSET_IP_ADDRESS "127.0.0.1"
28#define RIL_REQUEST_DEVICE_IDENTITY 98
29#define MAX_LEN 1024
30#define TIMER 30
31#define LOG_UCI_FILE "lynq_uci"
32#define LOG_UCI_MODULE "debug_mode"
33#define update_ril_digit 0x7 //The last three digits are reserved for RIL service,0x111
34#define update_userdata_digit 1<<3
35#define update_gnss_digit 1<<4
36
37#define DEFAULT_PERIOD_RIL 30
38#define DEFAULT_PERIOD_GNSS 300
39#define DEFAULT_PERIOD_MD 60
40#define DEFAULT_PERIOD_PTN 120
41#define DEFAULT_PERIOD_SYS 120
42#define DEFAULT_PERIOD_BOOT 60
43
44#define MIN_PERIOD_RIL 10
45#define MIN_PERIOD_GNSS 60
46#define MIN_PERIOD_MD 30
47#define MIN_PERIOD_PTN 120
48#define MIN_PERIOD_SYS 120
49#define RIL_UNSOL_TELEPHONY_RESTART 3113
50
51#define GET_CPU_NUM "cat /proc/cpuinfo | grep processor | wc -l"
52#define GET_LOAD_AVG_INFO "/proc/loadavg"
53#define GET_INTR_INFO "/proc/stat"
54#define GET_MEM_INFO "/proc/meminfo"
55#define GET_MIN_FREE "/proc/sys/vm/min_free_kbytes"
56
57#define BIT_EXCPT_RIL 1
58#define BIT_EXCPT_MD 1 << 1
59#define BIT_EXCPT_GNSS 1 << 2
60#define BIT_EXCPT_PTN 1 << 3
61#define BIT_EXCPT_SYS 1 << 4
62
63using ::android::Parcel;
64
65static pthread_mutex_t g_lynq_sim_sendto_mutex;
66static pthread_mutex_t lock;
67static pthread_mutex_t s_startupMutex = PTHREAD_MUTEX_INITIALIZER;
68static pthread_cond_t s_startupCond = PTHREAD_COND_INITIALIZER;
69
70// 全局变量
71static lynq_sdk_check_param_t *global_param = NULL;
72static lynq_sdk_status_cb global_sdk_status_cb = NULL;
73static lynq_sdk_ready_t global_sdk_status;
74static int utoken = 0;
75static int global_sdk_ready_status = 1;
76static int s_ril_started = 0;
77static int s_sys_started = 0;
78static int s_ptn_started = 0;
79static int s_gnss_started = 0;
80static int boot_ril_check_timer[8] = {2,2,4,4,8,8,16,16};
81enum in_ril_excpt {
82 RIL_REQUEST_SUCCESS=0,
83 RIL_MODEM_BOOT_EXCPT=1,
84 RIL_RESP_ERROR_FAIL=2,
85 RIL_SOCKET_CREATE_FAIL=3,
86 RIL_SOCKET_SEND_REC_FAIL=4,
87};
88
89typedef struct{
90 int uToken;
91 int request;
92 int paramLen;
93 char param[MAX_LEN];
94}lynq_client_t;
95
96
97void unlock_with_s_start(int *s_start)
98{
99 pthread_mutex_lock(&s_startupMutex);
100 *s_start = 1;
101 pthread_cond_broadcast(&s_startupCond);
102 pthread_mutex_unlock(&s_startupMutex);
103}
104long get_uptime()
105{
106 struct timespec start_time;
107 clock_gettime(CLOCK_MONOTONIC, &start_time);
108 return start_time.tv_sec;
109}
110const char * sdk_status_excpt_to_string(lynq_sdk_status_t excpt)
111{
112 switch(excpt)
113 {
114 case LYNQ_SDK_READY: return "LYNQ_SDK_READY";
115 case LYNQ_SDK_MD_EXCPT: return "LYNQ_SDK_MD_EXCPT";
116 case LYNQ_SDK_MD_REBOOT_EXCPT: return "LYNQ_SDK_MD_REBOOT_EXCPT";
117 case LYNQ_SDK_RIL_EXCPT: return "LYNQ_SDK_RIL_EXCPT";
118 case LYNQ_SDK_PARTITION_EXCPT: return "LYNQ_SDK_PARTITION_EXCPT";
119 case LYNQ_SDK_MIN_FREE_EXCPT: return "LYNQ_SDK_MIN_FREE_EXCPT";
120 case LYNQ_SDK_INTR_EXCPT: return "LYNQ_ACTION_INTR_EXCPT";
121 case LYNQ_SDK_LOAD_AVG_EXCPT: return "LYNQ_SDK_LOAD_AVG_EXCPT";
122 case LYNQ_SDK_NET_CHANNEL_EXCPT: return "LYNQ_SDK_NET_CHANNEL_EXCPT";
123 case LYNQ_SDK_GNSS_EXCPT: return "LYNQ_SDK_GNSS_EXCPT";
124 default: return "<unknown excpt>";
125 }
126}
127const char * sdk_status_action_to_string(lynq_sdk_ref_action_t action)
128{
129 switch(action)
130 {
131 case LYNQ_ACTION_NOTHING: return "LYNQ_ACTION_NOTHING";
132 case LYNQ_ACTION_REBOOT: return "LYNQ_ACTION_REBOOT";
133 case LYNQ_ACTION_RESET_MD: return "LYNQ_ACTION_RESET_MD";
134 case LYNQ_ACTION_RETRY_DATA_CALL: return "LYNQ_ACTION_RETRY_DATA_CALL";
135 case LYNQ_ACTION_PTN_CLEAN: return "LYNQ_ACTION_PTN_CLEAN";
136 case LYNQ_ACTION_SYS_WARNING: return "LYNQ_ACTION_SYS_WARNING";
137 default: return "<unknown action>";
138 }
139}
140void reset_sdk_ready_status()
141{
142 global_sdk_status.sdk_ready_status = LYNQ_SDK_READY;
143 global_sdk_status.ref_action = LYNQ_ACTION_NOTHING;
144}
145void trigger_sdk_ready_cb(lynq_sdk_status_t excpt, lynq_sdk_ref_action_t action)
146{
147 pthread_mutex_lock(&lock);
148 RLOGI("trigger sdk ready cb excpt:%s,action:%s",sdk_status_excpt_to_string(excpt),sdk_status_action_to_string(action));
149 long uptime = get_uptime();
150 if((excpt != LYNQ_SDK_READY) && (uptime < global_param->period.BOOT))
151 {
152 goto end;
153 }
154 //if((global_sdk_status.sdk_ready_status == excpt) && (global_sdk_status.ref_action == action))
155 //{
156 // goto end;
157 //}
158 global_sdk_status.sdk_ready_status = excpt;
159 global_sdk_status.ref_action = action;
160 global_sdk_status_cb(&global_sdk_status,NULL);
161end:
162 pthread_mutex_unlock(&lock);
163 return;
164}
165//maybe uci,or other
166void set_sdk_ready_nv(int value)
167{
168 char cmd[64] = {0};
169 RLOGI("set_sdk_ready_nv:%d",value);
170 sprintf(cmd,"uci set lynq_uci.sdk_ready=%d",value);//set uci
171 system(cmd);
172 return;
173}
174void set_sdk_ready_status_bit(int bit,int status)
175{
176 pthread_mutex_lock(&lock);
177 int old = 1;
178 if((global_sdk_ready_status & bit) == 0)
179 {
180 old = 0;
181 }
182 if(old == status)
183 {
184 goto end;
185 }
186 if(status == 1)
187 {
188 global_sdk_ready_status |= bit;
189 }
190 else
191 {
192 global_sdk_ready_status &= ~bit;
193 }
194 set_sdk_ready_nv(global_sdk_ready_status);
195end:
196 pthread_mutex_unlock(&lock);
197 return;
198}
199static int get_md_sta(void)
200{
201 FILE *fp;
202 char buffer[64]={};
203 fp = popen("cat /sys/kernel/ccci/boot","r");
204 if(fp == NULL)
205 {
206 RLOGD("function %s fp is null\n", __FUNCTION__);
207 return 0;
208 }
209 fgets(buffer,sizeof(buffer),fp);
210 if(!strlen(buffer))
211 {
212 RLOGD("function %s line %d\n", __FUNCTION__, __LINE__);
213 pclose(fp);
214 return 0;
215 }
216 if(buffer[4] == '4')
217 {
218 pclose(fp);
219 return 1;
220 }
221 RLOGD("function %s line %d\n", __FUNCTION__, __LINE__);
222 pclose(fp);
223 return 0;
224}
225
226static int check_service(const char *service)
227{
228 FILE *fp = NULL;
229 char buffer[1024]={};
230 if(!strcmp(service, "/usr/sbin/mtkfusionrild"))
231 {
232 fp = popen("ps -ef|grep rild","r");
233 }
234 else if(!strcmp(service, "lynq-ril-service"))
235 {
236 fp = popen("ps -ef|grep ril-service","r");
237 }
238 if(fp == NULL)
239 {
240 RLOGD("function %s fp is null\n", __FUNCTION__);
241 return 0;
242 }
243 while(NULL != fgets(buffer,sizeof(buffer),fp))
244 {
245 if(strstr(buffer,service))
246 {
247 pclose(fp);
248 RLOGD("check_service 1\n");
249 return 1;
250 }
251 }
252 RLOGD("check_service 0\n");
253 pclose(fp);
254 return 0;
255}
256
257/**
258 * @brief find partition zhengshu for exzample 5.7M,get value 5
259 *
260 * @param arg
261 * @return
262 */
263static void removeSpaces(char* str)
264{
265 char* dest = str;
266 while (*str) {
267 if (*str != ' ') {
268 *dest++ = *str;
269 }
270 str++;
271 }
272 *dest = '\0';
273 return ;
274}
275void check_ril_sleep(int count)
276{
277 if((count < sizeof(boot_ril_check_timer)/sizeof(int)) && ((global_sdk_ready_status & 1) == 1))// total 60s
278 {
279 sleep(boot_ril_check_timer[count]);
280 }
281 else
282 {
283 sleep(global_param->period.RIL);
284 }
285 return;
286}
287void update_ril_value(int value)
288{
289 switch (value)
290 {
291 case RIL_REQUEST_SUCCESS:
292 {
293 trigger_sdk_ready_cb(LYNQ_SDK_READY, LYNQ_ACTION_NOTHING);
294 set_sdk_ready_status_bit(BIT_EXCPT_RIL,0);
295 break;
296 }
297 case RIL_MODEM_BOOT_EXCPT:
298 {
299 set_sdk_ready_status_bit(BIT_EXCPT_RIL,1);
300 trigger_sdk_ready_cb(LYNQ_SDK_MD_EXCPT,LYNQ_ACTION_REBOOT);
301 break;
302 }
303 case RIL_RESP_ERROR_FAIL:
304 {
305 set_sdk_ready_status_bit(BIT_EXCPT_RIL,1);
306 trigger_sdk_ready_cb(LYNQ_SDK_RIL_EXCPT,LYNQ_ACTION_NOTHING);
307 break;
308 }
309 case RIL_SOCKET_CREATE_FAIL:
310 case RIL_SOCKET_SEND_REC_FAIL:
311 {
312 set_sdk_ready_status_bit(BIT_EXCPT_RIL,1);
313 trigger_sdk_ready_cb(LYNQ_SDK_RIL_EXCPT,LYNQ_ACTION_REBOOT);
314 break;
315 }
316 default:
317 RLOGE("Not this case:%d",value);
318 }
319 return;
320}
321
322void update_userdata_value()
323{
324 pthread_mutex_lock(&lock);
325 trigger_sdk_ready_cb(LYNQ_SDK_PARTITION_EXCPT, LYNQ_ACTION_REBOOT);
326 set_sdk_ready_status_bit(BIT_EXCPT_PTN,1);
327 pthread_mutex_unlock(&lock);
328 return;
329}
330
331void update_gnss_value()
332{
333 pthread_mutex_lock(&lock);
334 trigger_sdk_ready_cb(LYNQ_SDK_GNSS_EXCPT, LYNQ_ACTION_REBOOT);
335 set_sdk_ready_status_bit(BIT_EXCPT_GNSS,1);
336 pthread_mutex_unlock(&lock);
337 return;
338}
339/**
340 * @brief send request imei
341 *
342 * @param arg
343 * 线程run起来后前两个60s 不做异常上报,这段时间是模组就绪时间因此只报ready 状态,60s 以后如果还是检测到异常,说明是真异常
344 * @return void*
345 */
346void * timer_request_imei(void * arg)
347{
348 unlock_with_s_start(&s_ril_started);
349 int send_num = -1;
350 int recv_num = -1;
351 int resp_type = -1;
352 int request = -1;
353 int slot_id = -1;
354 int token = -1;
355 int res_error = -1;
356 int count = 0;
357 Parcel p;
358 struct sockaddr_in addr_serv;
359 struct sockaddr_in liblynq_sdk_ready_socket;
360 memset(&liblynq_sdk_ready_socket, 0,sizeof(liblynq_sdk_ready_socket));
361 memset(&addr_serv, 0, sizeof(addr_serv));
362 addr_serv.sin_family = AF_INET;
363 addr_serv.sin_addr.s_addr = inet_addr(DSET_IP_ADDRESS);
364 addr_serv.sin_port = htons(DEST_PORT);
365 liblynq_sdk_ready_socket.sin_family = AF_INET;
366 liblynq_sdk_ready_socket.sin_addr.s_addr = inet_addr(DSET_IP_ADDRESS);
367 int len_addr_serv = sizeof(addr_serv);
368
369 lynq_client_t client_t;
370 char res_data[MAX_LEN] = {0};
371 client_t.request = RIL_REQUEST_DEVICE_IDENTITY;
372 client_t.paramLen = 0;
373 client_t.uToken = utoken;
374 memset(client_t.param, 0, sizeof(client_t.param));
375
376 struct timeval timeOut;
377 timeOut.tv_sec = 3;//timeout time 3s
378 timeOut.tv_usec = 0;
379
380 int sock_fd = socket(AF_INET, SOCK_DGRAM, 0);
381 if (-1 == sock_fd)
382 {
383 RLOGD("__FUNCTION__ %s create sock_fd failed %s\n", __FUNCTION__, strerror(errno));
384 exit(EXIT_FAILURE);
385 return NULL;
386 }
387 int ret = bind(sock_fd, (struct sockaddr *)&liblynq_sdk_ready_socket, sizeof(liblynq_sdk_ready_socket));
388 if (-1 == ret)
389 {
390 RLOGE("liblynq_data_socket bind fail,errno:%d",errno);
391 return NULL;
392 }
393
394 if (setsockopt(sock_fd, SOL_SOCKET, SO_RCVTIMEO, &timeOut, sizeof(timeOut)) < 0)
395 {
396 RLOGD("__FUNCTION__ %s time out setting failed %s\n", __FUNCTION__, strerror(errno));
397 exit(EXIT_FAILURE);
398 return NULL;
399 }
400 while (1)
401 {
402 bzero(res_data, MAX_LEN);
403 pthread_mutex_lock(&g_lynq_sim_sendto_mutex);
404 send_num = sendto(sock_fd, &client_t, sizeof(client_t), 0, (struct sockaddr *)&addr_serv, len_addr_serv);
405 RLOGD("send_num %d\n", send_num);
406 if(send_num == 0)
407 {
408 RLOGD("__FUNCTION__ %s Close to end %s\n", __FUNCTION__, strerror(errno));
409 //unknow
410 update_ril_value(RIL_SOCKET_SEND_REC_FAIL);
411 pthread_mutex_unlock(&g_lynq_sim_sendto_mutex);
412 continue;
413 }
414 if(send_num < 0)
415 {
416 RLOGD("__FUNCTION__ %s sendto error %s\n", __FUNCTION__, strerror(errno));
417 //unknow
418 update_ril_value(RIL_SOCKET_SEND_REC_FAIL);
419 pthread_mutex_unlock(&g_lynq_sim_sendto_mutex);
420 continue;
421 }
422 //get data msg
423 recv_num = recvfrom(sock_fd,res_data,sizeof(char)*MAX_LEN,0,(struct sockaddr *)&addr_serv,(socklen_t*)&len_addr_serv);
424 RLOGD("recv_num %d\n", recv_num);
425 if(recv_num == -1 && errno == EAGAIN)
426 {
427 RLOGD("__FUNCTION__ %srecvfrom fail because timeout\n", __FUNCTION__);
428 /*set uci*/
429 if(!get_md_sta())
430 {
431 update_ril_value(RIL_MODEM_BOOT_EXCPT);
432 }
433 else
434 {
435 if(check_service("/usr/sbin/mtkfusionrild"))//rild work
436 {
437 if(!check_service("lynq-ril-service"))//not find,must be socket error
438 {
439 update_ril_value(RIL_SOCKET_CREATE_FAIL);
440 }
441 else
442 {
443 //unknow error
444 update_ril_value(RIL_SOCKET_SEND_REC_FAIL);
445 }
446 }
447 else//rild no work
448 {
449 //unknow
450 update_ril_value(RIL_SOCKET_SEND_REC_FAIL);
451 }
452 }
453 pthread_mutex_unlock(&g_lynq_sim_sendto_mutex);
454 check_ril_sleep(count);
455 count++;
456 continue;
457 }
458 if(recv_num <= 0)
459 {
460 RLOGD("__FUNCTION__ %s recvfrom fail %s\n", __FUNCTION__, strerror(errno));
461 update_ril_value(RIL_SOCKET_SEND_REC_FAIL);
462 pthread_mutex_unlock(&g_lynq_sim_sendto_mutex);
463 check_ril_sleep(count);
464 count++;
465 continue;
466 }
467 p.setData((uint8_t *)res_data,sizeof(char)*recv_num);
468 p.setDataPosition(0);
469 if(p.dataAvail() > 0)
470 {
471 p.readInt32(&resp_type);
472 p.readInt32(&token);
473 p.readInt32(&request);
474 p.readInt32(&slot_id);
475 p.readInt32(&res_error);
476 }
477 /*judge the res_error*/
478 if(!res_error)
479 {
480 update_ril_value(RIL_REQUEST_SUCCESS);
481 }
482 else
483 {
484 update_ril_value(RIL_RESP_ERROR_FAIL);
485 }
486 count = 0;
487 RLOGD("__FUNCTION__ %s res_error %d\n", __FUNCTION__, res_error);
488 /*judge the res_error*/
489 pthread_mutex_unlock(&g_lynq_sim_sendto_mutex);
490 check_ril_sleep(sizeof(boot_ril_check_timer)/sizeof(int));
491 }
492 return NULL;
493}
494
495void * wait_ril_event(void * arg)
496{
497 unlock_with_s_start(&s_ril_started);
498 int REC_BUFF_LEN = 64;
499 int recv_num = 0;
500 char rec_data[REC_BUFF_LEN] = {0};
501 int count = 0;
502 struct sockaddr_in wait_ril_event_socket;
503 struct sockaddr_in addr_client;
504 memset(&wait_ril_event_socket, 0,sizeof(wait_ril_event_socket));
505 memset(&addr_client, 0, sizeof(addr_client));
506 wait_ril_event_socket.sin_family = AF_INET;
507 wait_ril_event_socket.sin_addr.s_addr = inet_addr(DSET_IP_ADDRESS);
508 wait_ril_event_socket.sin_port = htons(SDK_READY_PORT);
509 int len_addr_serv = sizeof(addr_client);
510
511 int sock_fd = socket(AF_INET, SOCK_DGRAM, 0);
512 if (-1 == sock_fd)
513 {
514 RLOGD("__FUNCTION__ %s create sock_fd failed %s\n", __FUNCTION__, strerror(errno));
515 exit(EXIT_FAILURE);
516 return NULL;
517 }
518 int ret = bind(sock_fd, (struct sockaddr *)&wait_ril_event_socket, sizeof(wait_ril_event_socket));
519 if (-1 == ret)
520 {
521 RLOGE("liblynq_data_socket bind fail,errno:%d",errno);
522 exit(EXIT_FAILURE);
523 return NULL;
524 }
525 while(1)
526 {
527 memset(rec_data,0,REC_BUFF_LEN);
528 recv_num = recvfrom(sock_fd,rec_data,sizeof(char)*REC_BUFF_LEN,0,(struct sockaddr *)&addr_client,(socklen_t*)&len_addr_serv);
529 if(recv_num <= 0)
530 {
531 RLOGD("__FUNCTION__ %s Close to end\n", __FUNCTION__);
532 update_ril_value(RIL_SOCKET_SEND_REC_FAIL);
533 continue;
534 }
535 rec_data[recv_num] = '\0';
536 if((atoi(rec_data) == RIL_UNSOL_TELEPHONY_RESTART) && (count%2 == 0))//this urc will be reported twice in a row
537 {
538 set_sdk_ready_status_bit(BIT_EXCPT_MD, 1);
539 trigger_sdk_ready_cb(LYNQ_SDK_MD_REBOOT_EXCPT,LYNQ_ACTION_RETRY_DATA_CALL);
540 count = 0;
541 }
542 count ++;
543 }
544 close(sock_fd);
545}
546
547
548void delete_enter(char data[])
549{
550 char *find = strchr(data, '\n');
551 if(find)
552 *find = '\0';
553 return ;
554}
555
556unsigned long long get_interrupts(int fd,char *buffer,int size)
557{
558 char *line = NULL;
559 unsigned long long intr_value = 0;
560 memset(buffer,0,size);
561 lseek(fd, 0, SEEK_SET);
562 ssize_t bytes_intr_read = read(fd,buffer, size - 1);
563 buffer[bytes_intr_read] = '\0';
564 line = strstr(buffer, "intr");
565 if (line == NULL)
566 {
567 RLOGE("get intr fail");
568 }
569 else
570 {
571 line += 5;
572 sscanf(line,"%llu",&intr_value);
573 }
574 return intr_value;
575}
576unsigned long long get_mem_free(int fd,char *buffer,int size)
577{
578 char *line = NULL;
579 unsigned long long mem_value = 0;
580 lseek(fd, 0, SEEK_SET);
581 memset(buffer,0,size);
582 ssize_t bytes_mem_read = read(fd, buffer, size - 1);
583 buffer[bytes_mem_read] = '\0';
584 line = strstr(buffer, "MemFree:");
585 if (line == NULL)
586 {
587 RLOGE("get MemFree fail");
588 }
589 else
590 {
591 line += 9;
592 while (*line == ' ')
593 {
594 line++;
595 }
596 sscanf(line,"%llu",&mem_value);
597 }
598 return mem_value;
599}
600
601void *check_system(void * arg)
602{
603 int fd_mem = 0;
604 int fd_intr = 0;
605 int fd_avg = 0;
606 int fd_free = 0;
607 int BUFFER_SIZE = 512;
608 unsigned long long min_free = 0;
609 unsigned long long mem_value = 0;
610 unsigned long long intr_value_old = 0;
611 unsigned long long intr_value_new = 0;
612 float avg_value = 0;
613 int excpt_flag = 0;
614 char sys_buffer[BUFFER_SIZE];
615 char min_free_buffer[BUFFER_SIZE];
616 unlock_with_s_start(&s_sys_started);
617 fd_mem = open(GET_MEM_INFO,O_RDONLY);
618 fd_free = open(GET_MIN_FREE,O_RDONLY);
619 fd_intr = open(GET_INTR_INFO,O_RDONLY);
620 fd_avg = open(GET_LOAD_AVG_INFO,O_RDONLY);
621 if((fd_mem < 0) || (fd_intr < 0) || (fd_avg < 0) || (fd_free < 0))
622 {
623 RLOGE("check system open fail");
624 exit(EXIT_FAILURE);
625 }
626 memset(min_free_buffer,0,BUFFER_SIZE);
627 ssize_t bytes_min_free_read = read(fd_free, min_free_buffer, BUFFER_SIZE - 1);
628 if(bytes_min_free_read == -1)
629 {
630 RLOGE("get min free fail");
631 exit(EXIT_FAILURE);
632 }
633 min_free = atoi(min_free_buffer);
634 close(fd_free);
635 ssize_t bytes_avg_read = 0;
636 intr_value_old = get_interrupts(fd_intr, sys_buffer, BUFFER_SIZE);
637 while(1)
638 {
639 memset(sys_buffer,0,BUFFER_SIZE);
640 lseek(fd_avg, 0, SEEK_SET);
641 bytes_avg_read = read(fd_avg, sys_buffer, BUFFER_SIZE - 1);
642 sys_buffer[bytes_avg_read] = '\0';
643 sscanf(sys_buffer,"%*f %f",&avg_value);
644
645 mem_value = get_mem_free(fd_mem, sys_buffer, BUFFER_SIZE);
646 intr_value_new = get_interrupts(fd_intr, sys_buffer, BUFFER_SIZE);
647 //pages_min = /proc/sys/vm/min_free_kbytes
648 //pages_low = pages_min*5/4
649 //pages_high = pages_min*3/2
650 if((mem_value >= min_free) && (mem_value < min_free*1.25))//pages_min-pages_low
651 {
652 trigger_sdk_ready_cb(LYNQ_SDK_MIN_FREE_EXCPT,LYNQ_ACTION_SYS_WARNING);
653 excpt_flag = 1;
654 }
655 if(mem_value < min_free)
656 {
657 trigger_sdk_ready_cb(LYNQ_SDK_MIN_FREE_EXCPT,LYNQ_ACTION_REBOOT);
658 excpt_flag = 1;
659 }
660 if(avg_value > global_param->threshold.load_average)
661 {
662 trigger_sdk_ready_cb(LYNQ_SDK_LOAD_AVG_EXCPT,LYNQ_ACTION_SYS_WARNING);
663 excpt_flag = 1;
664 }
665 if((intr_value_new - intr_value_old) > global_param->threshold.interrupts)
666 {
667 trigger_sdk_ready_cb(LYNQ_SDK_INTR_EXCPT,LYNQ_ACTION_SYS_WARNING);
668 excpt_flag = 1;
669 }
670 set_sdk_ready_status_bit(BIT_EXCPT_SYS,excpt_flag);
671 RLOGI("memfree:%llu,intr_old:%llu,intr_new:%llu,intr_delat:%llu,avg:%.2f\n",mem_value,intr_value_old,intr_value_new,(intr_value_new - intr_value_old),avg_value);
672 intr_value_old = intr_value_new;
673 excpt_flag = 0;
674 sleep(global_param->period.SYS);
675 }
676 close(fd_mem);
677 close(fd_intr);
678 close(fd_avg);
679}
680
681/* old code 2024/11/04 close
682void *check(void * arg)
683{
684
685 char pid[200][8];
686 char ffd[200][4];
687 char buf[64];
688 char check_time[4];
689 char timebuf[32];
690 int num = 1;
691 int i=0;
692 int j;
693 FILE *fp,*fp_1;
694 int ret;
695
696 RLOGD("check cpu/pid/interrupts/fd!!!\n");
697 system("mkdir /media/check_file");
698 system("touch /media/check_time");
699 fp_1 = popen("cat /media/check_time","r");
700 if(fgets(check_time, 4, fp_1) != NULL)
701 {
702 num = atoi(check_time);
703 }
704 pclose(fp_1);
705 while(1)
706 {
707 i = 0;
708 system("date >>/media/check_file/cpu_moniter.txt");
709 ret = system("top -b |head -n 25 >>/media/check_file/cpu_moniter.txt");
710 RLOGD("cpu ret %d", ret);
711 system("date >>/media/check_file/inter_moniter.txt");
712 ret = system("cat /proc/interrupts |grep -v \": 0 0\" >>/media/check_file/inter_moniter.txt");
713 RLOGD("interrupts ret %d", ret);
714
715 system("date >>/media/check_file/pid_moniter.txt");
716 ret = system("ps -eo \"%p %a\" | grep -v \"\\[\" >>/media/check_file/pid_moniter.txt");
717 RLOGD("pid ret %d", ret);
718
719 system("date >>/media/check_file/meminfo_moniter.txt");
720 ret = system("cat /proc/meminfo >>/media/check_file/meminfo_moniter.txt");
721 RLOGD("meminfo ret %d", ret);
722
723 system("date >>/media/check_file/buddyinfo_moniter.txt");
724 ret = system("cat /proc/buddyinfo >>/media/check_file/buddyinfo_moniter.txt");
725 RLOGD("buddyinfo ret %d", ret);
726
727 system("date >>/media/check_file/ps_auxw_moniter.txt");
728 ret = system("ps -auxw|grep -v \"0.0 0.0\"|grep -v \"0.1 0.0\"|grep -v \"0.0 0.1\" >>/media/check_file/ps_auxw_moniter.txt");
729 RLOGD("ps_auxw ret %d", ret);
730
731 system("date >>/media/check_file/cur_freq_moniter.txt");
732 ret = system("cat /sys/devices/system/cpu/cpufreq/policy0/scaling_cur_freq >>/media/check_file/cur_freq_moniter.txt");
733 RLOGD("cur_freq ret %d", ret);
734
735 system("date >>/media/check_file/available_frequencies_moniter.txt");
736 ret = system("cat /sys/devices/system/cpu/cpufreq/policy0/scaling_available_frequencies >>/media/check_file/available_frequencies_moniter.txt");
737 RLOGD("available_frequencies ret %d", ret);
738
739 system("date >>/media/check_file/fd_moniter.txt");
740 fp = popen("ps -eo \"%p %a\" | grep -v \"\\[\"|awk '{print $1}'","r");
741 while(fgets(pid[i], 8, fp) != NULL)
742 {
743 delete_enter(pid[i]);
744 i++;
745 }
746 pclose(fp);
747
748 for(j=1;j<i;j++)
749 {
750 sprintf(buf, "ls /proc/%s/fd | wc -l", pid[j]);
751 fp = popen(buf, "r");
752 fgets(ffd[j], 4, fp);
753 sprintf(buf,"echo \"pid: %s, fd_num: %s\" >>/media/check_file/fd_moniter.txt",pid[j], ffd[j]);
754 system(buf);
755 pclose(fp);
756 }
757
758 if(num > 228)
759 {
760 system("cp /media/check_file/cpu_moniter.txt /media/check_file/cpu_moniter_1.txt");
761 system("cp /media/check_file/inter_moniter.txt /media/check_file/inter_moniter_1.txt");
762 system("cp /media/check_file/pid_moniter.txt /media/check_file/pid_moniter_1.txt");
763 system("cp /media/check_file/fd_moniter.txt /media/check_file/fd_moniter_1.txt");
764 system("cp /media/check_file/fd_moniter.txt /media/check_file/meminfo_moniter_1.txt");
765 system("cp /media/check_file/fd_moniter.txt /media/check_file/buddyinfo_moniter_1.txt");
766 system("cp /media/check_file/fd_moniter.txt /media/check_file/ps_auxw_moniter_1.txt");
767 system("cp /media/check_file/fd_moniter.txt /media/check_file/cur_freq_moniter_1.txt");
768 system("cp /media/check_file/fd_moniter.txt /media/check_file/available_frequencies_moniter_1.txt");
769
770
771 system("rm -rf /media/check_file/cpu_moniter.txt");
772 system("rm -rf /media/check_file/inter_moniter.txt");
773 system("rm -rf /media/check_file/pid_moniter.txt");
774 system("rm -rf /media/check_file/fd_moniter.txt");
775 system("rm -rf /media/check_file/meminfo_moniter.txt");
776 system("rm -rf /media/check_file/buddyinfo_moniter.txt");
777 system("rm -rf /media/check_file/ps_auxw_moniter.txt");
778 system("rm -rf /media/check_file/cur_freq_moniter.txt");
779 system("rm -rf /media/check_file/available_frequencies_moniter.txt");
780
781 num = 0;
782 }
783 num++;
784 sprintf(timebuf, "echo \"%d\" >/media/check_time", num);
785 ret = system(timebuf);
786 sleep(300);
787 }
788 return NULL;
789
790}
791
792int num = 0;
793void *check_uci(void * arg)
794{
795 int ret[6];
796 int result = 0;
797 int flag = 0;
798
799 char uci_0[]="/etc/config/lynq_uci";
800 char uci_1[]="/etc/config/lynq_uci_ro";
801 char uci_2[]="/etc/config/mdlog";
802 char uci_3[]="/etc/config/radio_property";
803 char uci_4[]="/etc/config/service";
804 char uci_5[]="/etc/config/usb";
805 RLOGD("start check uci\n");
806 while(num++ < 4)
807 {
808 RLOGD("@@@@@@@num=%d\n", num);
809 flag = 0;
810 ret[0] = system("uci show | grep \"lynq_uci.lynq_ril\" > /dev/null");
811 if(ret[0] != 0)
812 {
813 RLOGD("lynq_uci unload\n");
814 flag = 1;
815 }
816
817 ret[1] = system("uci show | grep \"^lynq_uci_ro\.\" > /dev/null");
818 if(ret[1] != 0)
819 {
820 RLOGD("lynq_uci_ro unload\n");
821 flag = 1;
822 }
823
824 ret[2] = system("uci show | grep \"^mdlog\.\"");
825 if(ret[2] != 0)
826 {
827 RLOGD("mdlog unload\n");
828 flag = 1;
829 }
830
831 ret[3] = system("uci show | grep \"^radio_property\.\" > /dev/null");
832 if(ret[3] != 0)
833 {
834 RLOGD("radio_property unload\n");
835 flag = 1;
836 }
837
838 ret[4] = system("uci show | grep \"^service\.\" > /dev/null");
839 if(ret[4] != 0)
840 {
841 RLOGD("service unload\n");
842 flag = 1;
843 }
844
845 ret[5] = system("uci show | grep \"^usb\.\" > /dev/null");
846 if(ret[5] != 0)
847 {
848 RLOGD("usb unload\n");
849 flag = 1;
850 }
851
852 RLOGD("flag=%d\n",flag);
853 if(flag != 0)
854 {
855 RLOGD("config reload\n");
856 result = chdir("/data_backup/");
857 result =system("tar -zxvf userdata.tar.gz -C /STATE/ >/dev/null");
858 if(result!= 0)
859 {
860 RLOGD("cp config fail\n");
861 }
862 if(ret[0] != 0)
863 {
864 lynq_load_config(uci_0);
865 RLOGD("reload lynq_uci\n");
866 system("systemctl start autosuspend");
867 }
868 if(ret[1] != 0)
869 {
870 lynq_load_config(uci_1);
871 RLOGD("reload lynq_uci_ro\n");
872 }
873 if(ret[2] != 0)
874 {
875 lynq_load_config(uci_2);
876 RLOGD("reload mdlog\n");
877 }
878 if(ret[3] != 0)
879 {
880 lynq_load_config(uci_3);
881 RLOGD("reload radio_property\n");
882 system("systemctl restart mtkfusionrild");
883 }
884 if(ret[4] != 0)
885 {
886 lynq_load_config(uci_4);
887 RLOGD("reload service\n");
888 }
889 if(ret[5] != 0)
890 {
891 lynq_load_config(uci_5);
892 RLOGD("reload usb\n");
893 }
894 }
895 else
896 {
897 RLOGD("uci check success, exit check!\n");
898 break;
899 }
900 sleep(2);
901 }
902 return NULL;
903}
904old code 2024/11/04 close*/
905
906static void t800_check_partition()
907{
908 char buf[64] = {0};
909 FILE *fp = NULL;
910 int q = 22*1024;
911 int ubisize = 0;
912
913 fp = popen("df -l| grep '/data$' | awk '{print $3}'","r");
914 if(fp == NULL)
915 {
916 RLOGD("Failed to run command\n");
917 return;
918 }
919 fgets(buf, sizeof(buf) - 1, fp);
920 RLOGD("buf is: %s\n",buf);
921 ubisize = atoi(buf);
922 if(ubisize >= q)
923 {
924 RLOGD(">set ready 5,userdata size is %d M\n",ubisize);
925 update_userdata_value();
926 }
927 else
928 {
929 set_sdk_ready_status_bit(BIT_EXCPT_PTN, 0);
930 }
931 return;
932}
933void t800_check_mnld()
934{
935 FILE *fp;
936 const char *symble = "NRestarts=";
937 const char *cmd = "systemctl show -p NRestarts mnld.service";
938 char buf[64];
939 int count_old = 0;
940 int count_new = 0;
941 while(1)
942 {
943 fp = popen(cmd,"r");
944 while(fgets(buf, sizeof(buf) - 1, fp) != NULL)
945 {
946 if(strncmp(buf,symble,strlen(symble)) == 0)
947 count_new = atoi(buf+strlen(symble));
948 memset(buf,0,sizeof(buf));
949 }
950 if((count_new - count_old) > 1)
951 {
952 update_gnss_value();//out put mnld severe abnormal state
953 RLOGD("mnld is severe abnormal state = %d\n",count_new - count_old);
954 }
955 else
956 {
957 set_sdk_ready_status_bit(BIT_EXCPT_GNSS,0);
958 }
959 pclose(fp);
960 count_old = count_new;
961 sleep(global_param->period.GNSS);
962 }
963 return;
964}
965void *check_partition(void *arg)
966{
967 unlock_with_s_start(&s_ptn_started);
968 while(1)
969 {
970 t800_check_partition();
971 sleep(global_param->period.PTN);
972 }
973 return NULL;
974}
975
976void *check_gnss(void * arg)
977{
978 unlock_with_s_start(&s_gnss_started);
979 t800_check_mnld();
980 return NULL;
981}
982int get_cpu_info()
983{
984 FILE *CPU_FD = NULL;
985 int cpu_num = 0;
986 char cpu_info[8];
987 CPU_FD = popen(GET_CPU_NUM,"r");
988 if(CPU_FD == NULL)
989 {
990 RLOGD("get cpu info fail:%s",GET_CPU_NUM);
991 return -1;
992 }
993 fgets(cpu_info, sizeof(cpu_info) - 1, CPU_FD);
994 cpu_num = atoi(cpu_info);
995 pclose(CPU_FD);
996 return cpu_num;
997}
998int set_default_sdk_check_param(lynq_sdk_check_param_t *param)
999{
1000 int cpu_num = 0;
1001 param->period.RIL = DEFAULT_PERIOD_RIL;
1002 param->period.GNSS = DEFAULT_PERIOD_GNSS;
1003 param->period.MD = DEFAULT_PERIOD_MD;
1004 param->period.PTN = DEFAULT_PERIOD_PTN;
1005 param->period.SYS = DEFAULT_PERIOD_SYS;
1006 param->period.BOOT = DEFAULT_PERIOD_BOOT;
1007 cpu_num = get_cpu_info();
1008 if(cpu_num <= 0)
1009 {
1010 RLOGE("set default sdk check param fail");
1011 return -1;
1012 }
1013 param->threshold.interrupts = (DEFAULT_PERIOD_SYS/30)*cpu_num*5000;
1014 param->threshold.load_average = cpu_num*2;
1015 return 0;
1016}
1017int create_check_threads(void)
1018{
1019 pthread_t thid,thid_1,thid_2,thid_3,thid_4;
1020 pthread_attr_t attr;
1021 pthread_attr_init(&attr);
1022 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
1023 int ret;
1024 pthread_mutex_lock(&s_startupMutex);
1025 ret = pthread_create(&thid, &attr, timer_request_imei, NULL);
1026 if(ret != 0)
1027 {
1028 RLOGE("timer_request_imei error!!!");
1029 goto excp;
1030 }
1031 while (s_ril_started == 0)
1032 {
1033 pthread_cond_wait(&s_startupCond, &s_startupMutex);
1034 }
1035 ret = pthread_create(&thid_1, &attr, check_system, NULL);
1036 if(ret != 0)
1037 {
1038 RLOGE("check_system error!!!");
1039 goto excp;
1040 }
1041 while (s_sys_started == 0)
1042 {
1043 pthread_cond_wait(&s_startupCond, &s_startupMutex);
1044 }
1045
1046 ret = pthread_create(&thid_2, &attr,check_gnss,NULL);
1047 if(ret != 0)
1048 {
1049 RLOGD("check_gnss error!!!");
1050 goto excp;
1051 }
1052 while (s_gnss_started == 0)
1053 {
1054 pthread_cond_wait(&s_startupCond, &s_startupMutex);
1055 }
1056 ret = pthread_create(&thid_3, &attr,check_partition,NULL);
1057 if(ret != 0)
1058 {
1059 RLOGD("check_partition error!!!");
1060 goto excp;
1061 }
1062 while (s_ptn_started == 0)
1063 {
1064 pthread_cond_wait(&s_startupCond, &s_startupMutex);
1065 }
1066 s_ril_started = 0;
1067 ret = pthread_create(&thid_4, &attr,wait_ril_event,NULL);
1068 if(ret != 0)
1069 {
1070 RLOGD("wait_ril_event error!!!");
1071 goto excp;
1072 }
1073 while (s_ril_started == 0)
1074 {
1075 pthread_cond_wait(&s_startupCond, &s_startupMutex);
1076 }
1077 pthread_mutex_unlock(&s_startupMutex);
1078 return 0;
1079excp:
1080 pthread_mutex_unlock(&s_startupMutex);
1081 return LYNQ_E_NORMAL;
1082}
1083int lynq_sdk_ready_register(const int uToken,const lynq_sdk_check_param_t* param,lynq_sdk_status_cb sdk_status_cb)
1084{
1085 int ret = 0;
1086 if (param == NULL || sdk_status_cb == NULL)
1087 {
1088 RLOGE("input null");
1089 return LYNQ_E_NULL_ANONALY;
1090 }
1091 utoken = uToken;
1092 global_param = (lynq_sdk_check_param_t *)malloc(sizeof(lynq_sdk_check_param_t));
1093 if(global_param == NULL)
1094 {
1095 RLOGE("malloc global_param fail");
1096 goto end;
1097 }
1098 memset(global_param,0,sizeof(lynq_sdk_check_param_t));
1099 if(param->isvalid == 0)
1100 {
1101 ret = set_default_sdk_check_param(global_param);
1102 if (ret < 0)
1103 {
1104 RLOGE("get default param fail");
1105 goto end;
1106 }
1107 }
1108 else
1109 {
1110 if((param->period.RIL < MIN_PERIOD_RIL) || (param->period.GNSS < MIN_PERIOD_GNSS) || (param->period.MD < MIN_PERIOD_MD)
1111 || (param->period.PTN < MIN_PERIOD_PTN) || (param->period.SYS < MIN_PERIOD_SYS))
1112 {
1113 RLOGE("param excption");
1114 goto end;
1115 }
1116 global_param->period.RIL = param->period.RIL;
1117 global_param->period.GNSS = param->period.GNSS;
1118 global_param->period.MD = param->period.MD;
1119 global_param->period.PTN = param->period.PTN;
1120 global_param->period.SYS = param->period.SYS;
1121 global_param->period.BOOT = param->period.BOOT;
1122 global_param->threshold.interrupts = param->threshold.interrupts;
1123 global_param->threshold.load_average = param->threshold.load_average;
1124 }
1125 RLOGI("period.RIL:%d,period.GNSS:%d,period.MD:%d,period.PTN:%d,period.SYS:%d,threshold.interrupts:%llu,threshold.load_average:%d",
1126 global_param->period.RIL,global_param->period.GNSS,global_param->period.MD,global_param->period.PTN,
1127 global_param->period.SYS,global_param->threshold.interrupts,global_param->threshold.load_average);
1128 global_sdk_status_cb = sdk_status_cb;
1129 global_sdk_status.sdk_ready_status = (lynq_sdk_status_t)-1;
1130 global_sdk_status.ref_action = (lynq_sdk_ref_action_t)-1;
1131 set_sdk_ready_nv(1);//开机默认RIL 异常,第一次检测完成之后更新正确值
1132 ret = create_check_threads();
1133 if(ret != 0)
1134 {
1135 goto end;
1136 }
1137 return ret;
1138end:
1139 exit(EXIT_FAILURE);
1140}
1141int lynq_get_sdk_ready_status(int *status)
1142{
1143 if (status == NULL)
1144 {
1145 RLOGE("sdk_ready_status is null");
1146 return LYNQ_E_NULL_ANONALY;
1147 }
1148 *status = global_sdk_ready_status;
1149 return 0;
1150}