Commit 860fd9f8 authored by Gabriel Margiani's avatar Gabriel Margiani

added busy and busyall commands.

parent 957a7239
......@@ -17,24 +17,14 @@
**/
#include "account.h"
#include "call.h"
#include "sipphone.h"
p3::account::account(sipphone& p) : phone(p){};
p3::account::account(sipphone& p) : phone(p) {};
p3::account::~account() {};
void p3::account::onRegState(pj::OnRegStateParam &prm) {
}
void p3::account::onIncomingCall(pj::OnIncomingCallParam &iprm) {
p3::call* c = phone.register_new_call(iprm.callId);
phone.register_number(c->get_nr(), c->get_id());
pj::CallOpParam o;
if (phone.get_call_count() < 1) {
o.statusCode = PJSIP_SC_BUSY_HERE;
c->answer(o);
} else {
o.statusCode = PJSIP_SC_RINGING;
c->answer(o);
}
phone.handle_incoming_call(iprm.callId);
}
......@@ -34,6 +34,8 @@ std::map<std::string, std::string> p3::client::command_shorthands {
{"m", "mute"},
{"ma", "muteall"},
{"a", "answer"},
{"b", "busy"},
{"ba", "busyall"},
{"l", "list"},
{"j", "conference"},
{"t", "transfer"},
......
......@@ -27,12 +27,6 @@ p3::eventHook::eventHook(config& c, phonebook& p) : conf(c), book(p), command(co
}
void p3::eventHook::run_hook(std::string event, int cid, std::string nr) {
// TODO: Think of a better place for this
if (conf.get_bool("phonebook:auto_add_unanswered")) {
book.add(nr);
}
int pid = fork();
if (pid == 0) {
execl(
......
......@@ -40,6 +40,8 @@ void print_usage() {
<< "p3 reload - reload phonebook and some parts of the configuration." << std::endl
<< "p3 c all [nr] - call someone" << std::endl
<< "p3 a nswer - answer a currently ringing call" << std::endl
<< "p3 b usy - answer busy to a currently ringing call" << std::endl
<< "p3 b usyall - toggle: answer all incoming calls with busy" << std::endl
<< "p3 l ist - list current calls" << std::endl
<< "p3 h angup [id] - hanup" << std::endl
<< "p3 ha ngupall - hanup all current calls" << std::endl
......
......@@ -41,6 +41,7 @@ std::map<std::string, std::string> p3::server::default_config {
{"hook:command", "~/.3phone/hook"},
{"phone:ringtone", "/usr/share/3phone/rt.wav"},
{"phone:holdmusic", "none"},
{"phone:busy_on_busy", "true"},
};
......@@ -49,7 +50,7 @@ p3::server::server() :
connection(p3::mQueue::DefaultId, true),
book(),
hook(conf, book),
phone(conf, hook)
phone(conf, hook, book)
{
p3::phonebook::set_config(conf);
book.load();
......@@ -168,6 +169,10 @@ void p3::clientHandler::parse_command(const std::string& c) {
handle_mute();
} else if ("muteall" == c) {
handle_mute_all();
} else if ("busy" == c) {
handle_busy();
} else if ("busyall" == c) {
handle_busy_all();
} else if ("conference" == c) {
handle_conference();
} else if ("transfer" == c) {
......@@ -234,6 +239,16 @@ void p3::clientHandler::handle_mute_all() {
connection.send(p3::protocol::OK, "(un)mute all OK");
}
void p3::clientHandler::handle_busy() {
phone.busy(get_call_id("Call to reject (id)"));
connection.send(p3::protocol::OK, "busy OK");
}
void p3::clientHandler::handle_busy_all() {
phone.busyall_toggle();
connection.send(p3::protocol::OK, "busyall OK");
}
void p3::clientHandler::handle_list() {
send_calls_list();
connection.send(p3::protocol::OK, "List OK");
......
......@@ -113,6 +113,8 @@ namespace p3 {
void handle_hold();
void handle_mute();
void handle_mute_all();
void handle_busy();
void handle_busy_all();
void handle_reload();
void handle_conference();
void handle_transfer();
......
......@@ -21,7 +21,16 @@
#include "error.h"
#include "sipphone.h"
p3::sipphone::sipphone(p3::config& c, p3::eventHook& e) : conf(c), eventhook(e), id_counter(0), active_call(-1), mute(false), ring_index(0) {
p3::sipphone::sipphone(p3::config& c, p3::eventHook& e, p3::phonebook& b) :
conf(c),
eventhook(e),
book(b),
id_counter(0),
active_call(-1),
mute(false),
always_busy(false),
ring_index(0)
{
// Initiate pj
endpoint = new pj::Endpoint;
......@@ -61,6 +70,8 @@ p3::sipphone::sipphone(p3::config& c, p3::eventHook& e) : conf(c), eventhook(e),
pj::AccountConfig acc_cfg;
acc_cfg.idUri = conf.get_string("account:id_uri");
acc_cfg.regConfig.registrarUri = conf.get_string("account:registrar");
acc_cfg.regConfig.timeoutSec = 60;
acc_cfg.regConfig.retryIntervalSec = 30;
acc_cfg.sipConfig.authCreds.push_back(
pj::AuthCredInfo(
conf.get_string("account:sheme"),
......@@ -128,7 +139,7 @@ p3::sipphone::~sipphone() {
}
void p3::sipphone::register_thread(const std::string& id) {
std::lock_guard<std::mutex> g(threads_mutex);
std::lock_guard<std::recursive_mutex> g(threads_mutex);
pj_thread_desc* ptd = new pj_thread_desc[1]();
pj_thread_t* tptr;
pj_thread_register(id.c_str(), *ptd, &tptr);
......@@ -136,7 +147,7 @@ void p3::sipphone::register_thread(const std::string& id) {
}
void p3::sipphone::unregister_thread(const std::string& id) {
std::lock_guard<std::mutex> g(threads_mutex);
std::lock_guard<std::recursive_mutex> g(threads_mutex);
pj_thread_destroy(pj_threads[id].first);
}
......@@ -170,7 +181,7 @@ void p3::sipphone::stop_ringing() {
}
p3::call* p3::sipphone::register_new_call(int pjid) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
if (calls.empty()) {
id_counter = 0;
}
......@@ -180,6 +191,24 @@ p3::call* p3::sipphone::register_new_call(int pjid) {
return c;
}
void p3::sipphone::handle_incoming_call(int pjid) {
p3::call* c = register_new_call(pjid);
register_number(c->get_nr(), c->get_id());
if (conf.get_bool("phonebook:auto_add_unanswered")) {
book.add(c->get_nr());
}
pj::CallOpParam o;
if (always_busy || (get_call_count() < 1 && conf.get_bool("phone:busy_on_busy"))) {
o.statusCode = PJSIP_SC_BUSY_HERE;
c->hangup(o);
} else {
o.statusCode = PJSIP_SC_RINGING;
c->answer(o);
}
}
void p3::sipphone::call(const std::string& nr) {
p3::call* c = register_new_call();
try {
......@@ -192,7 +221,7 @@ void p3::sipphone::call(const std::string& nr) {
}
void p3::sipphone::hangup(int id) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
pj::CallOpParam o;
try {
get_call_by_id(id)->hangup(o);
......@@ -202,7 +231,7 @@ void p3::sipphone::hangup(int id) {
}
void p3::sipphone::hangup_all() {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
pj::CallOpParam o;
try {
for (auto c : calls) {
......@@ -215,7 +244,7 @@ void p3::sipphone::hangup_all() {
}
void p3::sipphone::answer(int id) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
pj::CallOpParam o;
o.statusCode = PJSIP_SC_OK;
try {
......@@ -225,25 +254,40 @@ void p3::sipphone::answer(int id) {
}
}
void p3::sipphone::busy(int id) {
std::lock_guard<std::recursive_mutex> g(calls_mutex);
pj::CallOpParam o;
o.statusCode = PJSIP_SC_BUSY_HERE;
try {
get_call_by_id(id, p3::callState::INCOMING)->hangup(o);
} catch (pj::Error &e) {
throw p3::perror("sipphone:pjbusy", e.info());
}
}
void p3::sipphone::busyall_toggle() {
always_busy = !always_busy;
}
void p3::sipphone::hold_toggle(int id) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
pj::CallOpParam o;
o.statusCode = PJSIP_SC_OK;
try {
get_call_by_id(id, p3::callState::RUNNING)->hold_toggle();
} catch (pj::Error &e) {
throw p3::perror("sipphone:pjanswer", e.info());
throw p3::perror("sipphone:pjholdtoggle", e.info());
}
}
void p3::sipphone::mute_toggle(int id) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
pj::CallOpParam o;
o.statusCode = PJSIP_SC_OK;
try {
get_call_by_id(id)->mute_toggle();
} catch (pj::Error &e) {
throw p3::perror("sipphone:pjanswer", e.info());
throw p3::perror("sipphone:pjmutetoggle", e.info());
}
}
......@@ -263,7 +307,7 @@ void p3::sipphone::global_mute_toggle() {
}
void p3::sipphone::conference() {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
for (auto c = calls.begin(); c != calls.end(); c++) {
pj::AudioMedia* au = c->second->get_audio_media();
if (au == nullptr) continue;
......@@ -285,7 +329,7 @@ void p3::sipphone::conference() {
}
void p3::sipphone::transfer(int id, int destId) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
pj::CallOpParam o;
o.options = PJSUA_XFER_NO_REQUIRE_REPLACES;
try {
......@@ -300,7 +344,7 @@ void p3::sipphone::transfer(int id, int destId) {
}
void p3::sipphone::dial_dtmf(int id, const std::string& digits) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
try {
get_call_by_id(id)->dialDtmf(digits);
} catch (pj::Error &e) {
......@@ -333,7 +377,7 @@ p3::call* p3::sipphone::get_call_by_id(int id, p3::callState f, bool update_acti
}
void p3::sipphone::delete_call(int in) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
unregister_number(calls[in]->get_nr());
delete calls[in];
calls.erase(in);
......@@ -351,7 +395,7 @@ int p3::sipphone::get_call_count(p3::callState filter) {
return calls.size();
}
int co = 0;
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
for (auto a : calls) {
if (a.second->get_state() == filter) {
co++;
......@@ -362,7 +406,7 @@ int p3::sipphone::get_call_count(p3::callState filter) {
std::map<int, std::pair<std::string, char> > p3::sipphone::get_call_list(p3::callState filter) {
std::map<int, std::pair<std::string, char> > s;
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
for (auto a : calls) {
if (filter != p3::callState::NONE && a.second->get_state() != filter) {
continue;
......@@ -395,7 +439,7 @@ int p3::sipphone::get_id_by_nr(const std::string& nr) {
}
std::string p3::sipphone::get_nr_by_id(int id) {
std::lock_guard<std::mutex> g(calls_mutex);
std::lock_guard<std::recursive_mutex> g(calls_mutex);
try {
return get_call_by_id(id)->get_nr();
} catch (pj::Error &e) {
......
......@@ -30,6 +30,7 @@
#include "account.h"
#include "call.h"
#include "eventhook.h"
#include "phonebook.h"
namespace p3 {
......@@ -39,6 +40,8 @@ namespace p3 {
eventHook& eventhook;
phonebook& book;
pj::Endpoint* endpoint;
p3::account* acc;
......@@ -46,15 +49,16 @@ namespace p3 {
std::atomic_int active_call;
std::map<int, p3::call *> calls;
std::map<std::string, int> nr_map;
std::mutex calls_mutex;
std::recursive_mutex calls_mutex;
std::map<std::string, std::pair<pj_thread_t*, pj_thread_desc*> > pj_threads;
std::mutex threads_mutex;
std::recursive_mutex threads_mutex;
pj::AudioMediaPlayer* ringtone;
pj::AudioMediaPlayer* hold_music;
bool mute;
bool always_busy;
protected:
......@@ -76,9 +80,11 @@ namespace p3 {
void register_number(std::string nr, int id);
void unregister_number(std::string nr);
void handle_incoming_call (int pjid = PJSUA_INVALID_ID);
public:
explicit sipphone(config& c, eventHook& e);
explicit sipphone(config& c, eventHook& e, phonebook& b);
sipphone(const sipphone& c) = delete;
~sipphone();
......@@ -89,6 +95,8 @@ namespace p3 {
void hangup(int id = -1);
void hangup_all();
void answer(int id = -1);
void busy(int id = -1);
void busyall_toggle();
void hold_toggle(int id = -1);
void mute_toggle(int id = -1);
void global_mute_toggle();
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment