📄 bearerbox.c
字号:
if (cfg_get_integer(&max_incoming_sms_qlength, grp, octstr_imm("maximum-queue-length")) == -1) max_incoming_sms_qlength = -1; else { warning(0, "Option 'maximum-queue-length' is deprecated! Please use" " 'sms-incoming-queue-limit' instead!"); } if (max_incoming_sms_qlength == -1 && cfg_get_integer(&max_incoming_sms_qlength, grp, octstr_imm("sms-incoming-queue-limit")) == -1) max_incoming_sms_qlength = -1;#ifndef NO_SMS { List *list; list = cfg_get_multi_group(cfg, octstr_imm("smsc")); if (list != NULL) { start_smsc(cfg); list_destroy(list, NULL); } }#endif #ifndef NO_WAP grp = cfg_get_single_group(cfg, octstr_imm("core")); val = cfg_get(grp, octstr_imm("wdp-interface-name")); if (val != NULL && octstr_len(val) > 0) start_udp(cfg); octstr_destroy(val); if (cfg_get_single_group(cfg, octstr_imm("wapbox")) != NULL) start_wap(cfg);#endif return cfg;}static void empty_msg_lists(void){ Msg *msg;#ifndef NO_WAP if (list_len(incoming_wdp) > 0 || list_len(outgoing_wdp) > 0) warning(0, "Remaining WDP: %ld incoming, %ld outgoing", list_len(incoming_wdp), list_len(outgoing_wdp)); info(0, "Total WDP messages: received %ld, sent %ld", counter_value(incoming_wdp_counter), counter_value(outgoing_wdp_counter));#endif while((msg = list_extract_first(incoming_wdp))!=NULL) msg_destroy(msg); while((msg = list_extract_first(outgoing_wdp))!=NULL) msg_destroy(msg); list_destroy(incoming_wdp, NULL); list_destroy(outgoing_wdp, NULL); counter_destroy(incoming_wdp_counter); counter_destroy(outgoing_wdp_counter); #ifndef NO_SMS /* XXX we should record these so that they are not forever lost... */ if (list_len(incoming_sms) > 0 || list_len(outgoing_sms) > 0) debug("bb", 0, "Remaining SMS: %ld incoming, %ld outgoing", list_len(incoming_sms), list_len(outgoing_sms)); info(0, "Total SMS messages: received %ld, sent %ld", counter_value(incoming_sms_counter), counter_value(outgoing_sms_counter));#endif list_destroy(incoming_sms, msg_destroy_item); list_destroy(outgoing_sms, msg_destroy_item); counter_destroy(incoming_sms_counter); counter_destroy(outgoing_sms_counter);}int main(int argc, char **argv){ int cf_index; Cfg *cfg; Octstr *filename; bb_status = BB_RUNNING; gwlib_init(); start_time = time(NULL); suspended = list_create(); isolated = list_create(); list_add_producer(suspended); list_add_producer(isolated); cf_index = get_and_set_debugs(argc, argv, check_args); if (argv[cf_index] == NULL) filename = octstr_create("kannel.conf"); else filename = octstr_create(argv[cf_index]); cfg = cfg_create(filename); if (cfg_read(cfg) == -1) panic(0, "Couldn't read configuration from `%s'.", octstr_get_cstr(filename)); octstr_destroy(filename); dlr_init(cfg); report_versions("bearerbox"); flow_threads = list_create(); init_bearerbox(cfg); info(0, "----------------------------------------"); info(0, GW_NAME " bearerbox II version %s starting", GW_VERSION); gwthread_sleep(5.0); /* give time to threads to register themselves */ if (store_load()== -1) panic(0, "Cannot start with store-file failing"); info(0, "MAIN: Start-up done, entering mainloop"); if (bb_status == BB_SUSPENDED) { info(0, "Gateway is now SUSPENDED by startup arguments"); } else if (bb_status == BB_ISOLATED) { info(0, "Gateway is now ISOLATED by startup arguments"); list_remove_producer(suspended); } else { smsc2_resume(); list_remove_producer(suspended); list_remove_producer(isolated); } while(bb_status != BB_SHUTDOWN && bb_status != BB_DEAD && list_producer_count(flow_threads) > 0) { /* debug("bb", 0, "Main Thread: going to sleep."); */ /* * Not infinite sleep here, because we should notice * when all "flow threads" are dead and shutting bearerbox * down. * XXX if all "flow threads" call gwthread_wakeup(MAIN_THREAD_ID), * we can enter infinite sleep then. */ gwthread_sleep(10.0); /* debug("bb", 0, "Main Thread: woken up."); */ if (bb_todo == 0) { continue; } if (bb_todo & BB_LOGREOPEN) { warning(0, "SIGHUP received, catching and re-opening logs"); log_reopen(); alog_reopen(); bb_todo = bb_todo & ~BB_LOGREOPEN; } if (bb_todo & BB_CHECKLEAKS) { warning(0, "SIGQUIT received, reporting memory usage."); gw_check_leaks(); bb_todo = bb_todo & ~BB_CHECKLEAKS; } } if (bb_status == BB_SHUTDOWN || bb_status == BB_DEAD) warning(0, "Killing signal or HTTP admin command received, shutting down..."); /* call shutdown */ bb_shutdown(); /* wait until flow threads exit */ while(list_consume(flow_threads)!=NULL) ; info(0, "All flow threads have died, killing core"); bb_status = BB_DEAD; httpadmin_stop(); boxc_cleanup(); smsc2_cleanup(); empty_msg_lists(); list_destroy(flow_threads, NULL); list_destroy(suspended, NULL); list_destroy(isolated, NULL); mutex_destroy(status_mutex); alog_close(); /* if we have any */ bb_alog_shutdown(); cfg_destroy(cfg); dlr_shutdown(); gwlib_shutdown(); if (restart == 1) execvp(argv[0],argv); return 0;}/*---------------------------------------------------------------- * public functions used via HTTP adminstration interface/module */int bb_shutdown(void){ static int called = 0; mutex_lock(status_mutex); if (called) { mutex_unlock(status_mutex); return -1; } debug("bb", 0, "Shutting down " GW_NAME "..."); called = 1; set_shutdown_status(); mutex_unlock(status_mutex);#ifndef NO_SMS debug("bb", 0, "shutting down smsc"); smsc2_shutdown();#endif#ifndef NO_WAP debug("bb", 0, "shutting down udp"); udp_shutdown();#endif store_shutdown(); return 0;}int bb_isolate(void){ mutex_lock(status_mutex); if (bb_status != BB_RUNNING && bb_status != BB_SUSPENDED) { mutex_unlock(status_mutex); return -1; } if (bb_status == BB_RUNNING) { smsc2_suspend(); list_add_producer(isolated); } else list_remove_producer(suspended); bb_status = BB_ISOLATED; mutex_unlock(status_mutex); return 0;}int bb_suspend(void){ mutex_lock(status_mutex); if (bb_status != BB_RUNNING && bb_status != BB_ISOLATED) { mutex_unlock(status_mutex); return -1; } if (bb_status != BB_ISOLATED) { smsc2_suspend(); list_add_producer(isolated); } bb_status = BB_SUSPENDED; list_add_producer(suspended); mutex_unlock(status_mutex); return 0;}int bb_resume(void){ mutex_lock(status_mutex); if (bb_status != BB_SUSPENDED && bb_status != BB_ISOLATED) { mutex_unlock(status_mutex); return -1; } if (bb_status == BB_SUSPENDED) list_remove_producer(suspended); smsc2_resume(); bb_status = BB_RUNNING; list_remove_producer(isolated); mutex_unlock(status_mutex); return 0;}int bb_flush_dlr(void){ /* beware that mutex locking is done in dlr_foobar() routines */ if (bb_status != BB_SUSPENDED) { return -1; } dlr_flush(); return 0;}int bb_stop_smsc(Octstr *id){ return smsc2_stop_smsc(id);}int bb_restart_smsc(Octstr *id){ return smsc2_restart_smsc(id);}int bb_restart(void){ restart = 1; return bb_shutdown();}#define append_status(r, s, f, x) { s = f(x); octstr_append(r, s); \ octstr_destroy(s); }Octstr *bb_print_status(int status_type){ char *s, *lb; char *frmt, *footer; char buf[1024]; Octstr *ret, *str, *version; time_t t; if ((lb = bb_status_linebreak(status_type))==NULL) return octstr_create("Un-supported format"); t = time(NULL) - start_time; if (bb_status == BB_RUNNING) s = "running"; else if (bb_status == BB_ISOLATED) s = "isolated"; else if (bb_status == BB_SUSPENDED) s = "suspended"; else if (bb_status == BB_FULL) s = "filled"; else s = "going down"; version = version_report_string("bearerbox"); if (status_type == BBSTATUS_HTML) { frmt = "%s</p>\n\n" " <p>Status: %s, uptime %ldd %ldh %ldm %lds</p>\n\n" " <p>WDP: received %ld (%ld queued), sent %ld " "(%ld queued)</p>\n\n" " <p>SMS: received %ld (%ld queued), sent %ld " "(%ld queued), store size %ld</p>\n" " <p>SMS: inbound %.2f msg/sec, outbound %.2f msg/sec</p>\n\n" " <p>DLR: %ld queued, using %s storage</p>\n\n"; footer = "<p>"; } else if (status_type == BBSTATUS_WML) { frmt = "%s</p>\n\n" " <p>Status: %s, uptime %ldd %ldh %ldm %lds</p>\n\n" " <p>WDP: received %ld (%ld queued)<br/>\n" " WDP: sent %ld (%ld queued)</p>\n\n" " <p>SMS: received %ld (%ld queued)<br/>\n" " SMS: sent %ld (%ld queued)<br/>\n" " SMS: store size %ld<br/>\n" " SMS: inbound %.2f msg/sec<br/>\n" " SMS: outbound %.2f msg/sec</p>\n\n" " <p>DLR: %ld queued<br/>\n" " DLR: using %s storage</p>\n\n"; footer = "<p>"; } else if (status_type == BBSTATUS_XML) { frmt = "<version>%s</version>\n" "<status>%s, uptime %ldd %ldh %ldm %lds</status>\n" "\t<wdp>\n\t\t<received><total>%ld</total><queued>%ld</queued></received>\n\t\t<sent><total>%ld" "</total><queued>%ld</queued></sent>\n\t</wdp>\n" "\t<sms>\n\t\t<received><total>%ld</total><queued>%ld</queued></received>\n\t\t<sent><total>%ld" "</total><queued>%ld</queued></sent>\n\t\t<storesize>%ld</storesize>\n\t\t" "<inbound>%.2f</inbound>\n\t\t<outbound>%.2f</outbound>\n\t</sms>\n" "\t<dlr>\n\t\t<queued>%ld</queued>\n\t\t<storage>%s</storage>\n\t</dlr>\n"; footer = ""; } else { frmt = "%s\n\nStatus: %s, uptime %ldd %ldh %ldm %lds\n\n" "WDP: received %ld (%ld queued), sent %ld (%ld queued)\n\n" "SMS: received %ld (%ld queued), sent %ld (%ld queued), store size %ld\n" "SMS: inbound %.2f msg/sec, outbound %.2f msg/sec\n\n" "DLR: %ld queued, using %s storage\n\n"; footer = ""; } sprintf(buf, frmt, octstr_get_cstr(version), s, t/3600/24, t/3600%24, t/60%60, t%60, counter_value(incoming_wdp_counter), list_len(incoming_wdp) + boxc_incoming_wdp_queue(), counter_value(outgoing_wdp_counter), list_len(outgoing_wdp) + udp_outgoing_queue(), counter_value(incoming_sms_counter), list_len(incoming_sms), counter_value(outgoing_sms_counter), list_len(outgoing_sms), store_messages(), (float)counter_value(incoming_sms_counter)/t, (float)counter_value(outgoing_sms_counter)/t, dlr_messages(), dlr_type()); octstr_destroy(version); ret = octstr_create(buf); append_status(ret, str, boxc_status, status_type); append_status(ret, str, smsc2_status, status_type); octstr_append_cstr(ret, footer); return ret;}char *bb_status_linebreak(int status_type){ switch(status_type) { case BBSTATUS_HTML: return "<br>\n"; case BBSTATUS_WML: return "<br/>\n"; case BBSTATUS_TEXT: return "\n"; case BBSTATUS_XML: return "\n"; default: return NULL; }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -