generate_trunk_conf.c 31 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943
  1. /*
  2. ============================================================================
  3. Name : generate_trunk_conf.sh
  4. Author : ssc
  5. Version : v1.0
  6. Copyright : ZYCOO copyright
  7. Description : Generate trunk info from mysql to turnk conf file
  8. ============================================================================
  9. */
  10. #include <stdio.h>
  11. #include <stdlib.h>
  12. #include <string.h>
  13. #include <errno.h>
  14. #include <assert.h>
  15. #include <time.h>
  16. #include <ctype.h>
  17. #include <mysql/mysql.h>
  18. MYSQL *g_conn; // mysql 连接
  19. MYSQL_RES *g_res; // mysql 记录集
  20. MYSQL_ROW g_row; // 字符串数组,mysql 记录行
  21. #define MAX_TRUNK_SIZE 256
  22. #define MIDLE_SIZE 512
  23. #define MINI_SIZE 64
  24. #define TINY_SIZE 4
  25. #define PJSIP_TRUNK_REGS "/etc/asterisk/pjsip_trunk_regs.conf"
  26. #define PJSIP_TRUNK_AUTHS "/etc/asterisk/pjsip_trunk_auths.conf"
  27. #define PJSIP_TRUNK_EPS "/etc/asterisk/pjsip_trunk_eps.conf"
  28. #define PJSIP_TRUNK_AORS "/etc/asterisk/pjsip_trunk_aors.conf"
  29. #define PJSIP_TRUNK_IDFS "/etc/asterisk/pjsip_trunk_idfs.conf"
  30. #define TRUNK_GLOBAL_FILE "/etc/asterisk/extensions_trunks_global_custom.conf"
  31. #define DID_CONF_FILE "/etc/asterisk/extensions_extendid_custom.conf"
  32. #define DOD_CONF_FILE "/etc/asterisk/extensions_extendod_custom.conf"
  33. #define KEYVALLEN 100
  34. #define VERSION "V2.0.1"
  35. #define QUERY_TRUNK_SQL "select trunkactive,trunkstyle,trunk,host,port,outbound_proxy,voipusername,authuser,\
  36. fromuser,fromdomain,contact,voipsecret,qualify,qualifyfreq,transport,context,\
  37. dtmfmode,videosupport,encryption,srtpcapable,alaw,ulaw,g722,g729,g726,gsm,\
  38. speex,h261,h263,h263p,h264,vp8,opus,outboundcid,prefix from t_pbx_users_voiptrunk"
  39. #define QUERY_DID_SQL "select didnumber,type,exten from t_pbx_inbound_did"
  40. #define QUERY_DOD_SQL "select dodexten,trunkname,trunk from v_extension_trunk_dod"
  41. char g_host_name[MINI_SIZE];
  42. char g_user_name[MINI_SIZE];
  43. char g_password[MINI_SIZE];
  44. char g_db_name[MINI_SIZE];
  45. const unsigned int g_db_port = 3306;
  46. char * mytime(){
  47. time_t my_time;
  48. time(&my_time);
  49. char *time_string = ctime(&my_time);
  50. if (time_string[strlen(time_string) - 1] == '\n')
  51. {
  52. time_string[strlen(time_string) - 1] = '\0';
  53. }
  54. return time_string;
  55. }
  56. void print_mysql_error(const char *msg) { // 打印最后一次错误
  57. if (msg)
  58. printf("%s: %s\n", msg, mysql_error(g_conn));
  59. else
  60. puts(mysql_error(g_conn));
  61. }
  62. int executesql(const char * sql) {
  63. /*query the database according the sql*/
  64. if (mysql_real_query(g_conn, sql, strlen(sql))) // 如果失败
  65. return -1; // 表示失败
  66. return 0; // 成功执行
  67. }
  68. int init_mysql() { // 初始化连接
  69. // init the database connection
  70. g_conn = mysql_init(NULL);
  71. /* connect the database */
  72. if(!mysql_real_connect(g_conn, g_host_name, g_user_name, g_password, g_db_name, g_db_port, NULL, 0)) // 如果失败
  73. return -1;
  74. // 是否连接已经可用
  75. if (executesql("set names utf8")) // 如果失败
  76. return -1;
  77. return 0; // 返回成功
  78. }
  79. // mysql> desc users_voiptrunk;
  80. // +---------------+--------------+------+-----+---------------------+----------------+
  81. // | Field | Type | Null | Key | Default | Extra |
  82. // +---------------+--------------+------+-----+---------------------+----------------+
  83. // | _id | int(16) | NO | PRI | NULL | auto_increment |
  84. // | _trunkactive | varchar(3) | NO | | yes | |
  85. // | _trunk | varchar(64) | NO | UNI | | |
  86. // | _trunkname | varchar(64) | NO | UNI | NULL | |
  87. // | _trunkstyle | varchar(64) | NO | | | |
  88. // | _host | varchar(64) | NO | | yes | |
  89. // | _port | varchar(8) | NO | | | |
  90. // | _voipusername | varchar(64) | NO | | | |
  91. // | _authuser | varchar(64) | NO | | | |
  92. // | _fromuser | varchar(64) | NO | | | |
  93. // | _fromdomain | varchar(64) | NO | | | |
  94. // | _contact | varchar(64) | NO | | | |
  95. // | _voipsecret | varchar(128) | NO | | | |
  96. // | _outboundcid | varchar(32) | NO | | | |
  97. // | _prefix | varchar(16) | NO | | | |
  98. // | _qualify | varchar(8) | NO | | 2000 | |
  99. // | _qualifyfreq | varchar(8) | NO | | 60 | |
  100. // | _transport | varchar(16) | NO | | udp | |
  101. // | _context | varchar(32) | NO | | default | |
  102. // | _hasexten | varchar(3) | NO | | yes | |
  103. // | _dtmfmode | varchar(8) | NO | | rfc2833 | |
  104. // | _videosupport | varchar(3) | NO | | no | |
  105. // | _encryption | varchar(3) | NO | | yes | |
  106. // | _srtpcapable | varchar(3) | NO | | no | |
  107. // | _prack | varchar(3) | NO | | no | |
  108. // | _alaw | int(1) | NO | | 1 | |
  109. // | _ulaw | int(1) | NO | | 1 | |
  110. // | _g722 | int(1) | NO | | 0 | |
  111. // | _g729 | int(1) | NO | | 0 | |
  112. // | _g726 | int(1) | NO | | 0 | |
  113. // | _gsm | int(1) | NO | | 0 | |
  114. // | _speex | int(1) | NO | | 0 | |
  115. // | _h261 | int(1) | NO | | 0 | |
  116. // | _h263 | int(1) | NO | | 0 | |
  117. // | _h263p | int(1) | NO | | 0 | |
  118. // | _h264 | int(1) | NO | | 0 | |
  119. // | _vp8 | int(1) | YES | | 0 | |
  120. // | _opus | int(1) | YES | | 0 | |
  121. // | _recordin | varchar(32) | NO | | | |
  122. // | _recordout | varchar(32) | NO | | | |
  123. // +---------------+--------------+------+-----+---------------------+----------------+
  124. // 55 rows in set (0.00 sec)
  125. typedef struct trunk {
  126. char trunkactive[MINI_SIZE]; //0 //*
  127. char trunkstyle[MINI_SIZE]; //1 //*
  128. char trunk[MINI_SIZE]; //2 //*
  129. char host[MINI_SIZE]; //3 //*
  130. char port[MINI_SIZE]; //4 //*
  131. char outbound_proxy[MINI_SIZE];//5
  132. char voipusername[MINI_SIZE]; //6 //*
  133. char authuser[MINI_SIZE]; //7
  134. char fromuser[MINI_SIZE]; //8
  135. char fromdomain[MINI_SIZE]; //9
  136. char contact[MINI_SIZE]; //10
  137. char voipsecret[MINI_SIZE]; //11 //*
  138. char qualify[MINI_SIZE]; //12
  139. char qualifyfreq[MINI_SIZE]; //13
  140. char transport[MINI_SIZE]; //14
  141. char context[MINI_SIZE]; //15 //*
  142. char dtmfmode[MINI_SIZE]; //16
  143. char videosupport[MINI_SIZE]; //17
  144. char encryption[MINI_SIZE]; //18
  145. char srtpcapable[MINI_SIZE]; //19
  146. char alaw[TINY_SIZE]; //20
  147. char ulaw[TINY_SIZE]; //21
  148. char g722[TINY_SIZE]; //22
  149. char g729[TINY_SIZE]; //23
  150. char g726[TINY_SIZE]; //24
  151. char gsm[TINY_SIZE]; //25
  152. char speex[TINY_SIZE]; //26
  153. char h261[TINY_SIZE]; //27
  154. char h263[TINY_SIZE]; //28
  155. char h263p[TINY_SIZE]; //29
  156. char h264[TINY_SIZE]; //30
  157. char vp8[TINY_SIZE]; //31
  158. char opus[TINY_SIZE]; //32
  159. char outboundcid[MINI_SIZE]; //33
  160. char prefix[MINI_SIZE]; //34
  161. char allow[MIDLE_SIZE];
  162. char contact_uri[MIDLE_SIZE];
  163. char match[MINI_SIZE];
  164. char identify_by[MINI_SIZE];
  165. } TrunkObject;
  166. typedef struct did {
  167. char didnumber[MINI_SIZE];
  168. char type[MINI_SIZE];
  169. char exten[MINI_SIZE];
  170. } DidObject;
  171. typedef struct dod {
  172. char dodexten[MINI_SIZE];
  173. char trunkname[MINI_SIZE];
  174. char trunk[MINI_SIZE];
  175. } DodObject;
  176. int main(int argc, char **argv) {
  177. if (argc == 2){
  178. if (strcmp(argv[1], "-v") == 0)
  179. {
  180. printf("%s: %s\n", argv[0], VERSION);
  181. return EXIT_SUCCESS;
  182. }else if (strcmp(argv[1], "trunk") == 0 || strcmp(argv[1], "did") == 0 || strcmp(argv[1], "dod") == 0){
  183. }else{
  184. printf("Usage:%s -v | trunk | did | dod\n", argv[0]);
  185. return EXIT_SUCCESS;
  186. }
  187. }else{
  188. printf("Usage:%s -v | trunk | did | dod\n", argv[0]);
  189. return EXIT_SUCCESS;
  190. }
  191. strcpy(g_host_name,getenv("MYSQL"));
  192. strcpy(g_user_name,getenv("MYSQL_USER"));
  193. strcpy(g_password,getenv("MYSQL_PASSWORD"));
  194. strcpy(g_db_name,getenv("MYSQL_DATABASE"));
  195. if (init_mysql()){
  196. print_mysql_error(NULL);
  197. exit(1);
  198. }
  199. if (strcmp(argv[1], "trunk") == 0){
  200. if (executesql(QUERY_TRUNK_SQL)){
  201. print_mysql_error(NULL);
  202. exit(1);
  203. }
  204. g_res = mysql_store_result(g_conn); // 从服务器传送结果集至本地,mysql_use_result直接使用服务器上的记录集
  205. // int iNum_rows = mysql_num_rows(g_res); // 得到记录的行数
  206. // int iNum_fields = mysql_num_fields(g_res); // 得到记录的列数
  207. TrunkObject trunkObject[MAX_TRUNK_SIZE];
  208. memset(trunkObject, 0, sizeof(trunkObject));
  209. char registrationString[MIDLE_SIZE];
  210. int trunk_size = 0;
  211. while ((g_row=mysql_fetch_row(g_res))){ // 打印结果集
  212. // printf("%s\t%s\n", g_row[0], g_row[1]); // 第一,第二字段
  213. if (g_row[0] == NULL || strcmp(g_row[0], "yes") != 0 || g_row[1] == NULL || g_row[2] == NULL || g_row[3] == NULL \
  214. || g_row[4] == NULL || g_row[15] == NULL){
  215. printf("some feild is empty!\n");
  216. continue;
  217. }
  218. // trunkactive,trunkstyle,trunk,host,port,outbound_proxy,voipusername,authuser,\
  219. fromuser,fromdomain,contact,voipsecret,qualify,qualifyfreq,transport,context,\
  220. ,dtmfmode,videosupport,encryption,srtpcapable,alaw,ulaw,g722,g729,g726,gsm\
  221. ,speex,h261,h263,h263p,h264,vp8,opus,outboundcid,prefix
  222. strcpy(trunkObject[trunk_size].trunkactive, g_row[0]);
  223. strcpy(trunkObject[trunk_size].trunkstyle, g_row[1]);
  224. strcpy(trunkObject[trunk_size].trunk, g_row[2]);
  225. strcpy(trunkObject[trunk_size].host, g_row[3]);
  226. strcpy(trunkObject[trunk_size].port, g_row[4]);
  227. if(g_row[5] != NULL){
  228. sprintf(trunkObject[trunk_size].outbound_proxy,"sip:%s\\;lr", g_row[5]);
  229. strcpy(trunkObject[trunk_size].match, g_row[5]);
  230. }else{
  231. strcpy(trunkObject[trunk_size].outbound_proxy, "");
  232. strcpy(trunkObject[trunk_size].match, trunkObject[trunk_size].host);
  233. }
  234. strcpy(trunkObject[trunk_size].voipusername, g_row[6]);
  235. if (g_row[7] != NULL){
  236. strcpy(trunkObject[trunk_size].authuser, g_row[7]);
  237. }else{
  238. strcpy(trunkObject[trunk_size].authuser, trunkObject[trunk_size].voipusername);
  239. }
  240. if (g_row[8] != NULL){
  241. strcpy(trunkObject[trunk_size].fromuser, g_row[8]);
  242. }else{
  243. strcpy(trunkObject[trunk_size].fromuser, trunkObject[trunk_size].voipusername);
  244. }
  245. if (g_row[9] != NULL){
  246. strcpy(trunkObject[trunk_size].fromdomain, g_row[9]);
  247. }else{
  248. strcpy(trunkObject[trunk_size].fromdomain, trunkObject[trunk_size].host);
  249. }
  250. if (g_row[10] != NULL){
  251. strcpy(trunkObject[trunk_size].contact, g_row[10]);
  252. }else{
  253. strcpy(trunkObject[trunk_size].contact, trunkObject[trunk_size].voipusername);
  254. }
  255. strcpy(trunkObject[trunk_size].voipsecret, g_row[11]);
  256. strcpy(trunkObject[trunk_size].qualify, g_row[12]);
  257. strcpy(trunkObject[trunk_size].qualifyfreq, g_row[13]);
  258. strcpy(trunkObject[trunk_size].transport, g_row[14]);
  259. strcpy(trunkObject[trunk_size].context, g_row[15]);
  260. strcpy(trunkObject[trunk_size].dtmfmode, g_row[16]);
  261. strcpy(trunkObject[trunk_size].videosupport, g_row[17]);
  262. strcpy(trunkObject[trunk_size].encryption, g_row[18]);
  263. strcpy(trunkObject[trunk_size].srtpcapable, g_row[19]);
  264. strcpy(trunkObject[trunk_size].alaw, g_row[20]);
  265. strcpy(trunkObject[trunk_size].ulaw, g_row[21]);
  266. strcpy(trunkObject[trunk_size].g722, g_row[22]);
  267. strcpy(trunkObject[trunk_size].g729, g_row[23]);
  268. strcpy(trunkObject[trunk_size].g726, g_row[24]);
  269. strcpy(trunkObject[trunk_size].gsm, g_row[25]);
  270. strcpy(trunkObject[trunk_size].speex, g_row[26]);
  271. strcpy(trunkObject[trunk_size].h261, g_row[27]);
  272. strcpy(trunkObject[trunk_size].h263, g_row[28]);
  273. strcpy(trunkObject[trunk_size].h263p, g_row[29]);
  274. strcpy(trunkObject[trunk_size].h264, g_row[30]);
  275. strcpy(trunkObject[trunk_size].vp8, g_row[31]);
  276. strcpy(trunkObject[trunk_size].opus, g_row[32]);
  277. if (g_row[33] != NULL){
  278. strcpy(trunkObject[trunk_size].outboundcid, g_row[33]);
  279. }else{
  280. strcpy(trunkObject[trunk_size].outboundcid, "");
  281. }
  282. if (g_row[34] != NULL){
  283. strcpy(trunkObject[trunk_size].prefix, g_row[34]);
  284. }else{
  285. strcpy(trunkObject[trunk_size].prefix, "");
  286. }
  287. if(strlen(trunkObject[trunk_size].voipusername) > 0)
  288. {
  289. sprintf(trunkObject[trunk_size].contact_uri,"sip:%s@%s", trunkObject[trunk_size].voipusername, trunkObject[trunk_size].host);
  290. strcpy(trunkObject[trunk_size].identify_by, "auth_username");
  291. }
  292. else
  293. {
  294. sprintf(trunkObject[trunk_size].contact_uri,"sip:%s", trunkObject[trunk_size].host);
  295. strcpy(trunkObject[trunk_size].identify_by, "ip");
  296. }
  297. memset(trunkObject[trunk_size].allow, '\0', sizeof(trunkObject[trunk_size].allow));
  298. if (strcmp(trunkObject[trunk_size].alaw, "1") == 0){
  299. //sprintf(trunkObject[trunk_size].allow, "alaw,");
  300. strcpy(trunkObject[trunk_size].allow, "alaw,");
  301. }
  302. if (strcmp(trunkObject[trunk_size].ulaw, "1") == 0){
  303. //sprintf(trunkObject[trunk_size].allow, "%sulaw,", trunkObject[trunk_size].allow);
  304. strcat(trunkObject[trunk_size].allow, "ulaw,");
  305. }
  306. if (strcmp(trunkObject[trunk_size].g722, "1") == 0){
  307. //sprintf(trunkObject[trunk_size].allow, "%sg722,", trunkObject[trunk_size].allow);
  308. strcat(trunkObject[trunk_size].allow, "g722,");
  309. }
  310. if (strcmp(trunkObject[trunk_size].g729, "1") == 0){
  311. //sprintf(trunkObject[trunk_size].allow, "%sg729,", trunkObject[trunk_size].allow);
  312. strcat(trunkObject[trunk_size].allow, "g729,");
  313. }
  314. if (strcmp(trunkObject[trunk_size].g726, "1") == 0){
  315. //sprintf(trunkObject[trunk_size].allow, "%sg726,", trunkObject[trunk_size].allow);
  316. strcat(trunkObject[trunk_size].allow, "g726,");
  317. }
  318. if (strcmp(trunkObject[trunk_size].speex, "1") == 0){
  319. //sprintf(trunkObject[trunk_size].allow, "%sspeex,", trunkObject[trunk_size].allow);
  320. strcat(trunkObject[trunk_size].allow, "speex,");
  321. }
  322. if (strcmp(trunkObject[trunk_size].gsm, "1") == 0){
  323. //sprintf(trunkObject[trunk_size].allow, "%sgsm,", trunkObject[trunk_size].allow);
  324. strcat(trunkObject[trunk_size].allow, "gsm,");
  325. }
  326. if (strcmp(trunkObject[trunk_size].h261, "1") == 0){
  327. //sprintf(trunkObject[trunk_size].allow, "%sh261,", trunkObject[trunk_size].allow);
  328. strcat(trunkObject[trunk_size].allow, "h261,");
  329. }
  330. if (strcmp(trunkObject[trunk_size].h263, "1") == 0){
  331. //sprintf(trunkObject[trunk_size].allow, "%sh263,", trunkObject[trunk_size].allow);
  332. strcat(trunkObject[trunk_size].allow, "h263,");
  333. }
  334. if (strcmp(trunkObject[trunk_size].h263p, "1") == 0){
  335. //sprintf(trunkObject[trunk_size].allow, "%sh263p,", trunkObject[trunk_size].allow);
  336. strcat(trunkObject[trunk_size].allow, "h263p,");
  337. }
  338. if (strcmp(trunkObject[trunk_size].h264, "1") == 0){
  339. //sprintf(trunkObject[trunk_size].allow, "%sh264,", trunkObject[trunk_size].allow);
  340. strcat(trunkObject[trunk_size].allow, "h264,");
  341. }
  342. if (strcmp(trunkObject[trunk_size].vp8, "1") == 0){
  343. //sprintf(trunkObject[trunk_size].allow, "%svp8,", trunkObject[trunk_size].allow);
  344. strcat(trunkObject[trunk_size].allow, "vp8,");
  345. }
  346. if (strcmp(trunkObject[trunk_size].opus, "1") == 0){
  347. //sprintf(trunkObject[trunk_size].allow, "%sopus,", trunkObject[trunk_size].allow);
  348. strcat(trunkObject[trunk_size].allow, "opus,");
  349. }
  350. // printf("trunk:%s\n", trunkObject[trunk_size].trunk);
  351. trunkObject[trunk_size].allow[strlen(trunkObject[trunk_size].allow)-1]='\0';
  352. // printf("allow:%s\n", trunkObject[trunk_size].allow);
  353. trunk_size++;
  354. }
  355. // printf("trunk_size:%d\n", trunk_size);
  356. FILE *conf_trunk_regs = fopen(PJSIP_TRUNK_REGS, "w+");
  357. FILE *conf_trunk_auths = fopen(PJSIP_TRUNK_AUTHS, "w+");
  358. FILE *conf_trunk_eps = fopen(PJSIP_TRUNK_EPS, "w+");
  359. FILE *conf_trunk_aors = fopen(PJSIP_TRUNK_AORS, "w+");
  360. FILE *conf_trunk_idfs = fopen(PJSIP_TRUNK_IDFS, "w+");
  361. if (conf_trunk_regs == NULL){
  362. perror("Open sip registration conf file Error: ");
  363. exit(1);
  364. }
  365. fprintf(conf_trunk_regs, ";!\n\
  366. ;! Automatically generated configuration file\n\
  367. ;! Filename: pjsip_trunk_regs.conf (/etc/asterisk/pjsip_trunk_regs.conf)\n\
  368. ;! Generator: Generator Trunk Registrations\n\
  369. ;! Creation Date: %s\n\
  370. ;!\n\n\
  371. ",\
  372. mytime()\
  373. );
  374. if (conf_trunk_auths == NULL){
  375. perror("Open trunk auth file Error: ");
  376. exit(1);
  377. }
  378. fprintf(conf_trunk_auths, ";!\n\
  379. ;! Automatically generated configuration file\n\
  380. ;! Filename: pjsip_trunk_auths.conf (/etc/asterisk/pjsip_trunk_auths.conf)\n\
  381. ;! Generator: Generator Trunk Auths\n\
  382. ;! Creation Date: %s\n\
  383. ;!\n\n\
  384. ",\
  385. mytime()\
  386. );
  387. if (conf_trunk_eps == NULL){
  388. perror("Open trunk endpoint conf file Error: ");
  389. exit(1);
  390. }
  391. fprintf(conf_trunk_eps, ";!\n\
  392. ;! Automatically generated configuration file\n\
  393. ;! Filename: pjsip_trunk_eps.conf (/etc/asterisk/pjsip_trunk_eps.conf)\n\
  394. ;! Generator: Generator Trunk Endpoints\n\
  395. ;! Creation Date: %s\n\
  396. ;!\n\n\
  397. ",\
  398. mytime()\
  399. );
  400. if (conf_trunk_aors == NULL){
  401. perror("Open trunk aor conf file Error: ");
  402. exit(1);
  403. }
  404. fprintf(conf_trunk_aors, ";!\n\
  405. ;! Automatically generated configuration file\n\
  406. ;! Filename: pjsip_trunk_aors.conf (/etc/asterisk/pjsip_trunk_aors.conf)\n\
  407. ;! Generator: Generator Trunk Aors\n\
  408. ;! Creation Date: %s\n\
  409. ;!\n\n\
  410. ",\
  411. mytime()\
  412. );
  413. if (conf_trunk_idfs == NULL){
  414. perror("Open trunk identify conf file Error: ");
  415. exit(1);
  416. }
  417. fprintf(conf_trunk_idfs, ";!\n\
  418. ;! Automatically generated configuration file\n\
  419. ;! Filename: pjsip_trunk_idfs.conf (/etc/asterisk/pjsip_trunk_idfs.conf)\n\
  420. ;! Generator: Generator Trunk Identify\n\
  421. ;! Creation Date: %s\n\
  422. ;!\n\n\
  423. ",\
  424. mytime()\
  425. );
  426. int i = 0;
  427. while(i < trunk_size){
  428. if(strcmp(trunkObject[i].trunkactive, "yes") == 0){
  429. if(strcmp(trunkObject[i].trunkstyle, "Peer") != 0 && strlen(trunkObject[i].voipusername) > 0)
  430. {
  431. fprintf(conf_trunk_regs, "\
  432. [%s]\n\
  433. type = registration\n\
  434. transport = transport-%s\n\
  435. outbound_auth = %s_auth\n\
  436. server_uri = sip:%s:%s\n\
  437. client_uri = sip:%s@%s\n\
  438. contact_user = %s\n\
  439. retry_interval = 60\n\
  440. forbidden_retry_interval = 600\n\
  441. expiration = 3600\n\
  442. line = yes\n\
  443. outbound_proxy = %s\n\
  444. endpoint = %s\
  445. \n", \
  446. trunkObject[i].trunk,\
  447. trunkObject[i].transport,\
  448. trunkObject[i].trunk,\
  449. trunkObject[i].host,\
  450. trunkObject[i].port,\
  451. trunkObject[i].voipusername,\
  452. trunkObject[i].fromdomain,\
  453. trunkObject[i].contact,\
  454. trunkObject[i].outbound_proxy,\
  455. trunkObject[i].trunk\
  456. );
  457. fprintf(conf_trunk_auths, "\
  458. [%s_auth]\n\
  459. type = auth\n\
  460. auth_type = userpass\n\
  461. password = %s\n\
  462. username = %s\n\
  463. \n", \
  464. trunkObject[i].trunk,\
  465. trunkObject[i].voipsecret,\
  466. trunkObject[i].authuser\
  467. );
  468. fprintf(conf_trunk_eps, "\
  469. [%s]\n\
  470. type = endpoint\n\
  471. transport = transport-%s\n\
  472. context = %s\n\
  473. disallow = all\n\
  474. allow = %s\n\
  475. aors = %s\n\
  476. direct_media = yes\n\
  477. connected_line_method = update\n\
  478. direct_media_method = update\n\
  479. direct_media_glare_mitigation = incoming\n\
  480. disable_direct_media_on_nat = yes\n\
  481. dtmf_mode = %s\n\
  482. force_rport = no\n\
  483. ice_support = no\n\
  484. identify_by = %s\n\
  485. outbound_auth = %s_auth\n\
  486. outbound_proxy = %s\n\
  487. rewrite_contact = no\n\
  488. rtp_symmetric = no\n\
  489. send_diversion = no\n\
  490. send_pai = no\n\
  491. send_rpid = no\n\
  492. media_encryption = no\n\
  493. inband_progress = no\n\
  494. device_state_busy_at = 0\n\
  495. allow_transfer = yes\n\
  496. allow_subscribe = yes\n\
  497. sdp_session = IP Audio Center\n\
  498. tos_audio = ef\n\
  499. tos_video = AF41\n\
  500. from_domain = %s\n\
  501. from_user = %s\n\
  502. cos_audio = 5\n\
  503. cos_video = 4\n\
  504. user_eq_phone = no\n\
  505. rtp_keepalive = 60\n\
  506. rtp_timeout = 60\n\
  507. rtp_timeout_hold = 300\n\
  508. rtcp_mux = no\n\
  509. codec_prefs_incoming_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  510. codec_prefs_incoming_offer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  511. codec_prefs_outgoing_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  512. codec_prefs_outgoing_offer = prefer:pending, operation:union, keep:all, transcode:allow\n\
  513. \n",\
  514. trunkObject[i].trunk,\
  515. trunkObject[i].transport,\
  516. trunkObject[i].context,\
  517. trunkObject[i].allow,\
  518. trunkObject[i].trunk,\
  519. trunkObject[i].dtmfmode,\
  520. trunkObject[i].identify_by,\
  521. trunkObject[i].trunk,\
  522. trunkObject[i].outbound_proxy,\
  523. trunkObject[i].fromdomain,\
  524. trunkObject[i].fromuser\
  525. );
  526. fprintf(conf_trunk_aors, "\
  527. [%s]\n\
  528. type=aor\n\
  529. contact=%s\n\
  530. default_expiration=600\n\
  531. max_contacts=100\n\
  532. minimum_expiration=60\n\
  533. remove_existing=no\n\
  534. qualify_frequency=%s\n\
  535. authenticate_qualify=no\n\
  536. maximum_expiration=3600\n\
  537. outbound_proxy=%s\n\
  538. qualify_timeout=%s\n\
  539. \n",\
  540. trunkObject[i].trunk,\
  541. trunkObject[i].contact_uri,\
  542. trunkObject[i].qualifyfreq,\
  543. trunkObject[i].outbound_proxy,\
  544. trunkObject[i].qualify\
  545. );
  546. fprintf(conf_trunk_idfs, "\
  547. [%s]\n\
  548. type=identify\n\
  549. endpoint=%s\n\
  550. match=%s\n\
  551. ",\
  552. trunkObject[i].trunk,\
  553. trunkObject[i].trunk,\
  554. trunkObject[i].match\
  555. );
  556. }
  557. else
  558. {
  559. fprintf(conf_trunk_auths, "\
  560. [%s_auth]\n\
  561. type = auth\n\
  562. auth_type = userpass\n\
  563. password = %s\n\
  564. username = %s\n\
  565. \n", \
  566. trunkObject[i].voipusername,\
  567. trunkObject[i].voipsecret,\
  568. trunkObject[i].authuser\
  569. );
  570. fprintf(conf_trunk_eps, "\
  571. [%s]\n\
  572. type = endpoint\n\
  573. transport = transport-%s\n\
  574. context = %s\n\
  575. disallow = all\n\
  576. allow = %s\n\
  577. aors = %s\n\
  578. direct_media = yes\n\
  579. connected_line_method = update\n\
  580. direct_media_method = update\n\
  581. direct_media_glare_mitigation = incoming\n\
  582. disable_direct_media_on_nat = yes\n\
  583. dtmf_mode = %s\n\
  584. force_rport = no\n\
  585. ice_support = no\n\
  586. identify_by = %s\n\
  587. outbound_auth = %s_auth\n\
  588. rewrite_contact = no\n\
  589. rtp_symmetric = no\n\
  590. send_diversion = no\n\
  591. send_pai = no\n\
  592. send_rpid = no\n\
  593. media_encryption = no\n\
  594. inband_progress = no\n\
  595. device_state_busy_at = 0\n\
  596. allow_transfer = yes\n\
  597. allow_subscribe = yes\n\
  598. sdp_session = IP Audio Center\n\
  599. tos_audio = ef\n\
  600. tos_video = AF41\n\
  601. from_user = %s\n\
  602. cos_audio = 5\n\
  603. cos_video = 4\n\
  604. user_eq_phone = no\n\
  605. rtp_keepalive = 60\n\
  606. rtp_timeout = 60\n\
  607. rtp_timeout_hold = 300\n\
  608. rtcp_mux = no\n\
  609. codec_prefs_incoming_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  610. codec_prefs_incoming_offer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  611. codec_prefs_outgoing_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  612. codec_prefs_outgoing_offer = prefer:pending, operation:union, keep:all, transcode:allow\n\
  613. \n",\
  614. trunkObject[i].voipusername,\
  615. trunkObject[i].transport,\
  616. trunkObject[i].context,\
  617. trunkObject[i].allow,\
  618. trunkObject[i].voipusername,\
  619. trunkObject[i].dtmfmode,\
  620. trunkObject[i].identify_by,\
  621. trunkObject[i].voipusername,\
  622. trunkObject[i].fromuser\
  623. );
  624. fprintf(conf_trunk_aors, "\
  625. [%s]\n\
  626. type=aor\n\
  627. default_expiration=600\n\
  628. max_contacts=1\n\
  629. minimum_expiration=60\n\
  630. remove_existing=yes\n\
  631. qualify_frequency=%s\n\
  632. authenticate_qualify=no\n\
  633. maximum_expiration=3600\n\
  634. qualify_timeout=%s\n\
  635. \n",\
  636. trunkObject[i].voipusername,\
  637. trunkObject[i].qualifyfreq,\
  638. trunkObject[i].qualify\
  639. );
  640. }
  641. }
  642. i++;
  643. }
  644. fclose(conf_trunk_aors);
  645. fclose(conf_trunk_auths);
  646. fclose(conf_trunk_eps);
  647. fclose(conf_trunk_idfs);
  648. fclose(conf_trunk_regs);
  649. FILE *global_fp = fopen(TRUNK_GLOBAL_FILE, "w+");
  650. if (global_fp == NULL){
  651. perror("Open trunk conf file Error: ");
  652. exit(1);
  653. }
  654. fprintf(global_fp, ";!\n\
  655. ;! Automatically generated configuration file\n\
  656. ;! Filename: extensions_trunks_global_custom.conf (/etc/asterisk/extensions_trunks_global_custom.conf)\n\
  657. ;! Generator: Generator Trunk\n\
  658. ;! Creation Date: %s\n\
  659. ;!\n\n\
  660. ",\
  661. mytime()\
  662. );
  663. i = 0;
  664. // CID_$trunk = $outboundcid
  665. // P_CID_$trunk=$trunkcid_preferred
  666. // $trunk=SIP/$trunk/$prefix
  667. if (trunk_size > 0){
  668. while(i < trunk_size){
  669. fprintf(global_fp, "\
  670. CID_%s = %s\n\
  671. %s=SIP/%s/%s\
  672. \n", \
  673. trunkObject[i].trunk,\
  674. trunkObject[i].outboundcid,\
  675. trunkObject[i].trunk,\
  676. trunkObject[i].trunk,\
  677. trunkObject[i].prefix\
  678. );
  679. i++;
  680. }
  681. }
  682. fclose(global_fp);
  683. }else if (strcmp(argv[1], "did") == 0){
  684. if (executesql(QUERY_DID_SQL)){
  685. print_mysql_error(NULL);
  686. exit(1);
  687. }
  688. g_res = mysql_store_result(g_conn);
  689. DidObject didObject[MAX_TRUNK_SIZE];
  690. memset(didObject, 0, sizeof(didObject));
  691. int did_size = 0;
  692. while ((g_row=mysql_fetch_row(g_res))){ // 打印结果集
  693. if (g_row[0] != NULL){
  694. strcpy(didObject[did_size].didnumber, g_row[0]);
  695. }else{
  696. strcpy(didObject[did_size].didnumber, "");
  697. }
  698. if (g_row[1] != NULL){
  699. strcpy(didObject[did_size].type, g_row[1]);
  700. }else{
  701. strcpy(didObject[did_size].type, "");
  702. }
  703. if (g_row[2] != NULL){
  704. strcpy(didObject[did_size].exten, g_row[2]);
  705. }else{
  706. strcpy(didObject[did_size].exten, "");
  707. }
  708. did_size++;
  709. }
  710. FILE *did_fp = fopen(DID_CONF_FILE, "w+");
  711. if (did_fp == NULL){
  712. perror("Open did conf file Error: ");
  713. exit(1);
  714. }
  715. fprintf(did_fp, ";!\n\
  716. ;! Automatically generated configuration file\n\
  717. ;! Filename: extensions_extendid_custom.conf (/etc/asterisk/extensions_extendid_custom.conf)\n\
  718. ;! Generator: Generator did\n\
  719. ;! Creation Date: %s\n\
  720. ;!\n\n\
  721. ",\
  722. mytime()\
  723. );
  724. int m = 0;
  725. if (did_size > 0){
  726. while(m < did_size){
  727. if (strcmp(didObject[m].didnumber, "") != 0 && strcmp(didObject[m].type, "") != 0){
  728. //exten => _didnumber,1,Goto(default,_destexten,1)
  729. if(strcmp(didObject[m].type, "extension") == 0){
  730. fprintf(did_fp, "\
  731. exten => %s,1,Goto(default,%s,1)\
  732. \n", \
  733. didObject[m].didnumber,\
  734. didObject[m].exten\
  735. );
  736. }else if(strcmp(didObject[m].type, "ivr") == 0){
  737. fprintf(did_fp, "\
  738. exten => %s,1,Goto(voicemenu-custom-%s,%s,1)\
  739. \n", \
  740. didObject[m].didnumber,\
  741. didObject[m].exten,\
  742. didObject[m].exten\
  743. );
  744. }else if(strcmp(didObject[m].type, "group") == 0){
  745. fprintf(did_fp, "\
  746. exten => %s,1,Goto(paging-group-%s,%s,1)\
  747. \n", \
  748. didObject[m].didnumber,\
  749. didObject[m].exten,\
  750. didObject[m].exten\
  751. );
  752. }else if(strcmp(didObject[m].type, "trigger") == 0){
  753. fprintf(did_fp, "\
  754. exten => %s,1,Goto(call-trigger,${EXTEN},1)\
  755. \n", \
  756. didObject[m].didnumber\
  757. );
  758. }else if(strcmp(didObject[m].type, "user") == 0){
  759. int id = 100000 + atoi(didObject[m].exten);
  760. fprintf(did_fp, "\
  761. exten => %s,1,Goto(manager-queue-%d,s,1)\
  762. \n", \
  763. didObject[m].didnumber,\
  764. id\
  765. );
  766. }
  767. }
  768. m++;
  769. }
  770. }
  771. fclose(did_fp);
  772. }else if (strcmp(argv[1], "dod") == 0){
  773. if (executesql(QUERY_DOD_SQL)){
  774. print_mysql_error(NULL);
  775. exit(1);
  776. }
  777. g_res = mysql_store_result(g_conn);
  778. DodObject dodObject[MAX_TRUNK_SIZE];
  779. memset(dodObject, 0, sizeof(dodObject));
  780. int dod_size = 0;
  781. while ((g_row=mysql_fetch_row(g_res))){ // 打印结果集
  782. if (g_row[0] != NULL){
  783. strcpy(dodObject[dod_size].dodexten, g_row[0]);
  784. }else{
  785. strcpy(dodObject[dod_size].dodexten, "");
  786. }
  787. if (g_row[1] != NULL){
  788. strcpy(dodObject[dod_size].trunkname, g_row[1]);
  789. }else{
  790. strcpy(dodObject[dod_size].trunkname, "");
  791. }
  792. if (g_row[2] != NULL){
  793. strcpy(dodObject[dod_size].trunk, g_row[2]);
  794. }else{
  795. strcpy(dodObject[dod_size].trunk, "");
  796. }
  797. dod_size++;
  798. }
  799. FILE *dod_fp = fopen(DOD_CONF_FILE, "w+");
  800. if (dod_fp == NULL){
  801. perror("Open dod conf file Error: ");
  802. exit(1);
  803. }
  804. fprintf(dod_fp, ";!\n\
  805. ;! Automatically generated configuration file\n\
  806. ;! Filename: extensions_extendod_custom.conf (/etc/asterisk/extensions_extendod_custom.conf)\n\
  807. ;! Generator: Generator dod\n\
  808. ;! Creation Date: %s\n\
  809. ;!\n\n\
  810. ",\
  811. mytime()\
  812. );
  813. int n = 0;
  814. if (dod_size > 0){
  815. while(n < dod_size){
  816. if (strcmp(dodObject[n].dodexten, "") != 0 && strcmp(dodObject[n].trunk, "") != 0){
  817. //exten => _X./$dodexten,1, Macro(trunkdial-failover,,,${EXTEN},$trunk${EXTEN:0})
  818. fprintf(dod_fp, "\
  819. exten => _X./%s,1, Gosub(trunkdial-failover,s,1(,,,${EXTEN},${%s}${EXTEN:0}))\
  820. \n", \
  821. dodObject[n].dodexten,\
  822. dodObject[n].trunk\
  823. );
  824. }
  825. n++;
  826. }
  827. }
  828. fclose(dod_fp);
  829. }else{
  830. printf("Usage:%s [-v] | trunk | did | dod\n", argv[0]);
  831. }
  832. mysql_free_result(g_res); // 释放结果集
  833. mysql_close(g_conn); // 关闭链接
  834. return EXIT_SUCCESS;
  835. }