main.c 77 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272
  1. #include <sys/poll.h>
  2. #include <string.h>
  3. #include <stdio.h>
  4. #include <stdlib.h>
  5. #include <sys/types.h>
  6. #include <sys/wait.h>
  7. #include <spawn.h>
  8. #include <unistd.h>
  9. #include <fcntl.h>
  10. #include <assert.h>
  11. #include <time.h>
  12. #include <pthread.h>
  13. #include "hiredis/hiredis.h"
  14. #include "cjson/cJSON.h"
  15. #include "iniparser/iniparser.h"
  16. #include "log.h"
  17. #define Boolean int
  18. #define TRUE 1
  19. #define FALSE 0
  20. #define MAX_PIPE_BUFSIZE 256
  21. //KEYS
  22. #define UNKEY 0
  23. #define KEY 1
  24. #define KEY2_3 2
  25. #define KEY2_10 3
  26. #define OPEN 4
  27. #define CLOSED 4
  28. //SCHEDULE STATE
  29. #define ERROR -1
  30. #define STOP 0
  31. #define RUNNING 1
  32. #define PAUSED 2
  33. #define MAX_PRIORITY 10
  34. #define MAX_TRY 3
  35. //BARESIP_STATUS
  36. #define IDLE 0
  37. #define INUSE 1
  38. #define RING 2
  39. #define RINGING 3
  40. #define HOLD 4
  41. #define OFFLINE 5
  42. #define DIALING 6
  43. //BARESIP_REG
  44. #define REGISTER_FAIL 0
  45. #define REGISTER_OK 1
  46. //LED_STATUS
  47. #define Led_Off 0
  48. #define Led_On 1
  49. #define Led_Fast 2
  50. #define Led_Slow 3
  51. //REDIS_CHANNEL
  52. #define BARESIP_CHAN 0
  53. #define GPIO_CHAN 1
  54. //GPIO_STATUS
  55. #define GPIO_OFF 0
  56. #define GPIO_ON 1
  57. #define SPK_CONF "/etc/speaker.conf"
  58. #define VOL_CONF "/oem/etc/volctrl.conf"
  59. #define SIPLOGPATH "/userdata/system.csv"
  60. #define CDR_CSV "/userdata/cdr.csv"
  61. #define SCHEDULE_CONF "/oem/etc/schedule.conf"
  62. #define unix_socket_path "/tmp/redis.sock"
  63. //operator log type
  64. #define BTN "BUTTON"
  65. #define FUN "FUNCTION"
  66. #define STA "SIP STATE"
  67. #define SCHED "SCHEDULE"
  68. #define GPIO_RELAY "gpio112"
  69. #define VAR_IP "${ip}"
  70. #define VAR_MAC "${mac}"
  71. #define VAR_UA "${ua}"
  72. #define VAR_NUM "${number}"
  73. #define AUDIO_ON "{\"name\": \"SCHEDULER-AUDIO\", \"action\": \"on\"}"
  74. #define AUDIO_OFF "{\"name\": \"SCHEDULER-AUDIO\", \"action\": \"off\"}"
  75. struct date{ //声明结构体date用于表示日期
  76. int year;
  77. int month;
  78. int day;
  79. };
  80. struct VLC_INFO{
  81. pid_t pid;
  82. int prio;
  83. char param[96];
  84. };
  85. typedef struct _playInfo{
  86. int key_id;
  87. int prio;
  88. int vol;
  89. char file[64];
  90. char times_str[8];
  91. char enBeep[8];
  92. char enSrceen[8];
  93. } PlayInfo;
  94. struct CALL_LOG{
  95. char date[16];
  96. char start[16];
  97. char end[16];
  98. char acc[32];
  99. char num[32];
  100. char direct[8];
  101. char status[16];
  102. time_t answerTime;
  103. int duration;
  104. char desc[64];
  105. };
  106. typedef struct {
  107. int in_use[5];
  108. redisContext *context[5];
  109. const char *socket_path;
  110. time_t last_activity[5];
  111. pthread_mutex_t lock;
  112. } redis_client_t;
  113. static int BARESIP_STATUS = OFFLINE;
  114. static int key1LedStatus = Led_Off;
  115. static int key2LedStatus = Led_Off;
  116. static int CURRENT_KEY = UNKEY;
  117. static int DEBUG = FALSE;
  118. static int ACCOUNT1_REG = REGISTER_FAIL;
  119. static int ACCOUNT2_REG = REGISTER_FAIL;
  120. static int ACCOUNT3_REG = REGISTER_FAIL;
  121. static int ACCOUNTP2P_REG = REGISTER_FAIL;
  122. static int press_down = FALSE;
  123. static int CURRENT_CALLS = 0;
  124. static int regcount = 0;
  125. static char DTMF_STRING[32] = "\0";
  126. static int SCHEDULE[31];
  127. struct VLC_INFO vlcInfo[64];
  128. struct CALL_LOG callInfo;
  129. static redis_client_t *redisClient;
  130. redis_client_t* create_redis_pool_client(const char *socket_path) {
  131. redis_client_t *client = (redis_client_t *) malloc(sizeof(redis_client_t));
  132. client->socket_path = socket_path;
  133. pthread_mutex_init(&client->lock, NULL);
  134. for(int i = 0; i < 5; i++)
  135. {
  136. redisContext *c = redisConnectUnix(socket_path);
  137. if (c == NULL || c->err) {
  138. if (c) {
  139. printf("Connection error: %s\n", c->errstr);
  140. redisFree(c);
  141. } else {
  142. printf("Connection error: can't allocate redis context\n");
  143. }
  144. // 可以选择重试或退出
  145. continue;
  146. }
  147. client->context[i] = c;
  148. client->in_use[i] = FALSE;
  149. client->last_activity[i] = time(NULL);
  150. }
  151. return client;
  152. }
  153. const int redis_pool_get_context(redis_client_t *client) {
  154. pthread_mutex_lock(&client->lock);
  155. redisContext *context = NULL;
  156. int idx = -1;
  157. for(int i = 0;i < 5; i++)
  158. {
  159. if(!client->in_use[i])
  160. {
  161. idx = i;
  162. client->in_use[idx] = TRUE;
  163. context = client->context[idx];
  164. redisReply *reply = redisCommand(context, "PING");
  165. if (reply == NULL || context->err) {
  166. // 连接失效,尝试重连
  167. if(DEBUG)
  168. printf( "redis connect failed, retry!\n" );
  169. redisFree(context);
  170. context = redisConnectUnix(client->socket_path);
  171. client->context[idx] = context;
  172. }
  173. freeReplyObject(reply);
  174. client->last_activity[idx] = time(NULL);
  175. break;
  176. }
  177. }
  178. pthread_mutex_unlock(&client->lock);
  179. if (context == NULL) {
  180. printf("No available connections in pool\n");
  181. }
  182. return idx;
  183. }
  184. // 释放连接
  185. void redis_pool_release_connection(redis_client_t *client, const int id) {
  186. pthread_mutex_lock(&client->lock);
  187. client->in_use[id] = FALSE;
  188. pthread_mutex_unlock(&client->lock);
  189. }
  190. void redis_command_safe(const char *format, const char *value) {
  191. const int id = redis_pool_get_context(redisClient);
  192. if (id != -1) {
  193. redisReply *reply = (redisReply *) redisCommand(redisClient->context[id], format, value);
  194. if (reply) {
  195. // 处理回复
  196. freeReplyObject(reply);
  197. }
  198. redis_pool_release_connection(redisClient, id);
  199. }
  200. }
  201. int ensure_connected(redisContext *context) {
  202. if (context == NULL || context->err) {
  203. if (context) {
  204. redisFree(context);
  205. }
  206. context = redisConnectUnix(unix_socket_path);
  207. if (context == NULL || context->err) {
  208. return -1; // 连接失败
  209. }
  210. }
  211. return 0;
  212. }
  213. void reset_callInfo()
  214. {
  215. memset(&callInfo,0,sizeof(callInfo));
  216. callInfo.duration = 0;
  217. }
  218. void *write_opnlog()
  219. {
  220. char * pKey = "writelog-channel";
  221. redisReply *pReply, *pSubReply;
  222. redisContext *redisLogContext = NULL;
  223. redisLogContext = redisConnectUnix(unix_socket_path);
  224. restart:
  225. FILE *logFp = fopen(SIPLOGPATH, "a");
  226. log_add_fp(logFp, LOG_INFO);
  227. while(1)
  228. {
  229. pReply = NULL;
  230. if (ensure_connected(redisLogContext) == 0) {
  231. pReply = redisCommand( redisLogContext, "BRPOP %s 60", pKey );
  232. if(pReply != NULL && pReply->type == REDIS_REPLY_ARRAY){
  233. pSubReply = NULL;
  234. if ( pReply->elements == 2 )
  235. {
  236. pSubReply = pReply->element[1];
  237. if(DEBUG)
  238. printf( "opnLog [%s]\n", pSubReply->str );
  239. if(strcmp(pSubReply->str, "log_clean") == 0)
  240. {
  241. fclose(logFp);
  242. freeReplyObject( pReply );
  243. sleep(5);
  244. goto restart;
  245. }
  246. else
  247. log_info("%s", pSubReply->str);
  248. }
  249. }
  250. }
  251. if(pReply != NULL) freeReplyObject( pReply );
  252. usleep(200*1000);
  253. }
  254. redisFree( redisLogContext );
  255. }
  256. void writeLog(char *type,char *action, char *remark)
  257. {
  258. char logstr[256];
  259. sprintf(logstr, "%s,%s,%s", type, action, remark);
  260. redis_command_safe("LPUSH writelog-channel %s", logstr);
  261. }
  262. //发送状态指令
  263. void state_event(char *info)
  264. {
  265. redis_command_safe("PUBLISH volume-event-channel %s", info);
  266. }
  267. //发送屏幕显示指令
  268. void screen_control(char *cmd)
  269. {
  270. redis_command_safe("PUBLISH screen-channel %s", cmd);
  271. }
  272. void insert_call_log()
  273. {
  274. FILE *cdr_fp = fopen(CDR_CSV, "a");
  275. //日期,开始时间,结束时间,账号,号码,通话时长,方向,状态,描述
  276. fprintf(cdr_fp, "%s,%s,%s,%s,%s,%d,%s,%s,%s\n",
  277. callInfo.date, callInfo.start, callInfo.end, callInfo.acc, callInfo.num, callInfo.duration,
  278. callInfo.direct, callInfo.status, callInfo.desc);
  279. fclose(cdr_fp);
  280. reset_callInfo();
  281. }
  282. void setIncomingCallInfo(char *accuri, char *num)
  283. {
  284. char acc[32];
  285. time_t nSeconds;
  286. struct tm *pTM;
  287. int year, month, hour;
  288. time(&nSeconds);
  289. pTM = localtime(&nSeconds);
  290. year = pTM->tm_year + 1900;
  291. month = pTM->tm_mon + 1;
  292. memset(acc,0,sizeof(acc));
  293. strcpy(callInfo.direct,"in");
  294. sprintf(callInfo.date, "%d-%02d-%02d", year, month, pTM->tm_mday);
  295. sprintf(callInfo.start, "%02d:%02d:%02d", pTM->tm_hour, pTM->tm_min, pTM->tm_sec);
  296. //strncpy(acc, accuri, strchr(accuri,'@') - accuri);
  297. //strcpy(callInfo.acc, acc + 4);
  298. strcpy(callInfo.acc, accuri);
  299. strcpy(callInfo.num, num);
  300. strcpy(callInfo.status, "MISSED CALL");
  301. }
  302. void setOutgoingCallInfo(char *accuri, char *num)
  303. {
  304. char acc[32];
  305. time_t nSeconds;
  306. struct tm *pTM;
  307. int year, month, hour;
  308. time(&nSeconds);
  309. pTM = localtime(&nSeconds);
  310. year = pTM->tm_year + 1900;
  311. month = pTM->tm_mon + 1;
  312. memset(acc,0,sizeof(acc));
  313. strcpy(callInfo.direct,"out");
  314. sprintf(callInfo.date, "%d-%02d-%02d", year, month, pTM->tm_mday);
  315. sprintf(callInfo.start, "%02d:%02d:%02d", pTM->tm_hour, pTM->tm_min, pTM->tm_sec);
  316. //strncpy(acc, accuri, strchr(accuri,'@') - accuri);
  317. //strcpy(callInfo.acc, acc + 4);
  318. strcpy(callInfo.acc, accuri);
  319. strcpy(callInfo.num, num);
  320. strcpy(callInfo.status, "NO ANSWER");
  321. }
  322. void setAnswerCallInfo()
  323. {
  324. time_t nSeconds;
  325. time(&nSeconds);
  326. callInfo.answerTime = nSeconds;
  327. strcpy(callInfo.status, "ANSWERED");
  328. }
  329. void setClosedCallInfo(char *param)
  330. {
  331. time_t nSeconds;
  332. struct tm *pTM;
  333. time(&nSeconds);
  334. pTM = localtime(&nSeconds);
  335. sprintf(callInfo.end, "%02d:%02d:%02d", pTM->tm_hour, pTM->tm_min, pTM->tm_sec);
  336. strcpy(callInfo.desc, param);
  337. if(callInfo.answerTime)
  338. {
  339. callInfo.duration = nSeconds - callInfo.answerTime;
  340. }
  341. insert_call_log();
  342. }
  343. /*
  344. * @file 文件路径
  345. * @value 命令结果指针
  346. * @lenth 存储结果长度
  347. */
  348. int GetCmdValue(char *file, char *key, char *value, int lenth)
  349. {
  350. dictionary * ini ;
  351. ini = iniparser_load(file);
  352. if (ini==NULL) {
  353. fprintf(stderr, "cannot parse file: %s\n", file);
  354. return FALSE ;
  355. }
  356. strcpy(value, iniparser_getstring(ini, key, ""));
  357. if(DEBUG)
  358. printf("keystr: \"%s\" ; value: %s.\n", key, value);
  359. iniparser_freedict(ini);
  360. return TRUE;
  361. }
  362. char *strrpl(char *s, const char *s1, const char *s2)
  363. {
  364. char *ptr;
  365. while (ptr = strstr(s, s1)) /* 如果在s中找到s1 */
  366. {
  367. memmove(ptr + strlen(s2) , ptr + strlen(s1), strlen(ptr) - strlen(s1) + 1);
  368. memcpy(ptr, &s2[0], strlen(s2));
  369. }
  370. return s;
  371. }
  372. //控制功放的开启/关闭,TRUE/FALSE
  373. void amplifier_switch(Boolean enable){
  374. if(enable)
  375. system("echo 1 > /sys/class/gpio/gpio5/value");
  376. else
  377. system("echo 0 > /sys/class/gpio/gpio5/value");
  378. }
  379. Boolean get_ip(char * pv)
  380. {
  381. FILE * fp;
  382. char cmdbuf[128], value[32];
  383. char *tmp=NULL;
  384. sprintf(cmdbuf,"/sbin/ifconfig eth1 | grep 'inet ' | awk '{print $2}'");
  385. fp = popen(cmdbuf, "r");
  386. if (fp == NULL) {
  387. // printf("Fail to open pipe\n");
  388. return FALSE;
  389. }
  390. memset(value,0,sizeof(value));
  391. if (!feof(fp) && fgets(value,32,fp) != NULL)
  392. ;
  393. // printf("value:%s\n", value);
  394. else {
  395. printf("ip wrong\n");
  396. return FALSE;
  397. }
  398. pclose(fp);
  399. if(strlen(value) < 10)
  400. return FALSE;
  401. if(tmp = strstr(value,"\n"))
  402. {
  403. *tmp = '\0';
  404. }
  405. strcpy(pv,value);
  406. return TRUE;
  407. }
  408. Boolean get_mac(char * pv)
  409. {
  410. FILE * fp;
  411. char cmdbuf[128], value[32];
  412. char *tmp=NULL;
  413. sprintf(cmdbuf,"ifconfig eth1 | grep ether | tr -d : | awk '{print $2}'");
  414. fp = popen(cmdbuf, "r");
  415. if (fp == NULL) {
  416. return FALSE;
  417. }
  418. memset(value,0,sizeof(value));
  419. if (!feof(fp) && fgets(value,32,fp) != NULL)
  420. ;
  421. // printf("value:%s\n", value);
  422. else {
  423. printf("ip wrong\n");
  424. return FALSE;
  425. }
  426. pclose(fp);
  427. if(strlen(value) < 10)
  428. return FALSE;
  429. if(tmp = strstr(value,"\n"))
  430. {
  431. *tmp = '\0';
  432. }
  433. strcpy(pv,value);
  434. return TRUE;
  435. }
  436. int PlayIP()
  437. {
  438. //add by ssc 2019-12-26
  439. char language[32];
  440. GetCmdValue(SPK_CONF, "system:language", language, sizeof(language));
  441. char ipaddr[16],cmd_line[240];
  442. system("/usr/bin/amixer -q sset 'Master',0 29");
  443. amplifier_switch(TRUE); //开启功放
  444. if(!get_ip(ipaddr)) {
  445. if (strcmp(language, "en") == 0){
  446. system("mpg123 -r 48000 /usr/share/sounds/en/get_ip_failed.mp3");
  447. }else{
  448. system("mpg123 -r 48000 /usr/share/sounds/cn/get_ip_failed.mp3");
  449. }
  450. return 0;
  451. }
  452. if (strcmp(language, "en") == 0){
  453. strcpy(cmd_line,"cd /usr/share/sounds/en/;mpg123 -r 48000 ");
  454. }else{
  455. strcpy(cmd_line,"cd /usr/share/sounds/cn/;mpg123 -r 48000 ");
  456. }
  457. int i;
  458. for (i=0;i<strlen(ipaddr);i++){
  459. switch(ipaddr[i])
  460. {
  461. case '0':
  462. strcat(cmd_line,"digit-0.mp3 ");
  463. break;
  464. case '1':
  465. strcat(cmd_line,"digit-1.mp3 ");
  466. break;
  467. case '2':
  468. strcat(cmd_line,"digit-2.mp3 ");
  469. break;
  470. case '3':
  471. strcat(cmd_line,"digit-3.mp3 ");
  472. break;
  473. case '4':
  474. strcat(cmd_line,"digit-4.mp3 ");
  475. break;
  476. case '5':
  477. strcat(cmd_line,"digit-5.mp3 ");
  478. break;
  479. case '6':
  480. strcat(cmd_line,"digit-6.mp3 ");
  481. break;
  482. case '7':
  483. strcat(cmd_line,"digit-7.mp3 ");
  484. break;
  485. case '8':
  486. strcat(cmd_line,"digit-8.mp3 ");
  487. break;
  488. case '9':
  489. strcat(cmd_line,"digit-9.mp3 ");
  490. break;
  491. case '.':
  492. strcat(cmd_line,"dian.mp3 ");
  493. break;
  494. }
  495. }
  496. // printf("cmd-line:%s\n", cmd_line);
  497. system(cmd_line);
  498. amplifier_switch(FALSE); //关闭功放
  499. system("/etc/scripts/set_volume.sh resume");
  500. writeLog( FUN, "Play IP Address", ipaddr );
  501. return 0;
  502. }
  503. void action_url(char *url)
  504. {
  505. char cmd[320];
  506. sprintf(cmd,"curl -k --connect-timeout 5 '%s' 2>/dev/null &",url);
  507. if(DEBUG)
  508. printf( "Command: %s\n", cmd);
  509. system(cmd);
  510. }
  511. void playBeep()
  512. {
  513. char beep[8];
  514. GetCmdValue(VOL_CONF, "volume:key_beep", beep, sizeof(beep));
  515. if(strcmp(beep, "yes") == 0)
  516. {
  517. if(BARESIP_STATUS == IDLE || BARESIP_STATUS == OFFLINE)
  518. system("/usr/sbin/redis-cli PUBLISH volume-event-channel '{\"name\": \"SIP\", \"action\": \"on\"}'");
  519. system("mpg123 /home/new-speaker/target/share/sounds/beep.mp3");
  520. usleep(400*1000);
  521. if(BARESIP_STATUS == IDLE || BARESIP_STATUS == OFFLINE)
  522. system("/usr/sbin/redis-cli PUBLISH volume-event-channel '{\"name\": \"SIP\", \"action\": \"off\"}'"); //关闭功放
  523. }
  524. }
  525. //发送控制指令
  526. void control_cmd(int channel, char *cmd)
  527. {
  528. char redisCmd[256];
  529. switch (channel)
  530. {
  531. case BARESIP_CHAN:
  532. if(DEBUG)
  533. printf( "control-channel [%s]\n", cmd );
  534. redis_command_safe("LPUSH control-channel %s", cmd );
  535. break;
  536. case GPIO_CHAN:
  537. if(DEBUG)
  538. printf( "output-channel [%s]\n", cmd );
  539. redis_command_safe("LPUSH output-channel %s", cmd );
  540. break;
  541. default:
  542. redis_command_safe("LPUSH control-channel %s", cmd );
  543. break;
  544. }
  545. }
  546. void relayControl(char *id, int enable){
  547. char cmd[64];
  548. int channel = GPIO_CHAN;
  549. if(enable){
  550. char output_type[32];
  551. GetCmdValue(SPK_CONF, "relay_ctrl:type", output_type, sizeof(output_type));
  552. sprintf(cmd,"{\"id\":\"%s\",\"type\":\"%s\"}",id,output_type);
  553. control_cmd(channel,cmd);
  554. }
  555. else
  556. {
  557. sprintf(cmd,"{\"id\":\"%s\",\"type\":\"Off\"}",id);
  558. control_cmd(channel,cmd);
  559. }
  560. }
  561. void screenControl(int enable){
  562. char cmd[64], output_type[16];
  563. GetCmdValue(SPK_CONF, "screen_ctrl:type", output_type, sizeof(output_type));
  564. if(enable){
  565. sprintf(cmd,"{\"action\": \"on\", \"id\": %s}",output_type);
  566. screen_control(cmd);
  567. }
  568. else
  569. {
  570. sprintf(cmd,"{\"action\": \"off\", \"id\": %s}",output_type);
  571. screen_control(cmd);
  572. }
  573. }
  574. void ai_ctrl(Boolean en)
  575. {
  576. char hversion[16];
  577. GetCmdValue(SPK_CONF, "system:hard_version", hversion, sizeof(hversion));
  578. if(en)
  579. {
  580. char ai[8];
  581. GetCmdValue(SPK_CONF, "ai_settings:enable", ai, sizeof(ai));
  582. if(strcmp(ai, "yes") == 0)
  583. {
  584. if(strcmp(hversion, "Ver3.2") == 0)
  585. system("echo 1 > /sys/class/gpio/gpio143/value");
  586. else
  587. system("echo 1 > /sys/class/gpio/gpio134/value");
  588. }
  589. }
  590. else
  591. {
  592. if(strcmp(hversion, "Ver3.2") == 0)
  593. system("echo 0 > /sys/class/gpio/gpio143/value");
  594. else
  595. system("echo 0 > /sys/class/gpio/gpio134/value");
  596. }
  597. }
  598. //relay延时控制
  599. void *relayDelayControl()
  600. {
  601. char delay[8];
  602. GetCmdValue(SPK_CONF, "relay_ctrl:duration", delay, sizeof(delay));
  603. usleep(atoi(delay)*1000*1000);
  604. relayControl(GPIO_RELAY, GPIO_OFF);
  605. if(DEBUG)
  606. printf( "GPIO_RELAY set off\n" );
  607. }
  608. //srceen延时控制
  609. void *screenDelayControl()
  610. {
  611. char delay[8];
  612. GetCmdValue(SPK_CONF, "screen_ctrl:duration", delay, sizeof(delay));
  613. usleep(atoi(delay)*1000*1000);
  614. screenControl(FALSE);
  615. if(DEBUG)
  616. printf( "screen set off\n" );
  617. }
  618. void *key1ScreenDelayControl()
  619. {
  620. char delay[8], srceen_id[16], strtmp[64];
  621. GetCmdValue(SPK_CONF, "intercom:screen_1_duration", delay, sizeof(delay));
  622. usleep(atoi(delay)*1000*1000);
  623. GetCmdValue(SPK_CONF, "intercom:trigger_1_id", srceen_id, sizeof(srceen_id));
  624. sprintf(strtmp,"{\"action\": \"off\", \"id\": %s}",srceen_id);
  625. screen_control(strtmp);
  626. if(DEBUG)
  627. printf( "screen set off\n" );
  628. }
  629. void *key2ScreenDelayControl()
  630. {
  631. char delay[8], srceen_id[16], strtmp[64];
  632. GetCmdValue(SPK_CONF, "intercom:screen_2_duration", delay, sizeof(delay));
  633. usleep(atoi(delay)*1000*1000);
  634. GetCmdValue(SPK_CONF, "intercom:trigger_2_id", srceen_id, sizeof(srceen_id));
  635. sprintf(strtmp,"{\"action\": \"off\", \"id\": %s}",srceen_id);
  636. screen_control(strtmp);
  637. if(DEBUG)
  638. printf( "screen set off\n" );
  639. }
  640. //呼入触发
  641. void incomingTrigger()
  642. {
  643. char relay_call_state[8],relay_state_info[16],relay_mode[16];
  644. GetCmdValue(SPK_CONF, "relay_ctrl:call_state", relay_call_state, sizeof(relay_call_state));
  645. GetCmdValue(SPK_CONF, "relay_ctrl:state_info", relay_state_info, sizeof(relay_state_info));
  646. if( strcmp(relay_call_state, "yes") == 0 && ( strcmp(relay_state_info, "incoming") == 0 || strcmp(relay_state_info, "both") == 0 ) )
  647. {
  648. relayControl(GPIO_RELAY, GPIO_ON);
  649. if(DEBUG)
  650. printf( "GPIO_RELAY set on\n" );
  651. //gpio触发后判断是否为延时复位
  652. GetCmdValue(SPK_CONF, "relay_ctrl:mode", relay_mode, sizeof(relay_mode));
  653. if( strcmp(relay_mode, "delay") == 0 )
  654. {
  655. int ret_thrd_delay;
  656. pthread_t thread_delay;
  657. ret_thrd_delay = pthread_create(&thread_delay, NULL, relayDelayControl, NULL);
  658. if (ret_thrd_delay != 0) {
  659. printf("create thread_delay relayDelayControl failed\n");
  660. return;
  661. }
  662. pthread_detach(thread_delay);
  663. }
  664. }
  665. }
  666. //呼出触发
  667. void outgoingTrigger()
  668. {
  669. char relay_call_state[8],relay_state_info[16],relay_mode[16];
  670. char screen_call_state[8], screen_state_info[16], screen_mode[16];
  671. GetCmdValue(SPK_CONF, "relay_ctrl:call_state", relay_call_state, sizeof(relay_call_state));
  672. GetCmdValue(SPK_CONF, "relay_ctrl:state_info", relay_state_info, sizeof(relay_state_info));
  673. if( strcmp(relay_call_state, "yes") == 0 && ( strcmp(relay_state_info, "outgoing") == 0 || strcmp(relay_state_info, "both") == 0 ) )
  674. {
  675. relayControl(GPIO_RELAY, GPIO_ON);
  676. if(DEBUG)
  677. printf( "GPIO_RELAY set on\n" );
  678. //gpio触发后判断是否为延时复位
  679. GetCmdValue(SPK_CONF, "relay_ctrl:mode", relay_mode, sizeof(relay_mode));
  680. if( strcmp(relay_mode, "delay") == 0 )
  681. {
  682. int ret_thrd_delay;
  683. pthread_t thread_delay;
  684. ret_thrd_delay = pthread_create(&thread_delay, NULL, relayDelayControl, NULL);
  685. if (ret_thrd_delay != 0) {
  686. printf("create thread_delay relayDelayControl failed\n");
  687. return;
  688. }
  689. pthread_detach(thread_delay);
  690. }
  691. }
  692. }
  693. //应答触发
  694. void answeredTrigger()
  695. {
  696. char cmd[MAX_PIPE_BUFSIZE];
  697. char local_beep[4], local_beep_file[64], local_beep_volume[4];
  698. char remote_beep[4], remote_beep_file[64], remote_beep_volume[4];
  699. char relay_call_state[8],relay_state_info[16],relay_mode[16];
  700. char screen_call_state[8], screen_state_info[16], screen_mode[16];
  701. setAnswerCallInfo();
  702. //切换麦克风通道为通话通道
  703. ai_ctrl(FALSE);
  704. //判断RELAY是否需要应答复位
  705. GetCmdValue(SPK_CONF, "relay_ctrl:mode", relay_mode, sizeof(relay_mode));
  706. if( strcmp(relay_mode, "answered") == 0 )
  707. {
  708. relayControl(GPIO_RELAY, GPIO_OFF);
  709. if(DEBUG)
  710. printf( "GPIO_RELAY set off\n" );
  711. }
  712. else
  713. {
  714. GetCmdValue(SPK_CONF, "relay_ctrl:call_state", relay_call_state, sizeof(relay_call_state));
  715. GetCmdValue(SPK_CONF, "relay_ctrl:state_info", relay_state_info, sizeof(relay_state_info));
  716. if( strcmp(relay_call_state, "yes") == 0 && strcmp(relay_state_info, "answered") == 0 )
  717. {
  718. relayControl(GPIO_RELAY, GPIO_ON);
  719. if(DEBUG)
  720. printf( "GPIO_RELAY set on\n" );
  721. //gpio触发后判断是否为延时复位
  722. if( strcmp(relay_mode, "delay") == 0 )
  723. {
  724. int ret_thrd_delay;
  725. pthread_t thread_delay;
  726. ret_thrd_delay = pthread_create(&thread_delay, NULL, relayDelayControl, NULL);
  727. if (ret_thrd_delay != 0) {
  728. printf("create thread_delay relayDelayControl failed\n");
  729. return;
  730. }
  731. pthread_detach(thread_delay);
  732. }
  733. }
  734. }
  735. //触发应答提示音播放
  736. GetCmdValue(SPK_CONF, "sip_function:answer_local_beep", local_beep, sizeof(local_beep));
  737. if(strcmp(local_beep, "yes") == 0)
  738. {
  739. GetCmdValue(SPK_CONF, "sip_function:answer_local_beep_file", local_beep_file, sizeof(local_beep_file));
  740. GetCmdValue(SPK_CONF, "sip_function:answer_local_beep_volume", local_beep_volume, sizeof(local_beep_volume));
  741. sprintf(cmd,"{\"cmd\":\"mixausrc_dec_start\",\"data\":\"aufile /usr/share/baresip/%s 10 %s\"}", local_beep_file, local_beep_volume);
  742. control_cmd(BARESIP_CHAN, cmd);
  743. }
  744. GetCmdValue(SPK_CONF, "sip_function:answer_remote_beep", remote_beep, sizeof(remote_beep));
  745. if(strcmp(remote_beep, "yes") == 0)
  746. {
  747. GetCmdValue(SPK_CONF, "sip_function:answer_remote_beep_file", remote_beep_file, sizeof(remote_beep_file));
  748. GetCmdValue(SPK_CONF, "sip_function:answer_remote_beep_volume", remote_beep_volume, sizeof(remote_beep_volume));
  749. sprintf(cmd,"{\"cmd\":\"mixausrc_enc_start\",\"data\":\"aufile /usr/share/baresip/%s 10 %s\"}", remote_beep_file, remote_beep_volume);
  750. control_cmd(BARESIP_CHAN, cmd);
  751. }
  752. }
  753. //挂断触发
  754. void hangupTrigger(char *param)
  755. {
  756. char cmd[MAX_PIPE_BUFSIZE];
  757. char relay_call_state[8],relay_state_info[16],relay_mode[16];
  758. char call_state[8],state_info[16],output_mode[16], beep[4], beep_file[64], beep_volume[4];
  759. char screen_call_state[8], screen_state_info[16], screen_mode[16];
  760. //触发挂断提示音播放
  761. GetCmdValue(SPK_CONF, "sip_function:hangup_beep", beep, sizeof(beep));
  762. if(strcmp(beep, "yes") == 0)
  763. {
  764. GetCmdValue(SPK_CONF, "sip_function:hangup_beep_file", beep_file, sizeof(beep_file));
  765. GetCmdValue(SPK_CONF, "sip_function:hangup_beep_volume", beep_volume, sizeof(beep_volume));
  766. sprintf(cmd,"{\"cmd\":\"setaudiotempvol\",\"data\":\"%s\"}",beep_volume);
  767. control_cmd(BARESIP_CHAN, cmd);
  768. sprintf(cmd,"{\"cmd\":\"play\",\"data\":\"%s:0\"}", beep_file);
  769. control_cmd(BARESIP_CHAN, cmd);
  770. }
  771. setClosedCallInfo(param);
  772. //判断RELAY是否需要挂断复位
  773. GetCmdValue(SPK_CONF, "relay_ctrl:mode", relay_mode, sizeof(relay_mode));
  774. if( strcmp(relay_mode, "hangup") == 0 )
  775. {
  776. relayControl(GPIO_RELAY, GPIO_OFF);
  777. if(DEBUG)
  778. printf( "GPIO_RELAY set off\n" );
  779. }
  780. else
  781. {
  782. //否则判断是否需要执行挂断触发
  783. GetCmdValue(SPK_CONF, "relay_ctrl:call_state", relay_call_state, sizeof(relay_call_state));
  784. GetCmdValue(SPK_CONF, "relay_ctrl:state_info", relay_state_info, sizeof(relay_state_info));
  785. if( strcmp(relay_call_state, "yes") == 0){
  786. if(strcmp(relay_state_info, "hangup") == 0 )
  787. {
  788. relayControl(GPIO_RELAY, GPIO_ON);
  789. if(DEBUG)
  790. printf( "GPIO_RELAY set on\n" );
  791. //gpio触发后延时复位
  792. int ret_thrd_delay;
  793. pthread_t thread_delay;
  794. ret_thrd_delay = pthread_create(&thread_delay, NULL, relayDelayControl, NULL);
  795. if (ret_thrd_delay != 0) {
  796. printf("create thread_delay relayDelayControl failed\n");
  797. return;
  798. }
  799. pthread_detach(thread_delay);
  800. }
  801. else
  802. {
  803. relayControl(GPIO_RELAY, GPIO_OFF);
  804. if(DEBUG)
  805. printf( "GPIO_RELAY set off\n" );
  806. }
  807. }
  808. }
  809. }
  810. //DTMF检测
  811. void dtmfDetect(char *dtmf)
  812. {
  813. char dtmf_event[8],dtmf_code[32],relay_mode[16];
  814. char srceen_dtmf_event[8],srceen_dtmf_code[32],srceen_mode[16];
  815. char dtmf_tmp[32] = "\0";
  816. int dtmflen,codelen,srceen_codelen, reset = FALSE;
  817. GetCmdValue(SPK_CONF, "relay_ctrl:dtmf", dtmf_event, sizeof(dtmf_event));
  818. GetCmdValue(SPK_CONF, "screen_ctrl:dtmf", srceen_dtmf_event, sizeof(srceen_dtmf_event));
  819. if( strcmp(dtmf_event, "yes") == 0 || strcmp(srceen_dtmf_event, "yes") == 0 )
  820. {
  821. strcat(DTMF_STRING,dtmf);
  822. if(DEBUG)
  823. printf( "DTMF is [%s]\n", DTMF_STRING );
  824. dtmflen = strlen(DTMF_STRING);
  825. if(strcmp(dtmf_event, "yes") == 0 )
  826. {
  827. GetCmdValue(SPK_CONF, "relay_ctrl:dtmf_code", dtmf_code, sizeof(dtmf_code));
  828. codelen = strlen(dtmf_code);
  829. if( dtmflen >= codelen )
  830. {
  831. strcpy(dtmf_tmp, DTMF_STRING + dtmflen - codelen);
  832. if( strcmp(dtmf_tmp, dtmf_code) == 0 ){
  833. relayControl(GPIO_RELAY, GPIO_ON);
  834. if(DEBUG)
  835. printf( "GPIO_RELAY set on\n" );
  836. //gpio触发后判断是否为延时复位
  837. GetCmdValue(SPK_CONF, "relay_ctrl:mode", relay_mode, sizeof(relay_mode));
  838. if( strcmp(relay_mode, "delay") == 0 )
  839. {
  840. int ret_thrd_delay;
  841. pthread_t thread_delay;
  842. ret_thrd_delay = pthread_create(&thread_delay, NULL, relayDelayControl, NULL);
  843. if (ret_thrd_delay != 0) {
  844. printf("create thread_delay relayDelayControl failed\n");
  845. return;
  846. }
  847. pthread_detach(thread_delay);
  848. }
  849. reset = TRUE;
  850. }
  851. }
  852. }
  853. if(strcmp(srceen_dtmf_event, "yes") == 0 )
  854. {
  855. GetCmdValue(SPK_CONF, "screen_ctrl:dtmf_code", srceen_dtmf_code, sizeof(srceen_dtmf_code));
  856. srceen_codelen = strlen(srceen_dtmf_code);
  857. if( dtmflen >= srceen_codelen )
  858. {
  859. strcpy(dtmf_tmp, DTMF_STRING + dtmflen - srceen_codelen);
  860. if( strcmp(dtmf_tmp, srceen_dtmf_code) == 0 ){
  861. screenControl(TRUE);
  862. if(DEBUG)
  863. printf( "screen set on\n" );
  864. //触发后判断是否为延时复位
  865. GetCmdValue(SPK_CONF, "screen_ctrl:mode", srceen_mode, sizeof(srceen_mode));
  866. if( strcmp(srceen_mode, "delay") == 0 )
  867. {
  868. int ret_thrd_delay;
  869. pthread_t thread_delay;
  870. ret_thrd_delay = pthread_create(&thread_delay, NULL, screenDelayControl, NULL);
  871. if (ret_thrd_delay != 0) {
  872. printf("create thread_delay screenDelayControl failed\n");
  873. return;
  874. }
  875. pthread_detach(thread_delay);
  876. }
  877. reset = TRUE;
  878. }
  879. }
  880. }
  881. if(reset) memset(DTMF_STRING, 0, sizeof(DTMF_STRING));
  882. }
  883. }
  884. //baresip状态监控
  885. void ProcessReply( redisReply * pReply )
  886. {
  887. cJSON *pJson;
  888. redisReply * pSubReply = NULL;
  889. char callerid[128],strtmp[256];
  890. if ( pReply != NULL && pReply->elements == 3 )
  891. {
  892. pSubReply = pReply->element[2];
  893. if(DEBUG)
  894. printf( "Msg [%s]\n", pSubReply->str );
  895. pJson = cJSON_Parse(pSubReply->str);
  896. if ( pJson ) {
  897. if(strcmp(cJSON_GetObjectItem(pJson, "direction")->valuestring, "incoming") == 0 &&
  898. strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "CALL_ESTABLISHED") == 0)
  899. {
  900. //通话
  901. writeLog( STA, "CALL ESTABLISHED", "incoming" );
  902. //amplifier_switch(TRUE);
  903. BARESIP_STATUS = INUSE;
  904. answeredTrigger();
  905. }
  906. else if(strcmp(cJSON_GetObjectItem(pJson, "direction")->valuestring, "outgoing") == 0 &&
  907. strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "CALL_ESTABLISHED") == 0)
  908. {
  909. //通话
  910. writeLog( STA, "CALL ESTABLISHED", "outgoing" );
  911. //amplifier_switch(TRUE);
  912. BARESIP_STATUS = INUSE;
  913. answeredTrigger();
  914. }
  915. else if(strcmp(cJSON_GetObjectItem(pJson, "direction")->valuestring, "incoming") == 0 &&
  916. strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "CALL_CLOSED") == 0)
  917. {
  918. //挂断
  919. hangupTrigger(cJSON_GetObjectItem(pJson, "param")->valuestring);
  920. writeLog( STA, "CALL CLOSED", cJSON_GetObjectItem(pJson, "param")->valuestring );
  921. if(BARESIP_STATUS != OFFLINE){
  922. BARESIP_STATUS = IDLE;
  923. }
  924. if(strlen(DTMF_STRING))
  925. memset(DTMF_STRING, 0, sizeof(DTMF_STRING));
  926. CURRENT_CALLS --;
  927. if(CURRENT_CALLS < 1)
  928. {
  929. //amplifier_switch(FALSE);
  930. CURRENT_CALLS = 0;
  931. ai_ctrl(TRUE);
  932. }
  933. else
  934. {
  935. control_cmd(BARESIP_CHAN, "{\"cmd\":\"resume\",\"data\":\"\"}");
  936. }
  937. }
  938. else if(strcmp(cJSON_GetObjectItem(pJson, "direction")->valuestring, "outgoing") == 0 &&
  939. strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "CALL_CLOSED") == 0)
  940. {
  941. //挂断
  942. hangupTrigger(cJSON_GetObjectItem(pJson, "param")->valuestring);
  943. writeLog( STA, "CALL CLOSED", cJSON_GetObjectItem(pJson, "param")->valuestring );
  944. if(BARESIP_STATUS != OFFLINE){
  945. BARESIP_STATUS = IDLE;
  946. }
  947. CURRENT_KEY = UNKEY;
  948. if(strlen(DTMF_STRING))
  949. memset(DTMF_STRING, 0, sizeof(DTMF_STRING));
  950. CURRENT_CALLS --;
  951. if(CURRENT_CALLS < 1)
  952. {
  953. CURRENT_CALLS = 0;
  954. ai_ctrl(TRUE);
  955. }
  956. else
  957. {
  958. control_cmd(BARESIP_CHAN, "{\"cmd\":\"resume\",\"data\":\"\"}");
  959. }
  960. }
  961. else if(strcmp(cJSON_GetObjectItem(pJson, "direction")->valuestring, "incoming") == 0 &&
  962. strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "CALL_INCOMING") == 0)
  963. {
  964. //呼入振铃状态
  965. writeLog( STA, "INCOMING CALL", cJSON_GetObjectItem(pJson, "peeruri")->valuestring );
  966. CURRENT_CALLS ++;
  967. //amplifier_switch(TRUE);
  968. if(BARESIP_STATUS == IDLE)
  969. {
  970. BARESIP_STATUS = RING;
  971. CURRENT_KEY = UNKEY;
  972. incomingTrigger();
  973. }
  974. memset(callerid, 0, sizeof(callerid));
  975. if(strchr(cJSON_GetObjectItem(pJson, "peeruri")->valuestring,'@'))
  976. strncpy(callerid, cJSON_GetObjectItem(pJson, "peeruri")->valuestring,
  977. strchr(cJSON_GetObjectItem(pJson, "peeruri")->valuestring,'@') - cJSON_GetObjectItem(pJson, "peeruri")->valuestring);
  978. else
  979. strcpy(callerid, cJSON_GetObjectItem(pJson, "peeruri")->valuestring);
  980. setIncomingCallInfo(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, callerid + 4);
  981. }
  982. else if(strcmp(cJSON_GetObjectItem(pJson, "direction")->valuestring, "outgoing") == 0 &&
  983. strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "CALL_OUTGOING") == 0)
  984. {
  985. //呼出回铃状态
  986. writeLog( STA, "OUTGOING CALL", cJSON_GetObjectItem(pJson, "peeruri")->valuestring );
  987. CURRENT_CALLS ++;
  988. //amplifier_switch(TRUE);
  989. if(BARESIP_STATUS == IDLE || BARESIP_STATUS == DIALING)
  990. {
  991. BARESIP_STATUS = RINGING;
  992. outgoingTrigger();
  993. }
  994. memset(callerid, 0, sizeof(callerid));
  995. if(strchr(cJSON_GetObjectItem(pJson, "peeruri")->valuestring,'@'))
  996. strncpy(callerid, cJSON_GetObjectItem(pJson, "peeruri")->valuestring,
  997. strchr(cJSON_GetObjectItem(pJson, "peeruri")->valuestring,'@') - cJSON_GetObjectItem(pJson, "peeruri")->valuestring);
  998. else
  999. strncpy(callerid, cJSON_GetObjectItem(pJson, "peeruri")->valuestring,
  1000. strchr(cJSON_GetObjectItem(pJson, "peeruri")->valuestring,';') - cJSON_GetObjectItem(pJson, "peeruri")->valuestring);
  1001. setOutgoingCallInfo(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, callerid + 4);
  1002. }
  1003. else if(strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "CALL_DTMF_START") == 0)
  1004. {
  1005. //接收DTMF
  1006. writeLog( FUN, "RECEIVE DTMF", cJSON_GetObjectItem(pJson, "param")->valuestring );
  1007. dtmfDetect(cJSON_GetObjectItem(pJson, "param")->valuestring);
  1008. }
  1009. else if(strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "REGISTER_OK") == 0)
  1010. {
  1011. //如果是注册成功点亮指示灯
  1012. char enac1[8],enac2[8],enac3[8],accountaor1[192], accountaor2[192], accountaor3[192];
  1013. char account1[32], domain1[128], account2[32], domain2[128], account3[32], domain3[128];
  1014. if(BARESIP_STATUS == OFFLINE || BARESIP_STATUS == DIALING || strcmp(cJSON_GetObjectItem(pJson, "class")->valuestring, "init register") == 0)
  1015. {
  1016. BARESIP_STATUS = IDLE;
  1017. CURRENT_CALLS = 0;
  1018. }
  1019. if(cJSON_GetObjectItem(pJson, "accountaor") != NULL)
  1020. {
  1021. GetCmdValue(SPK_CONF, "account_info_1:enable", enac1, sizeof(enac1));
  1022. if(strcmp(enac1, "yes") == 0 && ACCOUNT1_REG == REGISTER_FAIL)
  1023. {
  1024. GetCmdValue(SPK_CONF, "account_info_1:username", account1, sizeof(account1));
  1025. GetCmdValue(SPK_CONF, "account_info_1:domain", domain1, sizeof(domain1));
  1026. if(strlen(domain1) == 0)
  1027. {
  1028. GetCmdValue(SPK_CONF, "account_info_1:server", domain1, sizeof(domain1));
  1029. }
  1030. memset(accountaor1, '\0', sizeof(accountaor1));
  1031. sprintf(accountaor1, "sip:%s@%s", account1, domain1);
  1032. if (strcmp(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, accountaor1) == 0)
  1033. {
  1034. ACCOUNT1_REG = REGISTER_OK;
  1035. cJSON_Delete(pJson);
  1036. sprintf(strtmp,"Primary SIP Account <%s>",accountaor1);
  1037. writeLog( STA, "SIP REGISTERED", strtmp );
  1038. return;
  1039. }
  1040. }
  1041. GetCmdValue(SPK_CONF, "account_info_2:enable", enac2, sizeof(enac2));
  1042. if(strcmp(enac2, "yes") == 0 && ACCOUNT2_REG == REGISTER_FAIL)
  1043. {
  1044. GetCmdValue(SPK_CONF, "account_info_2:username", account2, sizeof(account2));
  1045. GetCmdValue(SPK_CONF, "account_info_2:domain", domain2, sizeof(domain2));
  1046. if(strlen(domain2) == 0)
  1047. {
  1048. GetCmdValue(SPK_CONF, "account_info_2:server", domain2, sizeof(domain2));
  1049. }
  1050. memset(accountaor2, '\0', sizeof(accountaor2));
  1051. sprintf(accountaor2, "sip:%s@%s", account2, domain2);
  1052. if (strcmp(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, accountaor2) == 0)
  1053. {
  1054. ACCOUNT2_REG = REGISTER_OK;
  1055. cJSON_Delete(pJson);
  1056. sprintf(strtmp,"Secondary SIP Account-1 <%s>",accountaor2);
  1057. writeLog( STA, "SIP REGISTERED", strtmp );
  1058. return;
  1059. }
  1060. }
  1061. GetCmdValue(SPK_CONF, "account_info_3:enable", enac3, sizeof(enac3));
  1062. if(strcmp(enac3, "yes") == 0 && ACCOUNT3_REG == REGISTER_FAIL)
  1063. {
  1064. GetCmdValue(SPK_CONF, "account_info_3:username", account3, sizeof(account3));
  1065. GetCmdValue(SPK_CONF, "account_info_3:domain", domain3, sizeof(domain3));
  1066. if(strlen(domain3) == 0)
  1067. {
  1068. GetCmdValue(SPK_CONF, "account_info_3:server", domain3, sizeof(domain3));
  1069. }
  1070. memset(accountaor3, '\0', sizeof(accountaor3));
  1071. sprintf(accountaor3, "sip:%s@%s", account3, domain3);
  1072. if (strcmp(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, accountaor3) == 0)
  1073. {
  1074. ACCOUNT3_REG = REGISTER_OK;
  1075. cJSON_Delete(pJson);
  1076. sprintf(strtmp,"Secondary SIP Account-2 <%s>",accountaor3);
  1077. writeLog( STA, "SIP REGISTERED", strtmp );
  1078. return;
  1079. }
  1080. }
  1081. }
  1082. regcount ++;
  1083. }
  1084. else if(strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "REGISTER_FAIL") == 0 )
  1085. {
  1086. char enac1[8],enac2[8],enac3[8],accountaor1[192], accountaor2[192], accountaor3[192];
  1087. char account1[32], domain1[128], account2[32], domain2[128], account3[32], domain3[128];
  1088. if(cJSON_GetObjectItem(pJson, "accountaor") != NULL)
  1089. {
  1090. GetCmdValue(SPK_CONF, "account_info_1:enable", enac1, sizeof(enac1));
  1091. if(strcmp(enac1, "yes") == 0 && ACCOUNT1_REG == REGISTER_OK)
  1092. {
  1093. GetCmdValue(SPK_CONF, "account_info_1:username", account1, sizeof(account1));
  1094. GetCmdValue(SPK_CONF, "account_info_1:domain", domain1, sizeof(domain1));
  1095. if(strlen(domain1) == 0)
  1096. {
  1097. GetCmdValue(SPK_CONF, "account_info_1:server", domain1, sizeof(domain1));
  1098. }
  1099. memset(accountaor1, '\0', sizeof(accountaor1));
  1100. sprintf(accountaor1, "sip:%s@%s", account1, domain1);
  1101. if (strcmp(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, accountaor1) == 0)
  1102. {
  1103. ACCOUNT1_REG = REGISTER_FAIL;
  1104. if( ACCOUNT2_REG == REGISTER_FAIL && ACCOUNT3_REG == REGISTER_FAIL && ACCOUNTP2P_REG == REGISTER_FAIL ){
  1105. BARESIP_STATUS = OFFLINE;
  1106. }
  1107. sprintf(strtmp,"Primary Account REGISTER FAILED <%s>",accountaor1);
  1108. writeLog( STA, strtmp, cJSON_GetObjectItem(pJson, "param")->valuestring );
  1109. cJSON_Delete(pJson);
  1110. return;
  1111. }
  1112. }
  1113. GetCmdValue(SPK_CONF, "account_info_2:enable", enac2, sizeof(enac2));
  1114. if(strcmp(enac2, "yes") == 0 && ACCOUNT2_REG == REGISTER_OK)
  1115. {
  1116. GetCmdValue(SPK_CONF, "account_info_2:username", account2, sizeof(account2));
  1117. GetCmdValue(SPK_CONF, "account_info_2:domain", domain2, sizeof(domain2));
  1118. if(strlen(domain2) == 0)
  1119. {
  1120. GetCmdValue(SPK_CONF, "account_info_2:server", domain2, sizeof(domain2));
  1121. }
  1122. memset(accountaor2, '\0', sizeof(accountaor2));
  1123. sprintf(accountaor2, "sip:%s@%s", account2, domain2);
  1124. if (strcmp(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, accountaor2) == 0)
  1125. {
  1126. ACCOUNT2_REG = REGISTER_FAIL;
  1127. if( ACCOUNT1_REG == REGISTER_FAIL && ACCOUNT3_REG == REGISTER_FAIL && ACCOUNTP2P_REG == REGISTER_FAIL ){
  1128. BARESIP_STATUS = OFFLINE;
  1129. }
  1130. sprintf(strtmp,"Secondary Account-1 REGISTER FAILED <%s>",accountaor2);
  1131. writeLog( STA, strtmp, cJSON_GetObjectItem(pJson, "param")->valuestring );
  1132. cJSON_Delete(pJson);
  1133. return;
  1134. }
  1135. }
  1136. GetCmdValue(SPK_CONF, "account_info_3:enable", enac3, sizeof(enac3));
  1137. if(strcmp(enac3, "yes") == 0 && ACCOUNT3_REG == REGISTER_OK)
  1138. {
  1139. GetCmdValue(SPK_CONF, "account_info_3:username", account3, sizeof(account3));
  1140. GetCmdValue(SPK_CONF, "account_info_3:domain", domain3, sizeof(domain3));
  1141. if(strlen(domain3) == 0)
  1142. {
  1143. GetCmdValue(SPK_CONF, "account_info_3:server", domain3, sizeof(domain3));
  1144. }
  1145. memset(accountaor3, '\0', sizeof(accountaor3));
  1146. sprintf(accountaor3, "sip:%s@%s", account3, domain3);
  1147. if (strcmp(cJSON_GetObjectItem(pJson, "accountaor")->valuestring, accountaor3) == 0)
  1148. {
  1149. ACCOUNT3_REG = REGISTER_FAIL;
  1150. if( ACCOUNT1_REG == REGISTER_FAIL && ACCOUNT2_REG == REGISTER_FAIL && ACCOUNTP2P_REG == REGISTER_FAIL ){
  1151. BARESIP_STATUS = OFFLINE;
  1152. }
  1153. sprintf(strtmp,"Secondary Account-2 REGISTER FAILED <%s>",accountaor3);
  1154. writeLog( STA, strtmp, cJSON_GetObjectItem(pJson, "param")->valuestring );
  1155. cJSON_Delete(pJson);
  1156. return;
  1157. }
  1158. }
  1159. }
  1160. regcount ++;
  1161. }
  1162. else if(strcmp(cJSON_GetObjectItem(pJson, "type")->valuestring, "EXIT") == 0)
  1163. {
  1164. //如果是注册失败熄灭指示灯
  1165. BARESIP_STATUS = OFFLINE;
  1166. ACCOUNT1_REG = REGISTER_FAIL;
  1167. ACCOUNT2_REG = REGISTER_FAIL;
  1168. ACCOUNT3_REG = REGISTER_FAIL;
  1169. writeLog( STA, "APP EXIT", "" );
  1170. CURRENT_CALLS = 0;
  1171. }
  1172. else if(cJSON_GetObjectItem(pJson, "event")->type == 1 && cJSON_GetObjectItem(pJson, "event")->valueint == 0){
  1173. if(strncmp(cJSON_GetObjectItem(pJson, "data")->valuestring,"\n--- User Agents",16) == 0)
  1174. {
  1175. char p2penable[8];
  1176. GetCmdValue(SPK_CONF, "account_info_p2p:enable", p2penable, sizeof(p2penable));
  1177. if(strcmp(p2penable,"yes") == 0)
  1178. {
  1179. BARESIP_STATUS = IDLE;
  1180. if(ACCOUNTP2P_REG == REGISTER_FAIL)
  1181. {
  1182. ACCOUNTP2P_REG = REGISTER_OK;
  1183. writeLog( STA, "P2P ACCOUNT", "Enabled" );
  1184. }
  1185. }
  1186. else if(ACCOUNTP2P_REG == REGISTER_OK)
  1187. {
  1188. ACCOUNTP2P_REG = REGISTER_FAIL;
  1189. writeLog( STA, "P2P ACCOUNT", "Disabled" );
  1190. }
  1191. }
  1192. }
  1193. if(DEBUG)
  1194. printf( "Baresip Status is: %d\n", BARESIP_STATUS );
  1195. }else{
  1196. printf( "parse failed!\n");
  1197. }
  1198. if(pJson != NULL) cJSON_Delete(pJson);
  1199. }
  1200. }
  1201. /*
  1202. * 订阅baresip实时状态.
  1203. */
  1204. void *baresip_status()
  1205. {
  1206. redisContext * pContext = redisConnectUnix(unix_socket_path);
  1207. if ( NULL == pContext || pContext->err == 1 )
  1208. {
  1209. printf( "%s\n", pContext->errstr );
  1210. exit( -1 );
  1211. }
  1212. char * pKey = "session-channel";
  1213. redisReply * pReply = redisCommand( pContext, "SUBSCRIBE %s", pKey );
  1214. freeReplyObject( pReply );
  1215. while ( redisGetReply( pContext, (void **)&pReply ) == REDIS_OK )
  1216. {
  1217. ProcessReply( pReply );
  1218. freeReplyObject( pReply );
  1219. }
  1220. redisFree( pContext );
  1221. }
  1222. int get_line(int * line_id)
  1223. {
  1224. char enac[8], strtmp[32];
  1225. int id = 0;
  1226. memset(line_id,-1,sizeof(line_id));
  1227. for(int i = 1; i < 4;i ++)
  1228. {
  1229. bzero(strtmp, sizeof(strtmp));
  1230. sprintf(strtmp,"account_info_%d:enable",i);
  1231. GetCmdValue(SPK_CONF, strtmp, enac, sizeof(enac));
  1232. if(strcmp(enac,"yes") == 0)
  1233. {
  1234. line_id[i] = id;
  1235. id ++;
  1236. }
  1237. }
  1238. return TRUE;
  1239. }
  1240. //按键动作
  1241. void keyAction(int key)
  1242. {
  1243. char cmd[MAX_PIPE_BUFSIZE];
  1244. char accountaor[192],strtmp[64];
  1245. char account[32], enable[8],url[256],ipaddr[16],macaddr[16];
  1246. char onekey_num[32],onekey_line[24],repress_cancel[8];
  1247. int channel = BARESIP_CHAN, line_id[4];
  1248. if(DEBUG)
  1249. printf( "BARESIP_STATUS [%d]\n", BARESIP_STATUS );
  1250. switch(key){
  1251. case KEY://处理按键动作
  1252. if( CURRENT_KEY == UNKEY || CURRENT_KEY == KEY )
  1253. {
  1254. switch(BARESIP_STATUS)
  1255. {
  1256. case IDLE:
  1257. CURRENT_KEY = KEY;
  1258. BARESIP_STATUS = DIALING;
  1259. GetCmdValue(SPK_CONF, "intercom:onekey_1_num", onekey_num, sizeof(onekey_num));
  1260. GetCmdValue(SPK_CONF, "intercom:onekey_1_line", onekey_line, sizeof(onekey_line));
  1261. if(strlen(onekey_num) == 0)
  1262. {
  1263. BARESIP_STATUS = IDLE;
  1264. break;
  1265. }
  1266. get_line(line_id);
  1267. if(strcmp(onekey_line,"auto") == 0)
  1268. {
  1269. if(DEBUG)
  1270. printf("ACCOUNT1 is %d, ACCOUNT2 is %d, ACCOUNT3 is %d\n",ACCOUNT1_REG,ACCOUNT2_REG,ACCOUNT3_REG);
  1271. if(ACCOUNT1_REG == REGISTER_OK)
  1272. {
  1273. if(line_id[1] == -1)
  1274. {
  1275. BARESIP_STATUS = IDLE;
  1276. break;
  1277. }
  1278. sprintf(cmd,"{\"cmd\":\"dial\",\"data\":\"%s %d\"}",onekey_num, line_id[1]);
  1279. }
  1280. else if(ACCOUNT2_REG == REGISTER_OK)
  1281. {
  1282. if(line_id[2] == -1)
  1283. {
  1284. BARESIP_STATUS = IDLE;
  1285. break;
  1286. }
  1287. sprintf(cmd,"{\"cmd\":\"dial\",\"data\":\"%s %d\"}",onekey_num, line_id[2]);
  1288. }
  1289. else if(ACCOUNT3_REG == REGISTER_OK)
  1290. {
  1291. if(line_id[3] == -1)
  1292. {
  1293. BARESIP_STATUS = IDLE;
  1294. break;
  1295. }
  1296. sprintf(cmd,"{\"cmd\":\"dial\",\"data\":\"%s %d\"}",onekey_num, line_id[3]);
  1297. }
  1298. else
  1299. {
  1300. BARESIP_STATUS = IDLE;
  1301. break;
  1302. }
  1303. }
  1304. else if (strcmp(onekey_line, "account_info_1") == 0)
  1305. {
  1306. if(line_id[1] == -1 || ACCOUNT1_REG != REGISTER_OK)
  1307. {
  1308. BARESIP_STATUS = IDLE;
  1309. break;
  1310. }
  1311. sprintf(cmd,"{\"cmd\":\"dial\",\"data\":\"%s %d\"}",onekey_num, line_id[1]);
  1312. }
  1313. else if (strcmp(onekey_line, "account_info_2") == 0)
  1314. {
  1315. if(line_id[2] == -1 || ACCOUNT2_REG != REGISTER_OK)
  1316. {
  1317. BARESIP_STATUS = IDLE;
  1318. break;
  1319. }
  1320. sprintf(cmd,"{\"cmd\":\"dial\",\"data\":\"%s %d\"}",onekey_num, line_id[2]);
  1321. }
  1322. else if (strcmp(onekey_line, "account_info_3") == 0)
  1323. {
  1324. if(line_id[3] == -1 || ACCOUNT3_REG != REGISTER_OK)
  1325. {
  1326. BARESIP_STATUS = IDLE;
  1327. break;
  1328. }
  1329. sprintf(cmd,"{\"cmd\":\"dial\",\"data\":\"%s %d\"}",onekey_num, line_id[3]);
  1330. }
  1331. else if(strcmp(onekey_line,"p2p") == 0)
  1332. {
  1333. sprintf(cmd,"{\"cmd\":\"dial\",\"data\":\"%s\"}",onekey_num);
  1334. }
  1335. if(DEBUG)
  1336. printf( "dial [%s]\n", cmd );
  1337. control_cmd(channel, cmd);
  1338. sprintf(strtmp, "%s <%s>", onekey_num, onekey_line);
  1339. writeLog( FUN, "KEY Call", strtmp );
  1340. break;
  1341. case RINGING:
  1342. case INUSE:
  1343. GetCmdValue(SPK_CONF, "intercom:repress_1_cancel", repress_cancel, sizeof(repress_cancel));
  1344. if(strcmp(repress_cancel, "yes") == 0){
  1345. strcpy(cmd,"{\"cmd\":\"hangup\",\"data\":\"\"}");
  1346. if(DEBUG)
  1347. printf( "hangup call\n" );
  1348. control_cmd(channel, cmd);
  1349. writeLog( FUN, "KEY Hangup", "" );
  1350. }
  1351. break;
  1352. case RING:
  1353. CURRENT_KEY = KEY;
  1354. strcpy(cmd,"{\"cmd\":\"accept\",\"data\":\"\"}");
  1355. if(DEBUG)
  1356. printf( "answer call\n" );
  1357. control_cmd(channel, cmd);
  1358. writeLog( FUN, "KEY Answer", "" );
  1359. break;
  1360. case OFFLINE:
  1361. GetCmdValue(SPK_CONF, "call_action_url:unregistered_enable", enable, sizeof(enable));
  1362. if(strcmp(enable,"yes") == 0)
  1363. {
  1364. GetCmdValue(SPK_CONF, "call_action_url:unregistered_url", url, sizeof(url));
  1365. if(strstr(url,VAR_IP))
  1366. {
  1367. if(get_ip(ipaddr))
  1368. strcpy(url, strrpl(url, VAR_IP, ipaddr));
  1369. }
  1370. if(strstr(url,VAR_MAC))
  1371. {
  1372. if(get_mac(macaddr))
  1373. strcpy(url, strrpl(url, VAR_MAC, macaddr));
  1374. }
  1375. if(strstr(url,VAR_UA))
  1376. {
  1377. GetCmdValue(SPK_CONF, "intercom:onekey_line", onekey_line, sizeof(onekey_line));
  1378. sprintf(strtmp,"%s:username",onekey_line);
  1379. GetCmdValue(SPK_CONF, strtmp, account, sizeof(account));
  1380. strcpy(url, strrpl(url, VAR_UA, account));
  1381. }
  1382. if(strstr(url,VAR_NUM))
  1383. {
  1384. GetCmdValue(SPK_CONF, "intercom:onekey_num", onekey_num, sizeof(onekey_num));
  1385. strcpy(url, strrpl(url, VAR_NUM, onekey_num));
  1386. }
  1387. action_url(url);
  1388. writeLog(FUN, "HTTP Request", url);
  1389. }
  1390. break;
  1391. }
  1392. }
  1393. break;
  1394. case KEY2_10:
  1395. system("/etc/scripts/play_rebooting.sh");
  1396. system("rm -f /oem/.userdata && /sbin/reboot");
  1397. break;
  1398. case KEY2_3:
  1399. PlayIP();
  1400. break;
  1401. }
  1402. }
  1403. void *checkReg()
  1404. {
  1405. dictionary * ini ;
  1406. ini = iniparser_load(SPK_CONF);
  1407. if (ini==NULL) {
  1408. fprintf(stderr, "cannot parse file: %s\n", SPK_CONF);
  1409. return FALSE;
  1410. }
  1411. if((strcmp(iniparser_getstring(ini, "account_info_1:enable", "no"), "yes") == 0 || strcmp(iniparser_getstring(ini, "account_info_2:enable", "no"), "yes") == 0 ||
  1412. strcmp(iniparser_getstring(ini, "account_info_3:enable", "no"), "yes") == 0) && regcount == 0)
  1413. {
  1414. system("/etc/scrtips/sipphone.sh stop");
  1415. }
  1416. regcount = 0;
  1417. iniparser_freedict(ini);
  1418. }
  1419. void reset_vlcInfo(int id)
  1420. {
  1421. vlcInfo[id].pid = 0;
  1422. vlcInfo[id].prio = 0;
  1423. memset(vlcInfo->param, 0, sizeof(vlcInfo->param));
  1424. }
  1425. int file_exists(char *filename)
  1426. {
  1427. return (access(filename, 0) == 0);
  1428. }
  1429. int vlc_cmd_action(char *action, int id)
  1430. {
  1431. char cmd[128], ctrlfile[32];
  1432. int i = 0;
  1433. sprintf(ctrlfile,"/tmp/vlc_%d.sock",id);
  1434. while(i < MAX_TRY)
  1435. {
  1436. if(file_exists(ctrlfile))
  1437. {
  1438. sprintf(cmd,"echo \"%s\" | socat - unix-connect:%s", action, ctrlfile);
  1439. if(DEBUG) printf("volume CMD: %s\n", cmd);
  1440. if(system(cmd) == 0)
  1441. return TRUE;
  1442. else
  1443. continue;
  1444. }
  1445. usleep(200*1000);
  1446. i ++;
  1447. }
  1448. return FALSE;
  1449. }
  1450. int schedule_start_check_prio(int prio)
  1451. {
  1452. char cmd[64];
  1453. for(int i = 1; i < 31; i++)
  1454. {
  1455. if(DEBUG)
  1456. printf("==============%d,%d,%d,%s=============\n", i, SCHEDULE[i], vlcInfo[i].prio, vlcInfo[i].param);
  1457. if(SCHEDULE[i] != STOP)
  1458. {
  1459. if(prio < vlcInfo[i].prio)
  1460. return FALSE;
  1461. else if(SCHEDULE[i] == RUNNING && prio > vlcInfo[i].prio)
  1462. {
  1463. if(vlc_cmd_action("pause",i))
  1464. SCHEDULE[i] = PAUSED;
  1465. }
  1466. }
  1467. }
  1468. return TRUE;
  1469. }
  1470. void schedule_stop_check_prio(int prio)
  1471. {
  1472. char cmd[64];
  1473. int paused[30],running[30],c_paused = 0, c_running = 0;
  1474. int isRunning = FALSE;
  1475. for(int i = 1; i < 31; i++)
  1476. {
  1477. if(SCHEDULE[i] == RUNNING)
  1478. {
  1479. return;
  1480. }
  1481. if(SCHEDULE[i] == PAUSED)
  1482. {
  1483. paused[c_paused] = i;
  1484. c_paused ++;
  1485. }
  1486. }
  1487. for(int p = prio; p > 0; p--)
  1488. {
  1489. for(int n = 0; n < c_paused; n++)
  1490. {
  1491. if(p == vlcInfo[paused[n]].prio)
  1492. {
  1493. state_event(AUDIO_ON);
  1494. if(vlc_cmd_action("pause",paused[n]))
  1495. {
  1496. SCHEDULE[paused[n]] = RUNNING;
  1497. isRunning = TRUE;
  1498. }
  1499. }
  1500. }
  1501. if(isRunning) return;
  1502. }
  1503. state_event(AUDIO_OFF);
  1504. }
  1505. void playAudio(int id, int times, int isBeep, char *enSrceen, char *file, int prio, int vol)
  1506. {
  1507. char filetmp[64], action[128], sockio[32], paused[32],loop[16],cmd[64], gain[32];
  1508. int status, isPaused;
  1509. bzero(paused,sizeof(paused));
  1510. if(!schedule_start_check_prio(prio))
  1511. {
  1512. strcpy(paused,"--start-paused");
  1513. isPaused = TRUE;
  1514. }
  1515. else
  1516. {
  1517. strcpy(paused,"--no-start-paused");
  1518. isPaused = FALSE;
  1519. state_event(AUDIO_ON);
  1520. }
  1521. if(times == 0)
  1522. {
  1523. sprintf(filetmp, "/usr/share/baresip/%s", file);
  1524. strcpy(loop,"--loop");
  1525. }
  1526. else
  1527. {
  1528. sprintf(filetmp,"/tmp/playlist_%d.m3u",id);
  1529. FILE *fd = fopen(filetmp, "w+");
  1530. if(fd == NULL)
  1531. {
  1532. if(DEBUG) printf("play failed!\n");
  1533. return;
  1534. }
  1535. if(isBeep) fprintf(fd,"/usr/share/baresip/s_beep.mp3\n");
  1536. for(int i=0;i<times;i++)
  1537. {
  1538. fprintf(fd,"/usr/share/baresip/%s\n",file);
  1539. }
  1540. if(isBeep) fprintf(fd,"/usr/share/baresip/e_beep.mp3\n");
  1541. fclose(fd);
  1542. strcpy(loop,"--no-loop");
  1543. }
  1544. sprintf(gain, "--gain=%.02f", (float) vol/100);
  1545. sprintf(sockio,"--rc-unix=/tmp/vlc_%d.sock", id);
  1546. char *argv[] = {"vlc","--play-and-exit","--control","rc","--rc-fake-tty",sockio,paused,loop,gain,filetmp,NULL};
  1547. status = posix_spawn(&vlcInfo[id].pid,"/usr/sbin/vlc",NULL,NULL,argv,NULL);
  1548. if(status == 0)
  1549. {
  1550. usleep(300*1000);
  1551. // sprintf(action,"volume %d", 256 * vol/100);
  1552. // vlc_cmd_action(action,id);
  1553. SCHEDULE[id] = (isPaused)?PAUSED:RUNNING;
  1554. vlcInfo[id].prio = prio;
  1555. sprintf(vlcInfo[id].param,"%s", file);
  1556. sprintf(action,"Play audio: %s", vlcInfo[id].param);
  1557. writeLog(FUN, "Audio Control", action);
  1558. //system("echo 0 > /sys/class/gpio/gpio5/value");
  1559. if(waitpid(vlcInfo[id].pid, &status, 0) != -1)
  1560. {
  1561. if(DEBUG) printf("Child exited with status %i\n", status);
  1562. SCHEDULE[id] = STOP;
  1563. schedule_stop_check_prio(vlcInfo[id].prio);
  1564. reset_vlcInfo(id);
  1565. if(strcmp(enSrceen, "Disabled") != 0)
  1566. {
  1567. sprintf(cmd,"{\"action\": \"off\", \"id\": %s}", enSrceen);
  1568. screen_control(cmd);
  1569. }
  1570. //system("echo 1 > /sys/class/gpio/gpio5/value");
  1571. sprintf(action,"Stop audio: %s", vlcInfo[id].param);
  1572. writeLog(FUN, "Audio Control", action);
  1573. }
  1574. }
  1575. if(times) remove(filetmp);
  1576. }
  1577. void *handle_playAudio(void *arg)
  1578. {
  1579. int selfkey, isBeep = FALSE, times = 0;
  1580. PlayInfo *p = arg;
  1581. selfkey = p->key_id;
  1582. if(strlen(p->times_str)) times = atoi(p->times_str);
  1583. if(strcmp(p->enBeep, "yes") == 0) isBeep = TRUE;
  1584. if(strlen(p->file))
  1585. {
  1586. playAudio(selfkey, times, isBeep, p->enSrceen, p->file, p->prio, p->vol);
  1587. }
  1588. free(p);
  1589. }
  1590. int equalDate(struct date A,struct date B)
  1591. {
  1592. if(A.year==B.year && A.month==B.month && A.day==B.day)
  1593. return TRUE;
  1594. return FALSE;
  1595. }
  1596. int compareDate(struct date A,struct date B)
  1597. {
  1598. if(A.year<B.year)
  1599. return TRUE;
  1600. if(A.year==B.year && A.month<B.month)
  1601. return TRUE;
  1602. if(A.year==B.year && A.month==B.month && A.day<B.day)
  1603. return TRUE;
  1604. return FALSE;
  1605. }
  1606. void date_format(char *date_str, struct date *s_holiday, struct date *e_holiday)
  1607. {
  1608. struct date date;
  1609. sscanf(date_str, "%d-%d-%d:%d-%d-%d", &s_holiday->year, &s_holiday->month, &s_holiday->day, &e_holiday->year, &e_holiday->month, &e_holiday->day);
  1610. }
  1611. int isHoliday(struct date currDate, char *holidays)
  1612. {
  1613. cJSON *pJson, *pSub;
  1614. struct date s_holiday, e_holiday;
  1615. pJson = cJSON_Parse(holidays);
  1616. if (pJson)
  1617. {
  1618. cJSON *holidaysArray = cJSON_GetObjectItem( pJson, "holidays");
  1619. if(holidaysArray != NULL)
  1620. {
  1621. int array_size = cJSON_GetArraySize (holidaysArray);
  1622. for(int n = 0; n < array_size; n++)
  1623. {
  1624. pSub = cJSON_GetArrayItem(holidaysArray, n);
  1625. date_format(pSub->valuestring, &s_holiday, &e_holiday);
  1626. if(DEBUG)
  1627. {
  1628. printf("current date: %d-%d-%d\n",currDate.year, currDate.month, currDate.day);
  1629. printf("holiday start: %d-%d-%d\n",s_holiday.year, s_holiday.month, s_holiday.day);
  1630. printf("holiday end: %d-%d-%d\n",e_holiday.year, e_holiday.month, e_holiday.day);
  1631. }
  1632. if(equalDate(currDate, s_holiday) || (compareDate(s_holiday, currDate) && compareDate(currDate, e_holiday)))
  1633. {
  1634. cJSON_Delete(pJson);
  1635. return TRUE;
  1636. }
  1637. }
  1638. }
  1639. }
  1640. cJSON_Delete(pJson);
  1641. return FALSE;
  1642. }
  1643. void schedule(int year, int month, int day, int hour, int minute, int week)
  1644. {
  1645. char actiontype[32], keyaction[16], keyactiontype[32], type[16], action_type[16];
  1646. char keystr[32],enable[8],weeks[8], enholiday[8], holidays[4096];
  1647. char w[4],action[128],screen_id[16];
  1648. int s_hour, e_hour, s_min, e_min;
  1649. int s_time, e_time, time, interval;
  1650. struct date s_date, e_date, date;
  1651. dictionary * ini ;
  1652. date.year = year;
  1653. date.month = month;
  1654. date.day = day;
  1655. ini = iniparser_load(SCHEDULE_CONF);
  1656. if (ini==NULL) {
  1657. fprintf(stderr, "cannot parse file: %s\n", SCHEDULE_CONF);
  1658. return;
  1659. }
  1660. strcpy(holidays, iniparser_getstring(ini, "holidays:data", "{\"holidays\": []}"));
  1661. for(int i=1;i<31;i++)
  1662. {
  1663. sprintf(keystr,"schedule_%d:enable",i);
  1664. strcpy(enable, iniparser_getstring(ini, keystr, "no"));
  1665. if(strcmp(enable,"yes") == 0)
  1666. {
  1667. sprintf(keystr,"schedule_%d:enholiday",i);
  1668. strcpy(enholiday, iniparser_getstring(ini, keystr, "no"));
  1669. if(strcmp(enholiday, "yes") == 0 && isHoliday(date, holidays)) continue;
  1670. sprintf(keystr,"schedule_%d:weeks",i);
  1671. strcpy(weeks, iniparser_getstring(ini, keystr, ""));
  1672. sprintf(w,"%d",week);
  1673. if(strchr(weeks,w[0]) == NULL) continue;
  1674. sprintf(keystr,"schedule_%d:s_year",i);
  1675. s_date.year = iniparser_getint(ini, keystr, 0);
  1676. sprintf(keystr,"schedule_%d:e_year",i);
  1677. e_date.year = iniparser_getint(ini, keystr, 0);
  1678. sprintf(keystr,"schedule_%d:s_month",i);
  1679. s_date.month = iniparser_getint(ini, keystr, 0);
  1680. sprintf(keystr,"schedule_%d:e_month",i);
  1681. e_date.month = iniparser_getint(ini, keystr, 0);
  1682. sprintf(keystr,"schedule_%d:s_day",i);
  1683. s_date.day = iniparser_getint(ini, keystr, 0);
  1684. sprintf(keystr,"schedule_%d:e_day",i);
  1685. e_date.day = iniparser_getint(ini, keystr, 0);
  1686. if(compareDate(date, s_date) || compareDate(e_date, date)) continue;
  1687. sprintf(keystr,"schedule_%d:s_hour",i);
  1688. s_hour = iniparser_getint(ini, keystr, 0);
  1689. sprintf(keystr,"schedule_%d:e_hour",i);
  1690. e_hour = iniparser_getint(ini, keystr, 0);
  1691. sprintf(keystr,"schedule_%d:s_min",i);
  1692. s_min = iniparser_getint(ini, keystr, 0);
  1693. sprintf(keystr,"schedule_%d:e_min",i);
  1694. e_min = iniparser_getint(ini, keystr, 0);
  1695. sprintf(keystr,"schedule_%d:interval",i);
  1696. interval = iniparser_getint(ini, keystr, 60);
  1697. sprintf(keystr,"schedule_%d:trigger_screen",i);
  1698. strcpy(screen_id, iniparser_getstring(ini, keystr, "Disabled"));
  1699. time = hour * 60 + minute;
  1700. s_time = s_hour * 60 + s_min;
  1701. e_time = e_hour * 60 + e_min;
  1702. if(time >= s_time && time <= e_time)
  1703. {
  1704. if(time == e_time)
  1705. {
  1706. sprintf(keystr,"%d",i);
  1707. writeLog(SCHED, keystr, "Executed");
  1708. if(SCHEDULE[i] == RUNNING)
  1709. {
  1710. char strtmp[64],cmd[128];
  1711. if(strcmp(screen_id, "Disabled") != 0)
  1712. {
  1713. sprintf(strtmp,"{\"action\": \"off\", \"id\": %s}", screen_id);
  1714. screen_control(strtmp);
  1715. }
  1716. sprintf(cmd,"kill -9 %d",vlcInfo[i].pid);
  1717. system(cmd);
  1718. // system("echo 1 > /sys/class/gpio/gpio5/value");
  1719. // SCHEDULE[i] = STOP;
  1720. // sprintf(action,"Stop audio: %s", vlcInfo[i].param);
  1721. // writeLog(FUN, "Audio Control", action);
  1722. }
  1723. continue;
  1724. }
  1725. if((interval != 0 && (time - s_time) % interval == 0) || (interval == 0 && time == s_time))
  1726. {
  1727. sprintf(keystr,"%d",i);
  1728. writeLog(SCHED, keystr, "Executed");
  1729. char cmd[256], strtmp[64], source[16];
  1730. pthread_t thread_audio;
  1731. int ret_thrd;
  1732. if(SCHEDULE[i] == STOP)
  1733. {
  1734. PlayInfo *playAudioInfo = malloc(sizeof(PlayInfo));
  1735. playAudioInfo->key_id = i;
  1736. bzero(strtmp, sizeof(strtmp));
  1737. sprintf(strtmp,"schedule_%d:source",i);
  1738. strcpy(source, iniparser_getstring(ini, strtmp, ""));
  1739. bzero(strtmp, sizeof(strtmp));
  1740. sprintf(strtmp, "schedule_%d:audio_file", i);
  1741. strcpy(playAudioInfo->file, iniparser_getstring(ini, strtmp, ""));
  1742. bzero(strtmp, sizeof(strtmp));
  1743. sprintf(strtmp,"schedule_%d:play_times",i);
  1744. strcpy(playAudioInfo->times_str, iniparser_getstring(ini, strtmp, ""));
  1745. bzero(strtmp, sizeof(strtmp));
  1746. sprintf(strtmp,"schedule_%d:enBeep",i);
  1747. strcpy(playAudioInfo->enBeep, iniparser_getstring(ini, strtmp, "no"));
  1748. strcpy(playAudioInfo->enSrceen, screen_id);
  1749. bzero(strtmp, sizeof(strtmp));
  1750. sprintf(strtmp,"schedule_%d:priority",i);
  1751. playAudioInfo->prio = iniparser_getint(ini, strtmp, 1);
  1752. bzero(strtmp, sizeof(strtmp));
  1753. sprintf(strtmp,"schedule_%d:volume",i);
  1754. playAudioInfo->vol = iniparser_getint(ini, strtmp, 100);
  1755. if(strcmp(screen_id, "Disabled") != 0)
  1756. {
  1757. sprintf(strtmp,"{\"action\": \"on\", \"id\": %s}", screen_id);
  1758. screen_control(strtmp);
  1759. }
  1760. ret_thrd = pthread_create(&thread_audio, NULL, handle_playAudio, playAudioInfo);
  1761. if (ret_thrd != 0)
  1762. {
  1763. printf("create thread1 handle_playAudio failed\n");
  1764. free(playAudioInfo);
  1765. continue;
  1766. }
  1767. pthread_detach(thread_audio);
  1768. }
  1769. else
  1770. {
  1771. if(strcmp(screen_id, "Disabled") != 0)
  1772. {
  1773. sprintf(strtmp,"{\"action\": \"off\", \"id\": %s}", screen_id);
  1774. screen_control(strtmp);
  1775. }
  1776. sprintf(cmd,"kill -9 %d",vlcInfo[i].pid);
  1777. system(cmd);
  1778. // system("echo 1 > /sys/class/gpio/gpio5/value");
  1779. // SCHEDULE[i] = STOP;
  1780. // sprintf(action,"Stop audio: %s", vlcInfo[i].param);
  1781. // writeLog(FUN, "Audio Control", action);
  1782. }
  1783. }
  1784. }
  1785. }
  1786. }
  1787. iniparser_freedict(ini);
  1788. }
  1789. void *handleDateTime()
  1790. {
  1791. time_t nSeconds;
  1792. struct tm *pTM;
  1793. int year, month, hour, count;
  1794. pthread_t thread1;
  1795. while(1)
  1796. {
  1797. time(&nSeconds);
  1798. pTM = localtime(&nSeconds);
  1799. if(pTM->tm_sec == 0)
  1800. {
  1801. // year = pTM->tm_year + 1900;
  1802. // month = pTM->tm_mon + 1;
  1803. // schedule(year, month, pTM->tm_mday, pTM->tm_hour, pTM->tm_min, pTM->tm_wday);
  1804. count ++;
  1805. if(count > 120)
  1806. {
  1807. pthread_create(&thread1, NULL, checkReg, NULL);
  1808. pthread_detach(thread1);
  1809. count = 0;
  1810. }
  1811. }
  1812. sleep(1);
  1813. }
  1814. }
  1815. //解析音量设置数据
  1816. void ProcessVolumeReply( redisReply * pReply )
  1817. {
  1818. cJSON *pJson = NULL;
  1819. redisReply * pSubReply = NULL;
  1820. char cmd[MAX_PIPE_BUFSIZE];
  1821. int channel = BARESIP_CHAN;
  1822. if ( pReply != NULL && pReply->elements == 3 )
  1823. {
  1824. pSubReply = pReply->element[2];
  1825. pJson = cJSON_Parse(pSubReply->str);
  1826. if ( pJson ) {
  1827. if(cJSON_GetObjectItem(pJson, "audio_volume"))
  1828. {
  1829. if(cJSON_GetObjectItem(pJson, "audio_volume")->valueint == 0)
  1830. schedule_start_check_prio(MAX_PRIORITY + 1);
  1831. else
  1832. schedule_stop_check_prio(MAX_PRIORITY + 1);
  1833. }
  1834. }else{
  1835. printf( "parse failed!\n");
  1836. }
  1837. if(pJson != NULL) cJSON_Delete(pJson);
  1838. }
  1839. }
  1840. /*
  1841. * 订阅音量信息.
  1842. */
  1843. void *get_volume_info()
  1844. {
  1845. redisContext * pContext = redisConnectUnix(unix_socket_path);
  1846. if ( NULL == pContext || pContext->err == 1 )
  1847. {
  1848. printf( "%s\n", pContext->errstr );
  1849. exit( -1 );
  1850. }
  1851. char * pKey = "volume-value-channel";
  1852. redisReply * pReply = redisCommand( pContext, "SUBSCRIBE %s", pKey );
  1853. freeReplyObject( pReply );
  1854. while ( redisGetReply( pContext, (void **)&pReply ) == REDIS_OK )
  1855. {
  1856. ProcessVolumeReply( pReply );
  1857. freeReplyObject( pReply );
  1858. }
  1859. redisFree( pContext );
  1860. }
  1861. void play_audio(char *audiofile, int repeat)
  1862. {
  1863. char cmd[320];
  1864. int channel = BARESIP_CHAN;
  1865. sprintf(cmd,"{\"cmd\":\"play\",\"data\":\"%s:%d\"}",audiofile,repeat);
  1866. control_cmd(channel, cmd);
  1867. }
  1868. const int get_sip_status(char *accountaor)
  1869. {
  1870. int status = OFFLINE;
  1871. const int id = redis_pool_get_context(redisClient);
  1872. if (id != -1) {
  1873. redisReply *reply = NULL;
  1874. reply = (redisReply *) redisCommand(redisClient->context[id], "GET %s", accountaor);
  1875. if (reply && reply->type == REDIS_REPLY_STRING) {
  1876. // 处理回复
  1877. if(DEBUG) printf("SIP acc: %s, status: %s\n", accountaor, reply->str);
  1878. if(strcmp(reply->str, "{\"status\":\"idle\"}") == 0)
  1879. {
  1880. status = IDLE;
  1881. }
  1882. else if(strcmp(reply->str, "{\"status\":\"answer\"}") == 0)
  1883. {
  1884. status = INUSE;
  1885. }
  1886. else if(strcmp(reply->str, "{\"status\":\"ringing\"}") == 0)
  1887. {
  1888. status = RINGING;
  1889. }
  1890. else if(strcmp(reply->str, "{\"status\":\"ring\"}") == 0)
  1891. {
  1892. status = RING;
  1893. }
  1894. }
  1895. if(reply != NULL) freeReplyObject(reply);
  1896. redis_pool_release_connection(redisClient, id);
  1897. }
  1898. if(BARESIP_STATUS == OFFLINE || BARESIP_STATUS == IDLE)
  1899. BARESIP_STATUS = status;
  1900. return status;
  1901. }
  1902. void sip_reg_status_init()
  1903. {
  1904. //初始化SIP注册状态
  1905. char enac1[8],enac2[8],enac3[8],p2penable[8],accountaor1[192], accountaor2[192], accountaor3[192];
  1906. char account1[32], domain1[128], account2[32], domain2[128], account3[32], domain3[128];
  1907. GetCmdValue(SPK_CONF, "account_info_1:enable", enac1, sizeof(enac1));
  1908. if(strcmp(enac1, "yes") == 0)
  1909. {
  1910. GetCmdValue(SPK_CONF, "account_info_1:username", account1, sizeof(account1));
  1911. GetCmdValue(SPK_CONF, "account_info_1:domain", domain1, sizeof(domain1));
  1912. if(strlen(domain1) == 0)
  1913. {
  1914. GetCmdValue(SPK_CONF, "account_info_1:server", domain1, sizeof(domain1));
  1915. }
  1916. memset(accountaor1, '\0', sizeof(accountaor1));
  1917. sprintf(accountaor1, "baresip-call-status-%s-%s", account1, domain1);
  1918. if(get_sip_status(accountaor1) != OFFLINE)
  1919. {
  1920. ACCOUNT1_REG = REGISTER_OK;
  1921. }
  1922. }
  1923. GetCmdValue(SPK_CONF, "account_info_2:enable", enac2, sizeof(enac2));
  1924. if(strcmp(enac2, "yes") == 0)
  1925. {
  1926. GetCmdValue(SPK_CONF, "account_info_2:username", account2, sizeof(account2));
  1927. GetCmdValue(SPK_CONF, "account_info_2:domain", domain2, sizeof(domain2));
  1928. if(strlen(domain2) == 0)
  1929. {
  1930. GetCmdValue(SPK_CONF, "account_info_2:server", domain2, sizeof(domain2));
  1931. }
  1932. memset(accountaor2, '\0', sizeof(accountaor2));
  1933. sprintf(accountaor2, "baresip-call-status-%s-%s", account2, domain2);
  1934. if(get_sip_status(accountaor2) != OFFLINE)
  1935. {
  1936. ACCOUNT2_REG = REGISTER_OK;
  1937. }
  1938. }
  1939. GetCmdValue(SPK_CONF, "account_info_3:enable", enac3, sizeof(enac3));
  1940. if(strcmp(enac3, "yes") == 0)
  1941. {
  1942. GetCmdValue(SPK_CONF, "account_info_3:username", account3, sizeof(account3));
  1943. GetCmdValue(SPK_CONF, "account_info_3:domain", domain3, sizeof(domain3));
  1944. if(strlen(domain3) == 0)
  1945. {
  1946. GetCmdValue(SPK_CONF, "account_info_3:server", domain3, sizeof(domain3));
  1947. }
  1948. memset(accountaor3, '\0', sizeof(accountaor3));
  1949. sprintf(accountaor3, "baresip-call-status-%s-%s", account3, domain3);
  1950. if(get_sip_status(accountaor3) != OFFLINE)
  1951. {
  1952. ACCOUNT3_REG = REGISTER_OK;
  1953. }
  1954. }
  1955. GetCmdValue(SPK_CONF, "account_info_p2p:enable", p2penable, sizeof(p2penable));
  1956. if(strcmp(p2penable,"yes") == 0)
  1957. {
  1958. ACCOUNTP2P_REG = REGISTER_OK;
  1959. }
  1960. if(ACCOUNT1_REG == REGISTER_OK || ACCOUNT2_REG == REGISTER_OK || ACCOUNT3_REG == REGISTER_OK || ACCOUNTP2P_REG == REGISTER_OK)
  1961. {
  1962. key1LedStatus = Led_On;
  1963. key2LedStatus = Led_On;
  1964. }
  1965. }
  1966. const int init()
  1967. {
  1968. int ret_thrd1,ret_thrd2,ret_thrd3,ret_thrd4;
  1969. pthread_t thread1, thread2, thread3, thread4;
  1970. redisClient = create_redis_pool_client(unix_socket_path);
  1971. memset(SCHEDULE, 0,sizeof(SCHEDULE));
  1972. sip_reg_status_init();
  1973. //启动线程订阅BARESIP实时状态
  1974. ret_thrd1 = pthread_create(&thread1, NULL, baresip_status, NULL);
  1975. if (ret_thrd1 != 0) {
  1976. printf("create thread1 baresip_status failed\n");
  1977. return FALSE;
  1978. }
  1979. //启动日志记录线程
  1980. ret_thrd2 = pthread_create(&thread2, NULL, write_opnlog, NULL);
  1981. if (ret_thrd2 != 0) {
  1982. printf("create thread2 write_opnlog failed\n");
  1983. return FALSE;
  1984. }
  1985. //启动系统时间显示线程
  1986. ret_thrd3 = pthread_create(&thread3, NULL, handleDateTime, NULL);
  1987. if (ret_thrd3 != 0)
  1988. {
  1989. printf("create thread3 handleDateTime failed\n");
  1990. return FALSE;
  1991. }
  1992. //启动线程订阅音量设置
  1993. ret_thrd4 = pthread_create(&thread4, NULL, get_volume_info, NULL);
  1994. if (ret_thrd4 != 0) {
  1995. printf("create thread4 get_volume_info failed\n");
  1996. return FALSE;
  1997. }
  1998. return TRUE;
  1999. }
  2000. int main(int argc, char *argv[]){
  2001. struct pollfd fdset[2];
  2002. int switch_fd,reset_fd,ret;
  2003. int len, count, i, key1_action, key2_action;
  2004. char buf[8], strtmp[64],action[8],url[256], srceen[8], type[16], input[8];
  2005. time_t lastime, newtime;
  2006. if(argc == 2 && strcmp(argv[1], "debug") == 0)
  2007. DEBUG = TRUE;
  2008. if(!init())
  2009. {
  2010. printf("init failed!\n");
  2011. exit( -1 );
  2012. }
  2013. /* BUTTON */
  2014. switch_fd = open("/sys/class/gpio/gpio111/value", O_RDONLY);
  2015. read(switch_fd, buf, sizeof(buf));
  2016. lseek(switch_fd, 0, SEEK_SET);
  2017. /* RESET */
  2018. reset_fd = open("/sys/class/gpio/gpio73/value", O_RDONLY);
  2019. read(reset_fd, buf, sizeof(buf));
  2020. lseek(reset_fd, 0, SEEK_SET);
  2021. while(1)
  2022. {
  2023. memset(fdset, 0x00, sizeof(struct pollfd) * 2);
  2024. fdset[0].fd = switch_fd;
  2025. fdset[0].events = POLLPRI;
  2026. fdset[1].fd = reset_fd;
  2027. fdset[1].events = POLLPRI;
  2028. ret = poll(fdset, 2, 3000);
  2029. if(ret < 0){
  2030. printf("npoll() faild! \n");
  2031. return -1;
  2032. }
  2033. if(ret == 0)
  2034. continue;
  2035. /*BUTTON*/
  2036. if( fdset[0].revents & POLLPRI )
  2037. {
  2038. count = 0;
  2039. for(i=0;i<100;i++){ // 100ms
  2040. bzero(buf,sizeof(buf));
  2041. read(fdset[0].fd, buf, sizeof(buf));
  2042. lseek(fdset[0].fd, 0, SEEK_SET);
  2043. if(buf[0]-'0' == 0)
  2044. count++;
  2045. usleep(1000);
  2046. }
  2047. // printf("zero counts: %d\n", count);
  2048. if (count >= 70) {
  2049. playBeep();
  2050. if(DEBUG)
  2051. printf("KEY DOWN\n");
  2052. writeLog(BTN, "KEY", "DOWN");
  2053. GetCmdValue(SPK_CONF, "intercom:key_1_action", action, sizeof(action));
  2054. if(strcmp(action,"call") == 0)
  2055. {
  2056. keyAction(KEY);
  2057. }
  2058. if(strcmp(action,"http") == 0)
  2059. {
  2060. GetCmdValue(SPK_CONF, "intercom:http_1_url", url, sizeof(url));
  2061. action_url(url);
  2062. writeLog(FUN, "KEY1 HTTP Request", url);
  2063. }
  2064. else if(strcmp(action,"play") == 0)
  2065. {
  2066. char audiofile[32],repeat_tmp[16];
  2067. GetCmdValue(SPK_CONF, "intercom:audio_1_file", audiofile, sizeof(audiofile));
  2068. GetCmdValue(SPK_CONF, "intercom:audio_1_repeat", repeat_tmp, sizeof(repeat_tmp));
  2069. int repeat = atoi(repeat_tmp);
  2070. play_audio(audiofile,repeat);
  2071. sprintf(strtmp, "File: %s; Repeat: %d", audiofile, repeat);
  2072. writeLog( FUN, "KEY1 Play Auido", strtmp );
  2073. }
  2074. }
  2075. }
  2076. /*RESET*/
  2077. if( fdset[1].revents & POLLPRI )
  2078. {
  2079. count = 0;
  2080. for(i=0;i<100;i++){ // 100ms
  2081. bzero(buf,sizeof(buf));
  2082. read(fdset[1].fd, buf, sizeof(buf));
  2083. lseek(fdset[1].fd, 0, SEEK_SET);
  2084. if(buf[0]-'0' == 0)
  2085. count++;
  2086. usleep(1000);
  2087. }
  2088. if (count >= 70) {
  2089. time(&newtime);
  2090. printf("KEY DOWN\n");
  2091. writeLog(BTN, "RESET", "DOWN");
  2092. } else {
  2093. time(&lastime);
  2094. len = lastime - newtime;
  2095. printf("KEY UP, Time:%d\n", len);
  2096. sprintf(strtmp, "Release <Duration %ds>", len);
  2097. writeLog(BTN, "RESET", strtmp);
  2098. if(len > 10)
  2099. {
  2100. keyAction(KEY2_10);
  2101. }
  2102. else if(len > 3)
  2103. {
  2104. keyAction(KEY2_3);
  2105. }
  2106. }
  2107. }
  2108. }
  2109. }