generate_trunk_conf.c 33 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040
  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. if(strcmp(g_row[16],"rfc2833") == 0)
  261. strcpy(trunkObject[trunk_size].dtmfmode, "rfc4733");
  262. else
  263. strcpy(trunkObject[trunk_size].dtmfmode, g_row[16]);
  264. strcpy(trunkObject[trunk_size].videosupport, g_row[17]);
  265. strcpy(trunkObject[trunk_size].encryption, g_row[18]);
  266. strcpy(trunkObject[trunk_size].srtpcapable, g_row[19]);
  267. strcpy(trunkObject[trunk_size].alaw, g_row[20]);
  268. strcpy(trunkObject[trunk_size].ulaw, g_row[21]);
  269. strcpy(trunkObject[trunk_size].g722, g_row[22]);
  270. strcpy(trunkObject[trunk_size].g729, g_row[23]);
  271. strcpy(trunkObject[trunk_size].g726, g_row[24]);
  272. strcpy(trunkObject[trunk_size].gsm, g_row[25]);
  273. strcpy(trunkObject[trunk_size].speex, g_row[26]);
  274. strcpy(trunkObject[trunk_size].h261, g_row[27]);
  275. strcpy(trunkObject[trunk_size].h263, g_row[28]);
  276. strcpy(trunkObject[trunk_size].h263p, g_row[29]);
  277. strcpy(trunkObject[trunk_size].h264, g_row[30]);
  278. strcpy(trunkObject[trunk_size].vp8, g_row[31]);
  279. strcpy(trunkObject[trunk_size].opus, g_row[32]);
  280. if (g_row[33] != NULL){
  281. strcpy(trunkObject[trunk_size].outboundcid, g_row[33]);
  282. }else{
  283. strcpy(trunkObject[trunk_size].outboundcid, "");
  284. }
  285. if (g_row[34] != NULL){
  286. strcpy(trunkObject[trunk_size].prefix, g_row[34]);
  287. }else{
  288. strcpy(trunkObject[trunk_size].prefix, "");
  289. }
  290. if(strlen(trunkObject[trunk_size].voipusername) > 0)
  291. {
  292. sprintf(trunkObject[trunk_size].contact_uri,"sip:%s@%s", trunkObject[trunk_size].voipusername, trunkObject[trunk_size].host);
  293. strcpy(trunkObject[trunk_size].identify_by, "auth_username");
  294. }
  295. else
  296. {
  297. sprintf(trunkObject[trunk_size].contact_uri,"sip:%s", trunkObject[trunk_size].host);
  298. strcpy(trunkObject[trunk_size].identify_by, "ip");
  299. }
  300. memset(trunkObject[trunk_size].allow, '\0', sizeof(trunkObject[trunk_size].allow));
  301. if (strcmp(trunkObject[trunk_size].alaw, "1") == 0){
  302. //sprintf(trunkObject[trunk_size].allow, "alaw,");
  303. strcpy(trunkObject[trunk_size].allow, "alaw,");
  304. }
  305. if (strcmp(trunkObject[trunk_size].ulaw, "1") == 0){
  306. //sprintf(trunkObject[trunk_size].allow, "%sulaw,", trunkObject[trunk_size].allow);
  307. strcat(trunkObject[trunk_size].allow, "ulaw,");
  308. }
  309. if (strcmp(trunkObject[trunk_size].g722, "1") == 0){
  310. //sprintf(trunkObject[trunk_size].allow, "%sg722,", trunkObject[trunk_size].allow);
  311. strcat(trunkObject[trunk_size].allow, "g722,");
  312. }
  313. if (strcmp(trunkObject[trunk_size].g729, "1") == 0){
  314. //sprintf(trunkObject[trunk_size].allow, "%sg729,", trunkObject[trunk_size].allow);
  315. strcat(trunkObject[trunk_size].allow, "g729,");
  316. }
  317. if (strcmp(trunkObject[trunk_size].g726, "1") == 0){
  318. //sprintf(trunkObject[trunk_size].allow, "%sg726,", trunkObject[trunk_size].allow);
  319. strcat(trunkObject[trunk_size].allow, "g726,");
  320. }
  321. if (strcmp(trunkObject[trunk_size].speex, "1") == 0){
  322. //sprintf(trunkObject[trunk_size].allow, "%sspeex,", trunkObject[trunk_size].allow);
  323. strcat(trunkObject[trunk_size].allow, "speex,");
  324. }
  325. if (strcmp(trunkObject[trunk_size].gsm, "1") == 0){
  326. //sprintf(trunkObject[trunk_size].allow, "%sgsm,", trunkObject[trunk_size].allow);
  327. strcat(trunkObject[trunk_size].allow, "gsm,");
  328. }
  329. if (strcmp(trunkObject[trunk_size].h261, "1") == 0){
  330. //sprintf(trunkObject[trunk_size].allow, "%sh261,", trunkObject[trunk_size].allow);
  331. strcat(trunkObject[trunk_size].allow, "h261,");
  332. }
  333. if (strcmp(trunkObject[trunk_size].h263, "1") == 0){
  334. //sprintf(trunkObject[trunk_size].allow, "%sh263,", trunkObject[trunk_size].allow);
  335. strcat(trunkObject[trunk_size].allow, "h263,");
  336. }
  337. if (strcmp(trunkObject[trunk_size].h263p, "1") == 0){
  338. //sprintf(trunkObject[trunk_size].allow, "%sh263p,", trunkObject[trunk_size].allow);
  339. strcat(trunkObject[trunk_size].allow, "h263p,");
  340. }
  341. if (strcmp(trunkObject[trunk_size].h264, "1") == 0){
  342. //sprintf(trunkObject[trunk_size].allow, "%sh264,", trunkObject[trunk_size].allow);
  343. strcat(trunkObject[trunk_size].allow, "h264,");
  344. }
  345. if (strcmp(trunkObject[trunk_size].vp8, "1") == 0){
  346. //sprintf(trunkObject[trunk_size].allow, "%svp8,", trunkObject[trunk_size].allow);
  347. strcat(trunkObject[trunk_size].allow, "vp8,");
  348. }
  349. if (strcmp(trunkObject[trunk_size].opus, "1") == 0){
  350. //sprintf(trunkObject[trunk_size].allow, "%sopus,", trunkObject[trunk_size].allow);
  351. strcat(trunkObject[trunk_size].allow, "opus,");
  352. }
  353. // printf("trunk:%s\n", trunkObject[trunk_size].trunk);
  354. trunkObject[trunk_size].allow[strlen(trunkObject[trunk_size].allow)-1]='\0';
  355. // printf("allow:%s\n", trunkObject[trunk_size].allow);
  356. trunk_size++;
  357. }
  358. // printf("trunk_size:%d\n", trunk_size);
  359. FILE *conf_trunk_regs = fopen(PJSIP_TRUNK_REGS, "w+");
  360. FILE *conf_trunk_auths = fopen(PJSIP_TRUNK_AUTHS, "w+");
  361. FILE *conf_trunk_eps = fopen(PJSIP_TRUNK_EPS, "w+");
  362. FILE *conf_trunk_aors = fopen(PJSIP_TRUNK_AORS, "w+");
  363. FILE *conf_trunk_idfs = fopen(PJSIP_TRUNK_IDFS, "w+");
  364. if (conf_trunk_regs == NULL){
  365. perror("Open sip registration conf file Error: ");
  366. exit(1);
  367. }
  368. fprintf(conf_trunk_regs, ";!\n\
  369. ;! Automatically generated configuration file\n\
  370. ;! Filename: pjsip_trunk_regs.conf (/etc/asterisk/pjsip_trunk_regs.conf)\n\
  371. ;! Generator: Generator Trunk Registrations\n\
  372. ;! Creation Date: %s\n\
  373. ;!\n\n\
  374. ",\
  375. mytime()\
  376. );
  377. if (conf_trunk_auths == NULL){
  378. perror("Open trunk auth file Error: ");
  379. exit(1);
  380. }
  381. fprintf(conf_trunk_auths, ";!\n\
  382. ;! Automatically generated configuration file\n\
  383. ;! Filename: pjsip_trunk_auths.conf (/etc/asterisk/pjsip_trunk_auths.conf)\n\
  384. ;! Generator: Generator Trunk Auths\n\
  385. ;! Creation Date: %s\n\
  386. ;!\n\n\
  387. ",\
  388. mytime()\
  389. );
  390. if (conf_trunk_eps == NULL){
  391. perror("Open trunk endpoint conf file Error: ");
  392. exit(1);
  393. }
  394. fprintf(conf_trunk_eps, ";!\n\
  395. ;! Automatically generated configuration file\n\
  396. ;! Filename: pjsip_trunk_eps.conf (/etc/asterisk/pjsip_trunk_eps.conf)\n\
  397. ;! Generator: Generator Trunk Endpoints\n\
  398. ;! Creation Date: %s\n\
  399. ;!\n\n\
  400. ",\
  401. mytime()\
  402. );
  403. if (conf_trunk_aors == NULL){
  404. perror("Open trunk aor conf file Error: ");
  405. exit(1);
  406. }
  407. fprintf(conf_trunk_aors, ";!\n\
  408. ;! Automatically generated configuration file\n\
  409. ;! Filename: pjsip_trunk_aors.conf (/etc/asterisk/pjsip_trunk_aors.conf)\n\
  410. ;! Generator: Generator Trunk Aors\n\
  411. ;! Creation Date: %s\n\
  412. ;!\n\n\
  413. ",\
  414. mytime()\
  415. );
  416. if (conf_trunk_idfs == NULL){
  417. perror("Open trunk identify conf file Error: ");
  418. exit(1);
  419. }
  420. fprintf(conf_trunk_idfs, ";!\n\
  421. ;! Automatically generated configuration file\n\
  422. ;! Filename: pjsip_trunk_idfs.conf (/etc/asterisk/pjsip_trunk_idfs.conf)\n\
  423. ;! Generator: Generator Trunk Identify\n\
  424. ;! Creation Date: %s\n\
  425. ;!\n\n\
  426. ",\
  427. mytime()\
  428. );
  429. int i = 0;
  430. while(i < trunk_size){
  431. if(strcmp(trunkObject[i].trunkactive, "yes") == 0){
  432. if(strcmp(trunkObject[i].trunkstyle, "Peer") != 0)
  433. {
  434. if(strlen(trunkObject[i].voipusername) > 0)
  435. {
  436. fprintf(conf_trunk_regs, "\
  437. [%s]\n\
  438. type = registration\n\
  439. transport = transport-%s\n\
  440. outbound_auth = auth_%s\n\
  441. server_uri = sip:%s:%s\n\
  442. client_uri = sip:%s@%s\n\
  443. contact_user = %s\n\
  444. retry_interval = 60\n\
  445. forbidden_retry_interval = 600\n\
  446. expiration = 3600\n\
  447. line = yes\n\
  448. outbound_proxy = %s\n\
  449. endpoint = %s\
  450. \n", \
  451. trunkObject[i].trunk,\
  452. trunkObject[i].transport,\
  453. trunkObject[i].trunk,\
  454. trunkObject[i].host,\
  455. trunkObject[i].port,\
  456. trunkObject[i].voipusername,\
  457. trunkObject[i].fromdomain,\
  458. trunkObject[i].contact,\
  459. trunkObject[i].outbound_proxy,\
  460. trunkObject[i].trunk\
  461. );
  462. fprintf(conf_trunk_auths, "\
  463. [auth_%s]\n\
  464. type = auth\n\
  465. auth_type = userpass\n\
  466. password = %s\n\
  467. username = %s\n\
  468. \n", \
  469. trunkObject[i].trunk,\
  470. trunkObject[i].voipsecret,\
  471. trunkObject[i].authuser\
  472. );
  473. fprintf(conf_trunk_eps, "\
  474. [%s]\n\
  475. type = endpoint\n\
  476. transport = transport-%s\n\
  477. context = %s\n\
  478. disallow = all\n\
  479. allow = %s\n\
  480. aors = %s\n\
  481. direct_media = yes\n\
  482. connected_line_method = update\n\
  483. direct_media_method = update\n\
  484. direct_media_glare_mitigation = incoming\n\
  485. disable_direct_media_on_nat = yes\n\
  486. dtmf_mode = %s\n\
  487. force_rport = no\n\
  488. ice_support = no\n\
  489. identify_by = %s\n\
  490. outbound_auth = auth_%s\n\
  491. outbound_proxy = %s\n\
  492. rewrite_contact = no\n\
  493. rtp_symmetric = no\n\
  494. send_diversion = no\n\
  495. send_pai = no\n\
  496. send_rpid = no\n\
  497. media_encryption = no\n\
  498. inband_progress = no\n\
  499. device_state_busy_at = 0\n\
  500. allow_transfer = yes\n\
  501. allow_subscribe = yes\n\
  502. sdp_session = IP Audio Center\n\
  503. tos_audio = ef\n\
  504. tos_video = AF41\n\
  505. from_domain = %s\n\
  506. from_user = %s\n\
  507. cos_audio = 5\n\
  508. cos_video = 4\n\
  509. user_eq_phone = no\n\
  510. rtp_keepalive = 60\n\
  511. rtp_timeout = 60\n\
  512. rtp_timeout_hold = 300\n\
  513. rtcp_mux = no\n\
  514. codec_prefs_incoming_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  515. codec_prefs_incoming_offer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  516. codec_prefs_outgoing_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  517. codec_prefs_outgoing_offer = prefer:pending, operation:union, keep:all, transcode:allow\n\
  518. \n",\
  519. trunkObject[i].trunk,\
  520. trunkObject[i].transport,\
  521. trunkObject[i].context,\
  522. trunkObject[i].allow,\
  523. trunkObject[i].trunk,\
  524. trunkObject[i].dtmfmode,\
  525. trunkObject[i].identify_by,\
  526. trunkObject[i].trunk,\
  527. trunkObject[i].outbound_proxy,\
  528. trunkObject[i].fromdomain,\
  529. trunkObject[i].fromuser\
  530. );
  531. fprintf(conf_trunk_aors, "\
  532. [%s]\n\
  533. type=aor\n\
  534. contact=%s\n\
  535. default_expiration=600\n\
  536. max_contacts=100\n\
  537. minimum_expiration=60\n\
  538. remove_existing=no\n\
  539. qualify_frequency=%s\n\
  540. authenticate_qualify=no\n\
  541. maximum_expiration=3600\n\
  542. outbound_proxy=%s\n\
  543. qualify_timeout=%s\n\
  544. \n",\
  545. trunkObject[i].trunk,\
  546. trunkObject[i].contact_uri,\
  547. trunkObject[i].qualifyfreq,\
  548. trunkObject[i].outbound_proxy,\
  549. trunkObject[i].qualify\
  550. );
  551. fprintf(conf_trunk_idfs, "\
  552. [%s]\n\
  553. type=identify\n\
  554. endpoint=%s\n\
  555. match=%s\n\
  556. ",\
  557. trunkObject[i].trunk,\
  558. trunkObject[i].trunk,\
  559. trunkObject[i].match\
  560. );
  561. }
  562. else
  563. {
  564. fprintf(conf_trunk_eps, "\
  565. [%s]\n\
  566. type = endpoint\n\
  567. transport = transport-%s\n\
  568. context = %s\n\
  569. disallow = all\n\
  570. allow = %s\n\
  571. aors = %s\n\
  572. direct_media = yes\n\
  573. connected_line_method = update\n\
  574. direct_media_method = update\n\
  575. direct_media_glare_mitigation = incoming\n\
  576. disable_direct_media_on_nat = yes\n\
  577. dtmf_mode = %s\n\
  578. force_rport = no\n\
  579. ice_support = no\n\
  580. identify_by = %s\n\
  581. outbound_auth =\n\
  582. outbound_proxy = %s\n\
  583. rewrite_contact = no\n\
  584. rtp_symmetric = no\n\
  585. send_diversion = no\n\
  586. send_pai = no\n\
  587. send_rpid = no\n\
  588. media_encryption = no\n\
  589. inband_progress = no\n\
  590. device_state_busy_at = 0\n\
  591. allow_transfer = yes\n\
  592. allow_subscribe = yes\n\
  593. sdp_session = IP Audio Center\n\
  594. tos_audio = ef\n\
  595. tos_video = AF41\n\
  596. from_domain = %s\n\
  597. from_user = %s\n\
  598. cos_audio = 5\n\
  599. cos_video = 4\n\
  600. user_eq_phone = no\n\
  601. rtp_keepalive = 60\n\
  602. rtp_timeout = 60\n\
  603. rtp_timeout_hold = 300\n\
  604. rtcp_mux = no\n\
  605. codec_prefs_incoming_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  606. codec_prefs_incoming_offer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  607. codec_prefs_outgoing_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  608. codec_prefs_outgoing_offer = prefer:pending, operation:union, keep:all, transcode:allow\n\
  609. \n",\
  610. trunkObject[i].trunk,\
  611. trunkObject[i].transport,\
  612. trunkObject[i].context,\
  613. trunkObject[i].allow,\
  614. trunkObject[i].trunk,\
  615. trunkObject[i].dtmfmode,\
  616. trunkObject[i].identify_by,\
  617. trunkObject[i].outbound_proxy,\
  618. trunkObject[i].fromdomain,\
  619. trunkObject[i].fromuser\
  620. );
  621. fprintf(conf_trunk_aors, "\
  622. [%s]\n\
  623. type=aor\n\
  624. contact=%s\n\
  625. default_expiration=600\n\
  626. max_contacts=100\n\
  627. minimum_expiration=60\n\
  628. remove_existing=no\n\
  629. qualify_frequency=%s\n\
  630. authenticate_qualify=no\n\
  631. maximum_expiration=3600\n\
  632. outbound_proxy=%s\n\
  633. qualify_timeout=%s\n\
  634. \n",\
  635. trunkObject[i].trunk,\
  636. trunkObject[i].contact_uri,\
  637. trunkObject[i].qualifyfreq,\
  638. trunkObject[i].outbound_proxy,\
  639. trunkObject[i].qualify\
  640. );
  641. fprintf(conf_trunk_idfs, "\
  642. [%s]\n\
  643. type=identify\n\
  644. endpoint=%s\n\
  645. match=%s\n\
  646. ",\
  647. trunkObject[i].trunk,\
  648. trunkObject[i].trunk,\
  649. trunkObject[i].match\
  650. );
  651. }
  652. }
  653. else
  654. {
  655. fprintf(conf_trunk_auths, "\
  656. [auth_%s]\n\
  657. type = auth\n\
  658. auth_type = userpass\n\
  659. password = %s\n\
  660. username = %s\n\
  661. \n", \
  662. trunkObject[i].voipusername,\
  663. trunkObject[i].voipsecret,\
  664. trunkObject[i].authuser\
  665. );
  666. fprintf(conf_trunk_eps, "\
  667. [%s]\n\
  668. type = endpoint\n\
  669. transport = transport-%s\n\
  670. context = %s\n\
  671. disallow = all\n\
  672. allow = %s\n\
  673. aors = %s\n\
  674. auth = auth_%s\n\
  675. direct_media = yes\n\
  676. connected_line_method = update\n\
  677. direct_media_method = update\n\
  678. direct_media_glare_mitigation = incoming\n\
  679. disable_direct_media_on_nat = yes\n\
  680. dtmf_mode = %s\n\
  681. force_rport = no\n\
  682. ice_support = no\n\
  683. identify_by = %s\n\
  684. outbound_auth = auth_%s\n\
  685. rewrite_contact = no\n\
  686. rtp_symmetric = no\n\
  687. send_diversion = no\n\
  688. send_pai = no\n\
  689. send_rpid = no\n\
  690. media_encryption = no\n\
  691. inband_progress = no\n\
  692. device_state_busy_at = 0\n\
  693. allow_transfer = yes\n\
  694. allow_subscribe = yes\n\
  695. sdp_session = IP Audio Center\n\
  696. tos_audio = ef\n\
  697. tos_video = AF41\n\
  698. from_user = %s\n\
  699. cos_audio = 5\n\
  700. cos_video = 4\n\
  701. user_eq_phone = no\n\
  702. rtp_keepalive = 60\n\
  703. rtp_timeout = 60\n\
  704. rtp_timeout_hold = 300\n\
  705. rtcp_mux = no\n\
  706. codec_prefs_incoming_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  707. codec_prefs_incoming_offer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  708. codec_prefs_outgoing_answer = prefer:pending, operation:intersect, keep:all, transcode:allow\n\
  709. codec_prefs_outgoing_offer = prefer:pending, operation:union, keep:all, transcode:allow\n\
  710. \n",\
  711. trunkObject[i].voipusername,\
  712. trunkObject[i].transport,\
  713. trunkObject[i].context,\
  714. trunkObject[i].allow,\
  715. trunkObject[i].voipusername,\
  716. trunkObject[i].voipusername,\
  717. trunkObject[i].dtmfmode,\
  718. trunkObject[i].identify_by,\
  719. trunkObject[i].voipusername,\
  720. trunkObject[i].fromuser\
  721. );
  722. fprintf(conf_trunk_aors, "\
  723. [%s]\n\
  724. type=aor\n\
  725. default_expiration=600\n\
  726. max_contacts=1\n\
  727. minimum_expiration=60\n\
  728. remove_existing=yes\n\
  729. qualify_frequency=%s\n\
  730. authenticate_qualify=no\n\
  731. maximum_expiration=3600\n\
  732. qualify_timeout=%s\n\
  733. \n",\
  734. trunkObject[i].voipusername,\
  735. trunkObject[i].qualifyfreq,\
  736. trunkObject[i].qualify\
  737. );
  738. }
  739. }
  740. i++;
  741. }
  742. fclose(conf_trunk_aors);
  743. fclose(conf_trunk_auths);
  744. fclose(conf_trunk_eps);
  745. fclose(conf_trunk_idfs);
  746. fclose(conf_trunk_regs);
  747. FILE *global_fp = fopen(TRUNK_GLOBAL_FILE, "w+");
  748. if (global_fp == NULL){
  749. perror("Open trunk conf file Error: ");
  750. exit(1);
  751. }
  752. fprintf(global_fp, ";!\n\
  753. ;! Automatically generated configuration file\n\
  754. ;! Filename: extensions_trunks_global_custom.conf (/etc/asterisk/extensions_trunks_global_custom.conf)\n\
  755. ;! Generator: Generator Trunk\n\
  756. ;! Creation Date: %s\n\
  757. ;!\n\n\
  758. ",\
  759. mytime()\
  760. );
  761. i = 0;
  762. // CID_$trunk = $outboundcid
  763. // P_CID_$trunk=$trunkcid_preferred
  764. // $trunk=SIP/$trunk/$prefix
  765. if (trunk_size > 0){
  766. while(i < trunk_size){
  767. fprintf(global_fp, "\
  768. CID_%s = %s\n\
  769. %s=SIP/%s/%s\
  770. \n", \
  771. trunkObject[i].trunk,\
  772. trunkObject[i].outboundcid,\
  773. trunkObject[i].trunk,\
  774. trunkObject[i].trunk,\
  775. trunkObject[i].prefix\
  776. );
  777. i++;
  778. }
  779. }
  780. fclose(global_fp);
  781. }else if (strcmp(argv[1], "did") == 0){
  782. if (executesql(QUERY_DID_SQL)){
  783. print_mysql_error(NULL);
  784. exit(1);
  785. }
  786. g_res = mysql_store_result(g_conn);
  787. DidObject didObject[MAX_TRUNK_SIZE];
  788. memset(didObject, 0, sizeof(didObject));
  789. int did_size = 0;
  790. while ((g_row=mysql_fetch_row(g_res))){ // 打印结果集
  791. if (g_row[0] != NULL){
  792. strcpy(didObject[did_size].didnumber, g_row[0]);
  793. }else{
  794. strcpy(didObject[did_size].didnumber, "");
  795. }
  796. if (g_row[1] != NULL){
  797. strcpy(didObject[did_size].type, g_row[1]);
  798. }else{
  799. strcpy(didObject[did_size].type, "");
  800. }
  801. if (g_row[2] != NULL){
  802. strcpy(didObject[did_size].exten, g_row[2]);
  803. }else{
  804. strcpy(didObject[did_size].exten, "");
  805. }
  806. did_size++;
  807. }
  808. FILE *did_fp = fopen(DID_CONF_FILE, "w+");
  809. if (did_fp == NULL){
  810. perror("Open did conf file Error: ");
  811. exit(1);
  812. }
  813. fprintf(did_fp, ";!\n\
  814. ;! Automatically generated configuration file\n\
  815. ;! Filename: extensions_extendid_custom.conf (/etc/asterisk/extensions_extendid_custom.conf)\n\
  816. ;! Generator: Generator did\n\
  817. ;! Creation Date: %s\n\
  818. ;!\n\n\
  819. ",\
  820. mytime()\
  821. );
  822. int m = 0;
  823. if (did_size > 0){
  824. while(m < did_size){
  825. if (strcmp(didObject[m].didnumber, "") != 0 && strcmp(didObject[m].type, "") != 0){
  826. if(strcmp(didObject[m].type, "extension") == 0){
  827. fprintf(did_fp, "\
  828. exten => %s,1,Gosub(stdexten,s,1(%s,PJSIP/%s))\
  829. \n", \
  830. didObject[m].didnumber,\
  831. didObject[m].exten,\
  832. didObject[m].exten\
  833. );
  834. }else if(strcmp(didObject[m].type, "ivr") == 0){
  835. fprintf(did_fp, "\
  836. exten => %s,1,Goto(voicemenu-custom-%s,%s,1)\
  837. \n", \
  838. didObject[m].didnumber,\
  839. didObject[m].exten,\
  840. didObject[m].exten\
  841. );
  842. }else if(strcmp(didObject[m].type, "group") == 0){
  843. fprintf(did_fp, "\
  844. exten => %s,1,Goto(paging-group-%s,%s,1)\
  845. \n", \
  846. didObject[m].didnumber,\
  847. didObject[m].exten,\
  848. didObject[m].exten\
  849. );
  850. }else if(strcmp(didObject[m].type, "trigger") == 0){
  851. fprintf(did_fp, "\
  852. exten => %s,1,Goto(call-trigger,${EXTEN},1)\
  853. \n", \
  854. didObject[m].didnumber\
  855. );
  856. }else if(strcmp(didObject[m].type, "user") == 0){
  857. int id = 100000 + atoi(didObject[m].exten);
  858. fprintf(did_fp, "\
  859. exten => %s,1,Goto(manager-queue-%d,s,1)\
  860. \n", \
  861. didObject[m].didnumber,\
  862. id\
  863. );
  864. }
  865. }
  866. m++;
  867. }
  868. }
  869. fclose(did_fp);
  870. }else if (strcmp(argv[1], "dod") == 0){
  871. if (executesql(QUERY_DOD_SQL)){
  872. print_mysql_error(NULL);
  873. exit(1);
  874. }
  875. g_res = mysql_store_result(g_conn);
  876. DodObject dodObject[MAX_TRUNK_SIZE];
  877. memset(dodObject, 0, sizeof(dodObject));
  878. int dod_size = 0;
  879. while ((g_row=mysql_fetch_row(g_res))){ // 打印结果集
  880. if (g_row[0] != NULL){
  881. strcpy(dodObject[dod_size].dodexten, g_row[0]);
  882. }else{
  883. strcpy(dodObject[dod_size].dodexten, "");
  884. }
  885. if (g_row[1] != NULL){
  886. strcpy(dodObject[dod_size].trunkname, g_row[1]);
  887. }else{
  888. strcpy(dodObject[dod_size].trunkname, "");
  889. }
  890. if (g_row[2] != NULL){
  891. strcpy(dodObject[dod_size].trunk, g_row[2]);
  892. }else{
  893. strcpy(dodObject[dod_size].trunk, "");
  894. }
  895. dod_size++;
  896. }
  897. FILE *dod_fp = fopen(DOD_CONF_FILE, "w+");
  898. if (dod_fp == NULL){
  899. perror("Open dod conf file Error: ");
  900. exit(1);
  901. }
  902. fprintf(dod_fp, ";!\n\
  903. ;! Automatically generated configuration file\n\
  904. ;! Filename: extensions_extendod_custom.conf (/etc/asterisk/extensions_extendod_custom.conf)\n\
  905. ;! Generator: Generator dod\n\
  906. ;! Creation Date: %s\n\
  907. ;!\n\n\
  908. ",\
  909. mytime()\
  910. );
  911. int n = 0;
  912. if (dod_size > 0){
  913. while(n < dod_size){
  914. if (strcmp(dodObject[n].dodexten, "") != 0 && strcmp(dodObject[n].trunk, "") != 0){
  915. //exten => _X./$dodexten,1, Macro(trunkdial-failover,,,${EXTEN},$trunk${EXTEN:0})
  916. fprintf(dod_fp, "\
  917. exten => _X./%s,1, Gosub(trunkdial-failover,s,1(,,,${EXTEN},${%s}${EXTEN:0}))\
  918. \n", \
  919. dodObject[n].dodexten,\
  920. dodObject[n].trunk\
  921. );
  922. }
  923. n++;
  924. }
  925. }
  926. fclose(dod_fp);
  927. }else{
  928. printf("Usage:%s [-v] | trunk | did | dod\n", argv[0]);
  929. }
  930. mysql_free_result(g_res); // 释放结果集
  931. mysql_close(g_conn); // 关闭链接
  932. return EXIT_SUCCESS;
  933. }