sip_call_t * call_get_xcall(sip_call_t *call) { if (call_get_attribute(call, SIP_ATTR_XCALLID)) { return call_find_by_callid(call_get_attribute(call, SIP_ATTR_XCALLID)); } else { return call_find_by_xcallid(call_get_attribute(call, SIP_ATTR_CALLID)); } }
int call_attr_compare(sip_call_t *one, sip_call_t *two, enum sip_attr_id id) { char onevalue[256], twovalue[256]; int oneintvalue, twointvalue; int comparetype; /* TODO 0 = string compare, 1 = int comprare */ switch (id) { case SIP_ATTR_CALLINDEX: oneintvalue = one->index; twointvalue = two->index; comparetype = 1; break; case SIP_ATTR_MSGCNT: oneintvalue = call_msg_count(one); twointvalue = call_msg_count(two); comparetype = 1; break; default: // Get attribute values memset(onevalue, 0, sizeof(onevalue)); memset(twovalue, 0, sizeof(twovalue)); call_get_attribute(one, id, onevalue); call_get_attribute(two, id, twovalue); comparetype = 0; break; } switch (comparetype) { case 0: if (strlen(twovalue) == 0 && strlen(onevalue) == 0) return 0; if (strlen(twovalue) == 0) return 1; if (strlen(onevalue) == 0) return -1; return strcmp(onevalue, twovalue); case 1: if (oneintvalue == twointvalue) return 0; if (oneintvalue > twointvalue) return 1; if (oneintvalue < twointvalue) return -1; /* no break */ default: return 0; } }
int sip_check_call_ignore(sip_call_t *call) { int i; for (i = 0; i < sizeof(attrs) / sizeof(*attrs); i++) { if (is_ignored_value(attrs[i].name, call_get_attribute(call, attrs[i].id))) { return 1; } } return 0; }
sip_call_t * call_find_by_xcallid(const char *xcallid) { const char *cur_xcallid; sip_call_t *cur = calls; while (cur) { cur_xcallid = call_get_attribute(cur, SIP_ATTR_XCALLID); if (cur_xcallid && !strcmp(cur_xcallid, xcallid)) { return cur; } cur = cur->next; } return NULL; }
const char * call_list_line_text(PANEL *panel, sip_call_t *call, char *text) { int i, collen; char call_attr[256]; char coltext[256]; int colid; int width; WINDOW *win = panel_window(panel); // Get window width width = getmaxx(win); // Get panel info call_list_info_t *info = call_list_info(panel); // Print requested columns for (i = 0; i < info->columncnt; i++) { // Get current column id colid = info->columns[i].id; // Get current column width collen = info->columns[i].width; // Check if next column fits on window width if (strlen(text) + collen >= width) collen = width - strlen(text); // If no space left on the screen stop processing columns if (collen <= 0) break; // Initialize column text memset(coltext, 0, sizeof(coltext)); memset(call_attr, 0, sizeof(call_attr)); // Get call attribute for current column if (call_get_attribute(call, colid, call_attr)) { sprintf(coltext, "%.*s", collen, call_attr); } // Add the column text to the existing columns sprintf(text + strlen(text), "%-*s ", collen, coltext); } return text; }
void call_list_draw_list(PANEL *panel) { WINDOW *win; int height, width, cline = 0; struct sip_call *call; int i, collen; char coltext[256]; int colid; int colpos; int color; // Get panel info call_list_info_t *info = call_list_info(panel); // Get window of call list panel win = info->list_win; getmaxyx(win, height, width); // If autoscroll is enabled, select the last dialog if (info->autoscroll) { call_list_handle_key(panel, key_action_key(ACTION_END)); } // If no active call, use the fist one (if exists) if (info->first_call == -1 && vector_iterator_count(&info->calls)) { vector_iterator_reset(&info->calls); call = vector_iterator_next(&info->calls); info->cur_call = info->first_call = vector_index(vector_iterator_vector(&info->calls), call); info->cur_line = info->first_line = 1; } // Clear call list before redrawing werase(win); // Set the iterator position to the first call vector_iterator_set_current(&info->calls, info->first_call - 1 ); // Fill the call list while ((call = vector_iterator_next(&info->calls))) { // Stop if we have reached the bottom of the list if (cline == height) break; // We only print calls with messages (In fact, all call should have msgs) if (!call_msg_count(call)) continue; // Show bold selected rows if (call_group_exists(info->group, call)) wattron(win, A_BOLD | COLOR_PAIR(CP_DEFAULT)); // Highlight active call if (call->index == info->cur_call + 1) { wattron(win, COLOR_PAIR(CP_WHITE_ON_BLUE)); // Reverse colors on monochrome terminals if (!has_colors()) wattron(win, A_REVERSE); } // Set current line background clear_line(win, cline); // Set current line selection box mvwprintw(win, cline, 2, call_group_exists(info->group, call) ? "[*]" : "[ ]"); // Print requested columns colpos = 6; for (i = 0; i < info->columncnt; i++) { // Get current column id colid = info->columns[i].id; // Get current column width collen = info->columns[i].width; // Check if next column fits on window width if (colpos + collen >= width) break; // Initialize column text memset(coltext, 0, sizeof(coltext)); // Get call attribute for current column if (!call_get_attribute(call, colid, coltext)) { colpos += collen + 1; continue; } // Enable attribute color (if not current one) color = 0; if (call->index != info->cur_call + 1 && (color = sip_attr_get_color(colid, coltext)) > 0) wattron(win, color); // Add the column text to the existing columns mvwprintw(win, cline, colpos, "%.*s", collen, coltext); colpos += collen + 1; // Disable attribute color if (color > 0) wattroff(win, color); } cline++; wattroff(win, COLOR_PAIR(CP_DEFAULT)); wattroff(win, COLOR_PAIR(CP_DEF_ON_BLUE)); wattroff(win, A_BOLD | A_REVERSE); } // Draw scrollbar to the right draw_vscrollbar(win, info->first_line, info->dispcallcnt, 1); wnoutrefresh(info->list_win); }
void call_update_state(sip_call_t *call, sip_msg_t *msg) { const char *callstate; char dur[20]; int reqresp; sip_msg_t *first; if (!call_is_invite(call)) return; // Get the first message in the call first = vector_first(call->msgs); // Get current message Method / Response Code reqresp = msg->reqresp; // If this message is actually a call, get its current state if ((callstate = call_get_attribute(call, SIP_ATTR_CALLSTATE))) { if (!strcmp(callstate, SIP_CALLSTATE_CALLSETUP)) { if (reqresp == 200) { // Alice and Bob are talking call_set_attribute(call, SIP_ATTR_CALLSTATE, SIP_CALLSTATE_INCALL); // Store the timestap where call has started call->active = 1; call->cstart_msg = msg; } else if (reqresp == SIP_METHOD_CANCEL) { // Alice is not in the mood call_set_attribute(call, SIP_ATTR_CALLSTATE, SIP_CALLSTATE_CANCELLED); // Store total call duration call_set_attribute(call, SIP_ATTR_TOTALDUR, timeval_to_duration(msg_get_time(first), msg_get_time(msg), dur)); call->active = 0; } else if (reqresp > 400) { // Bob is not in the mood call_set_attribute(call, SIP_ATTR_CALLSTATE, SIP_CALLSTATE_REJECTED); // Store total call duration call_set_attribute(call, SIP_ATTR_TOTALDUR, timeval_to_duration(msg_get_time(first), msg_get_time(msg), dur)); call->active = 0; } } else if (!strcmp(callstate, SIP_CALLSTATE_INCALL)) { if (reqresp == SIP_METHOD_BYE) { // Thanks for all the fish! call_set_attribute(call, SIP_ATTR_CALLSTATE, SIP_CALLSTATE_COMPLETED); // Store Conversation duration call_set_attribute(call, SIP_ATTR_CONVDUR, timeval_to_duration(msg_get_time(call->cstart_msg), msg_get_time(msg), dur)); call->active = 0; } } else if (reqresp == SIP_METHOD_INVITE && strcmp(callstate, SIP_CALLSTATE_INCALL)) { // Call is being setup (after proper authentication) call_set_attribute(call, SIP_ATTR_CALLSTATE, SIP_CALLSTATE_CALLSETUP); call->active = 1; } else { // Store total call duration call_set_attribute(call, SIP_ATTR_TOTALDUR, timeval_to_duration(msg_get_time(first), msg_get_time(msg), dur)); } } else { // This is actually a call if (reqresp == SIP_METHOD_INVITE) { call_set_attribute(call, SIP_ATTR_CALLSTATE, SIP_CALLSTATE_CALLSETUP); call->active = 1; } } }