Commit a7ff1956 authored by Ronan's avatar Ronan

fix(core): misc =>

  - return nullptr if conference factory uri is not set
  - Address object is now more robust
  - remove custom SharedFromThis object
  - CoreAccessor throw exception if core is destroyed
  - Core must be created with a static method
  - Partial fetch of chat message
  - ...
parent 223bd817
......@@ -2259,7 +2259,7 @@ static void linphone_core_init(LinphoneCore * lc, LinphoneCoreCbs *cbs, LpConfig
lc->sal->set_callbacks(&linphone_sal_callbacks);
new(&lc->cppCore) std::shared_ptr<Core>();
lc->cppCore = ObjectFactory::create<Core>(lc);
lc->cppCore = Core::create(lc);
#ifdef TUNNEL_ENABLED
lc->tunnel=linphone_core_tunnel_new(lc);
......@@ -7237,7 +7237,7 @@ void linphone_core_set_conference_factory_uri(LinphoneCore *lc, const char *uri)
}
const char * linphone_core_get_conference_factory_uri(const LinphoneCore *lc) {
return lp_config_get_string(linphone_core_get_config(lc), "misc", "conference_factory_uri", "sip:");
return lp_config_get_string(linphone_core_get_config(lc), "misc", "conference_factory_uri", nullptr);
}
void linphone_core_enable_conference_server (LinphoneCore *lc, bool_t enable) {
......@@ -7249,7 +7249,11 @@ bool_t linphone_core_conference_server_enabled (const LinphoneCore *lc) {
}
bool_t _linphone_core_is_conference_creation (const LinphoneCore *lc, const LinphoneAddress *addr) {
LinphoneAddress *factoryAddr = linphone_address_new(linphone_core_get_conference_factory_uri(lc));
const char *uri = linphone_core_get_conference_factory_uri(lc);
if (!uri)
return FALSE;
LinphoneAddress *factoryAddr = linphone_address_new(uri);
if (!factoryAddr)
return FALSE;
bool_t result = linphone_address_weak_equal(factoryAddr, addr);
......
......@@ -83,12 +83,20 @@ bool Address::isValid () const {
const string &Address::getScheme () const {
L_D();
if (!d->internalAddress)
return Utils::getEmptyConstRefObject<string>();
d->cache.scheme = L_C_TO_STRING(sal_address_get_scheme(d->internalAddress));
return d->cache.scheme;
}
const string &Address::getDisplayName () const {
L_D();
if (!d->internalAddress)
return Utils::getEmptyConstRefObject<string>();
d->cache.displayName = L_C_TO_STRING(sal_address_get_display_name(d->internalAddress));
return d->cache.displayName;
}
......@@ -105,6 +113,10 @@ bool Address::setDisplayName (const string &displayName) {
const string &Address::getUsername () const {
L_D();
if (!d->internalAddress)
return Utils::getEmptyConstRefObject<string>();
d->cache.username = L_C_TO_STRING(sal_address_get_username(d->internalAddress));
return d->cache.username;
}
......@@ -121,6 +133,10 @@ bool Address::setUsername (const string &username) {
const string &Address::getDomain () const {
L_D();
if (!d->internalAddress)
return Utils::getEmptyConstRefObject<string>();
d->cache.domain = L_C_TO_STRING(sal_address_get_domain(d->internalAddress));
return d->cache.domain;
}
......@@ -187,6 +203,10 @@ bool Address::isSip () const {
const string &Address::getMethodParam () const {
L_D();
if (!d->internalAddress)
return Utils::getEmptyConstRefObject<string>();
d->cache.methodParam = L_C_TO_STRING(sal_address_get_method_param(d->internalAddress));
return d->cache.methodParam;
}
......@@ -203,6 +223,10 @@ bool Address::setMethodParam (const string &methodParam) {
const string &Address::getPassword () const {
L_D();
if (!d->internalAddress)
return Utils::getEmptyConstRefObject<string>();
d->cache.password = L_C_TO_STRING(sal_address_get_password(d->internalAddress));
return d->cache.password;
}
......@@ -260,10 +284,12 @@ bool Address::weakEqual (const Address &address) const {
const string &Address::getHeaderValue (const string &headerName) const {
L_D();
const char *value = sal_address_get_header(d->internalAddress, L_STRING_TO_C(headerName));
if (value) {
d->cache.headers[headerName] = value;
return d->cache.headers[headerName];
if (d->internalAddress) {
const char *value = sal_address_get_header(d->internalAddress, L_STRING_TO_C(headerName));
if (value) {
d->cache.headers[headerName] = value;
return d->cache.headers[headerName];
}
}
return Utils::getEmptyConstRefObject<string>();
......@@ -281,16 +307,18 @@ bool Address::setHeader (const string &headerName, const string &headerValue) {
bool Address::hasParam (const string &paramName) const {
L_D();
return !!sal_address_has_param(d->internalAddress, L_STRING_TO_C(paramName));
return d->internalAddress && !!sal_address_has_param(d->internalAddress, L_STRING_TO_C(paramName));
}
const string &Address::getParamValue (const string &paramName) const {
L_D();
const char *value = sal_address_get_param(d->internalAddress, L_STRING_TO_C(paramName));
if (value) {
d->cache.params[paramName] = value;
return d->cache.params[paramName];
if (d->internalAddress) {
const char *value = sal_address_get_param(d->internalAddress, L_STRING_TO_C(paramName));
if (value) {
d->cache.params[paramName] = value;
return d->cache.params[paramName];
}
}
return Utils::getEmptyConstRefObject<string>();
......@@ -318,16 +346,18 @@ bool Address::setParams (const string &params) {
bool Address::hasUriParam (const string &uriParamName) const {
L_D();
return !!sal_address_has_uri_param(d->internalAddress, L_STRING_TO_C(uriParamName));
return d->internalAddress && !!sal_address_has_uri_param(d->internalAddress, L_STRING_TO_C(uriParamName));
}
const string &Address::getUriParamValue (const string &uriParamName) const {
L_D();
const char *value = sal_address_get_uri_param(d->internalAddress, L_STRING_TO_C(uriParamName));
if (value) {
d->cache.uriParams[uriParamName] = value;
return d->cache.uriParams[uriParamName];
if (d->internalAddress) {
const char *value = sal_address_get_uri_param(d->internalAddress, L_STRING_TO_C(uriParamName));
if (value) {
d->cache.uriParams[uriParamName] = value;
return d->cache.uriParams[uriParamName];
}
}
return Utils::getEmptyConstRefObject<string>();
......
......@@ -1148,7 +1148,7 @@ void linphone_call_set_user_data (LinphoneCall *call, void *ud) {
LinphoneCall *linphone_call_new_outgoing (LinphoneCore *lc, const LinphoneAddress *from, const LinphoneAddress *to, const LinphoneCallParams *params, LinphoneProxyConfig *cfg) {
LinphoneCall *call = L_INIT(Call);
L_SET_CPP_PTR_FROM_C_OBJECT(call, LinphonePrivate::ObjectFactory::create<LinphonePrivate::Call>(call, lc, LinphoneCallOutgoing,
L_SET_CPP_PTR_FROM_C_OBJECT(call, make_shared<LinphonePrivate::Call>(call, lc, LinphoneCallOutgoing,
*L_GET_CPP_PTR_FROM_C_OBJECT(from), *L_GET_CPP_PTR_FROM_C_OBJECT(to),
cfg, nullptr, L_GET_CPP_PTR_FROM_C_OBJECT(params)));
call->currentParamsCache = linphone_call_params_new_for_wrapper();
......@@ -1160,7 +1160,7 @@ LinphoneCall *linphone_call_new_outgoing (LinphoneCore *lc, const LinphoneAddres
LinphoneCall *linphone_call_new_incoming (LinphoneCore *lc, const LinphoneAddress *from, const LinphoneAddress *to, LinphonePrivate::SalCallOp *op) {
LinphoneCall *call = L_INIT(Call);
L_SET_CPP_PTR_FROM_C_OBJECT(call, LinphonePrivate::ObjectFactory::create<LinphonePrivate::Call>(call, lc, LinphoneCallIncoming,
L_SET_CPP_PTR_FROM_C_OBJECT(call, make_shared<LinphonePrivate::Call>(call, lc, LinphoneCallIncoming,
*L_GET_CPP_PTR_FROM_C_OBJECT(from), *L_GET_CPP_PTR_FROM_C_OBJECT(to),
nullptr, op, nullptr));
call->currentParamsCache = linphone_call_params_new_for_wrapper();
......
......@@ -348,7 +348,7 @@ LinphoneChatRoom *_linphone_client_group_chat_room_new (LinphoneCore *core, cons
from = linphone_core_get_primary_contact(core);
LinphonePrivate::Address me(from);
LinphoneChatRoom *cr = L_INIT(ChatRoom);
L_SET_CPP_PTR_FROM_C_OBJECT(cr, LinphonePrivate::ObjectFactory::create<LinphonePrivate::ClientGroupChatRoom>(
L_SET_CPP_PTR_FROM_C_OBJECT(cr, make_shared<LinphonePrivate::ClientGroupChatRoom>(
core->cppCore, me, L_C_TO_STRING(uri), L_C_TO_STRING(subject))
);
L_GET_PRIVATE_FROM_C_OBJECT(cr)->setState(LinphonePrivate::ChatRoom::State::Instantiated);
......@@ -357,7 +357,7 @@ LinphoneChatRoom *_linphone_client_group_chat_room_new (LinphoneCore *core, cons
LinphoneChatRoom *_linphone_server_group_chat_room_new (LinphoneCore *core, LinphonePrivate::SalCallOp *op) {
LinphoneChatRoom *cr = L_INIT(ChatRoom);
L_SET_CPP_PTR_FROM_C_OBJECT(cr, LinphonePrivate::ObjectFactory::create<LinphonePrivate::ServerGroupChatRoom>(
L_SET_CPP_PTR_FROM_C_OBJECT(cr, make_shared<LinphonePrivate::ServerGroupChatRoom>(
core->cppCore,
op
));
......
......@@ -41,6 +41,7 @@ class LINPHONE_PUBLIC ChatMessage : public Object, public CoreAccessor {
friend class ChatRoom;
friend class ChatRoomPrivate;
friend class CpimChatMessageModifier;
friend class MainDbPrivate;
friend class RealTimeTextChatRoomPrivate;
friend class ServerGroupChatRoomPrivate;
......
......@@ -71,7 +71,7 @@ int BasicChatRoom::getNbParticipants () const {
list<shared_ptr<Participant>> BasicChatRoom::getParticipants () const {
L_D();
list<shared_ptr<Participant>> l;
l.push_back(ObjectFactory::create<Participant>(d->peerAddress));
l.push_back(make_shared<Participant>(d->peerAddress));
return l;
}
......
......@@ -480,7 +480,7 @@ shared_ptr<ChatMessage> ChatRoom::createMessage (const string &message) {
shared_ptr<ChatMessage> ChatRoom::createMessage () {
L_D();
shared_ptr<ChatMessage> chatMessage = ObjectFactory::create<ChatMessage>(getSharedFromThis());
shared_ptr<ChatMessage> chatMessage = make_shared<ChatMessage>(getSharedFromThis());
chatMessage->setToAddress(d->peerAddress);
chatMessage->setFromAddress(Address(linphone_core_get_identity(getCore()->getCCore())));
chatMessage->getPrivate()->setTime(ms_time(0));
......
......@@ -72,7 +72,7 @@ ClientGroupChatRoom::ClientGroupChatRoom (
const std::string &subject
) : ChatRoom(*new ClientGroupChatRoomPrivate, core, me), RemoteConference(core->getCCore(), me, nullptr) {
L_D_T(RemoteConference, dConference);
dConference->focus = ObjectFactory::create<Participant>(Address(uri));
dConference->focus = make_shared<Participant>(Address(uri));
RemoteConference::setSubject(subject);
}
......@@ -275,7 +275,7 @@ void ClientGroupChatRoom::onParticipantAdded (time_t tm, const Address &addr) {
return;
}
participant = ObjectFactory::create<Participant>(addr);
participant = make_shared<Participant>(addr);
dConference->participants.push_back(participant);
LinphoneChatRoom *cr = L_GET_C_BACK_PTR(this);
LinphoneChatRoomCbs *cbs = linphone_chat_room_get_callbacks(cr);
......
......@@ -171,7 +171,7 @@ int RealTimeTextChatRoom::getNbParticipants () const {
list<shared_ptr<Participant>> RealTimeTextChatRoom::getParticipants () const {
L_D();
list<shared_ptr<Participant>> l;
l.push_back(ObjectFactory::create<Participant>(d->peerAddress));
l.push_back(make_shared<Participant>(d->peerAddress));
return l;
}
......
......@@ -34,7 +34,7 @@ Conference::Conference (ConferencePrivate &p, LinphoneCore *core, const Address
d->mPublic = this;
d->core = core;
d->callListener = listener;
d->me = ObjectFactory::create<Participant>(myAddress);
d->me = make_shared<Participant>(myAddress);
}
Conference::~Conference () {
......
......@@ -41,7 +41,7 @@ void LocalConference::addParticipant (const Address &addr, const CallSessionPara
shared_ptr<Participant> participant = findParticipant(addr);
if (participant)
return;
participant = ObjectFactory::create<Participant>(addr);
participant = make_shared<Participant>(addr);
d->participants.push_back(participant);
if (!d->activeParticipant)
d->activeParticipant = participant;
......
......@@ -36,9 +36,9 @@ shared_ptr<CallSession> ParticipantPrivate::createSession (
const Conference &conference, const CallSessionParams *params, bool hasMedia, CallSessionListener *listener
) {
if (hasMedia && (!params || dynamic_cast<const MediaSessionParams *>(params))) {
session = ObjectFactory::create<MediaSession>(conference, params, listener);
session = make_shared<MediaSession>(conference, params, listener);
} else {
session = ObjectFactory::create<CallSession>(conference, params, listener);
session = make_shared<CallSession>(conference, params, listener);
}
return session;
}
......
......@@ -46,7 +46,7 @@ void RemoteConference::addParticipant (const Address &addr, const CallSessionPar
shared_ptr<Participant> participant = findParticipant(addr);
if (participant)
return;
participant = ObjectFactory::create<Participant>(addr);
participant = make_shared<Participant>(addr);
participant->getPrivate()->createSession(*this, params, hasMedia, this);
d->participants.push_back(participant);
if (!d->activeParticipant)
......
......@@ -35,23 +35,30 @@ public:
// -----------------------------------------------------------------------------
CoreAccessor::CoreAccessor (const shared_ptr<Core> &core) {
L_D();
d->core = core;
L_ASSERT(core);
mPrivate = new CoreAccessorPrivate();
mPrivate->core = core;
}
CoreAccessor::CoreAccessor (const shared_ptr<Core> &&core) {
L_D();
d->core = move(core);
L_ASSERT(core);
mPrivate = new CoreAccessorPrivate();
mPrivate->core = move(core);
}
CoreAccessor::~CoreAccessor () {}
CoreAccessor::~CoreAccessor () {
delete mPrivate;
}
shared_ptr<Core> CoreAccessor::getCore () const {
L_D();
shared_ptr<Core> core = d->core.lock();
if (!core)
if (!core) {
lWarning() << "Unable to get valid core instance.";
throw std::bad_weak_ptr();
}
return core;
}
......
......@@ -31,13 +31,15 @@ LINPHONE_BEGIN_NAMESPACE
class Core;
class CoreAccessorPrivate;
class CoreAccessor {
// Decorator to get a valid core instance.
LINPHONE_PUBLIC class CoreAccessor {
public:
CoreAccessor (const std::shared_ptr<Core> &core);
CoreAccessor (const std::shared_ptr<Core> &&core);
virtual ~CoreAccessor () = 0;
// Returns a valid core instance. Or throw one std::bad_weak_ptr exception if core is destroyed.
std::shared_ptr<Core> getCore () const;
private:
......
......@@ -39,6 +39,9 @@ LINPHONE_BEGIN_NAMESPACE
// -----------------------------------------------------------------------------
static inline Address getCleanedPeerAddress (const Address &peerAddress) {
if (!peerAddress.isValid())
return Address();
Address cleanedAddress = peerAddress;
cleanedAddress.clean();
cleanedAddress.setPort(0);
......@@ -50,8 +53,12 @@ static inline string resolveWorkaroundClientGroupChatRoomAddress (
const CorePrivate &corePrivate,
const Address &peerAddress
) {
const char *uri = linphone_core_get_conference_factory_uri(corePrivate.cCore);
if (!uri)
return "";
Address workaroundAddress = peerAddress;
workaroundAddress.setDomain(Address(linphone_core_get_conference_factory_uri(corePrivate.cCore)).getDomain());
workaroundAddress.setDomain(Address(uri).getDomain());
return workaroundAddress.asStringUriOnly();
}
......@@ -63,9 +70,9 @@ shared_ptr<ChatRoom> CorePrivate::createChatRoom (const Address &peerAddress, bo
shared_ptr<ChatRoom> chatRoom;
if (isRtt)
chatRoom = ObjectFactory::create<RealTimeTextChatRoom>(q->getSharedFromThis(), peerAddress);
chatRoom = make_shared<RealTimeTextChatRoom>(q->getSharedFromThis(), peerAddress);
else
chatRoom = ObjectFactory::create<BasicChatRoom>(q->getSharedFromThis(), peerAddress);
chatRoom = make_shared<BasicChatRoom>(q->getSharedFromThis(), peerAddress);
ChatRoomPrivate *dChatRoom = chatRoom->getPrivate();
insertChatRoom(chatRoom);
......
......@@ -32,20 +32,26 @@ using namespace std;
LINPHONE_BEGIN_NAMESPACE
Core::Core (LinphoneCore *cCore) : Object(*new CorePrivate) {
L_D();
Core::Core () : Object(*new CorePrivate) {}
shared_ptr<Core> Core::create (LinphoneCore *cCore) {
// Do not use `make_shared` => Private constructor.
shared_ptr<Core> core = shared_ptr<Core>(new Core);
CorePrivate * const d = core->getPrivate();
d->cCore = cCore;
d->mainDb.reset(new MainDb(this));
d->mainDb.reset(new MainDb(core->getSharedFromThis()));
AbstractDb::Backend backend;
string uri = L_C_TO_STRING(lp_config_get_string(linphone_core_get_config(d->cCore), "server", "db_uri", NULL));
string uri = L_C_TO_STRING(lp_config_get_string(linphone_core_get_config(d->cCore), "storage", "backend", nullptr));
if (!uri.empty())
backend = strcmp(lp_config_get_string(linphone_core_get_config(d->cCore), "server", "db_backend", NULL), "mysql") == 0
backend = strcmp(lp_config_get_string(linphone_core_get_config(d->cCore), "storage", "uri", nullptr), "mysql") == 0
? MainDb::Mysql
: MainDb::Sqlite3;
else {
backend = AbstractDb::Sqlite3;
uri = getDataPath() + LINPHONE_DB;
uri = core->getDataPath() + LINPHONE_DB;
}
lInfo() << "Opening " LINPHONE_DB " at: " << uri;
......@@ -54,6 +60,8 @@ Core::Core (LinphoneCore *cCore) : Object(*new CorePrivate) {
for (auto &chatRoom : d->mainDb->getChatRooms())
d->insertChatRoom(chatRoom);
return core;
}
LinphoneCore *Core::getCCore () const {
......
......@@ -42,7 +42,8 @@ class LINPHONE_PUBLIC Core : public Object {
public:
L_OVERRIDE_SHARED_FROM_THIS(Core);
Core (LinphoneCore *cCore);
// Return a new Core instance. Entry point of Linphone.
static std::shared_ptr<Core> create (LinphoneCore *cCore);
// ---------------------------------------------------------------------------
// C-Core.
......@@ -71,6 +72,8 @@ public:
static void deleteChatRoom (const std::shared_ptr<const ChatRoom> &chatRoom);
private:
Core ();
L_DECLARE_PRIVATE(Core);
L_DISABLE_COPY(Core);
};
......
......@@ -29,11 +29,8 @@
LINPHONE_BEGIN_NAMESPACE
class Content;
struct MessageEventReferences;
class MainDbPrivate : public AbstractDbPrivate {
public:
private:
// ---------------------------------------------------------------------------
// Low level API.
......@@ -108,8 +105,6 @@ private:
long long insertConferenceParticipantDeviceEvent (const std::shared_ptr<EventLog> &eventLog);
long long insertConferenceSubjectEvent (const std::shared_ptr<EventLog> &eventLog);
Core *core = nullptr;
L_DECLARE_PUBLIC(MainDb);
};
......
......@@ -26,6 +26,7 @@
#include "linphone/utils/utils.h"
#include "chat/chat-message/chat-message-p.h"
#include "chat/chat-room/chat-room.h"
#include "conference/participant.h"
#include "content/content-type.h"
......@@ -45,10 +46,7 @@ LINPHONE_BEGIN_NAMESPACE
// -----------------------------------------------------------------------------
MainDb::MainDb (Core *core) : AbstractDb(*new MainDbPrivate) {
L_D();
d->core = core;
}
MainDb::MainDb (const shared_ptr<Core> &core) : CoreAccessor(core), AbstractDb(*new MainDbPrivate) {}
#ifdef SOCI_ENABLED
......@@ -286,18 +284,49 @@ MainDb::MainDb (Core *core) : AbstractDb(*new MainDbPrivate) {
time_t date,
const string &peerAddress
) const {
L_Q();
shared_ptr<Core> core = q->getCore();
L_ASSERT(core);
// TODO: Avoid address creation.
shared_ptr<ChatRoom> chatRoom = core->findChatRoom(Address(peerAddress));
if (!chatRoom)
return nullptr;
string localSipAddress;
string remoteSipAddress;
string imdnMessageId;
int state;
int direction;
int isSecured;
soci::session *session = dbSession.getBackendSession<soci::session>();
*session << "SELECT event_id, type, date, local_sip_address.value, "
"remote_sip_address.value, imdn_message_id, state, direction, is_secured"
*session << "SELECT local_sip_address.value, remote_sip_address.value, imdn_message_id, state, direction, is_secured"
" FROM event, conference_chat_message_event, sip_address AS local_sip_address,"
" sip_address AS remote_sip_address"
" WHERE event_id = event.id"
" AND local_sip_address_id = local_sip_address.id"
" AND remote_sip_address_id = remote_sip_address.id"
" AND remote_sip_address.value = :peerAddress", soci::use(peerAddress);
" AND remote_sip_address.value = :peerAddress", soci::into(localSipAddress), soci::into(remoteSipAddress),
soci::into(imdnMessageId), soci::into(state), soci::into(direction), soci::into(isSecured),
soci::use(peerAddress);
// TODO: Create me.
shared_ptr<ChatMessage> chatMessage;
// TODO: Use cache, do not fetch the same message twice.
shared_ptr<ChatMessage> chatMessage = make_shared<ChatMessage>(chatRoom);
chatMessage->getPrivate()->setState(static_cast<ChatMessage::State>(state));
chatMessage->getPrivate()->setDirection(static_cast<ChatMessage::Direction>(direction));
chatMessage->setIsSecured(static_cast<bool>(isSecured));
if (direction == static_cast<int>(ChatMessage::Direction::Outgoing)) {
chatMessage->setFromAddress(Address(localSipAddress));
chatMessage->setToAddress(Address(remoteSipAddress));
} else {
chatMessage->setFromAddress(Address(remoteSipAddress));
chatMessage->setToAddress(Address(localSipAddress));
}
// TODO: Use cache.
return make_shared<ConferenceChatMessageEvent>(
......@@ -867,7 +896,7 @@ MainDb::MainDb (Core *core) : AbstractDb(*new MainDbPrivate) {
list<shared_ptr<EventLog>> MainDb::getConferenceNotifiedEvents (
const string &peerAddress,
unsigned int lastNotifyId
) {
) const {
static const string query = "SELECT id, type, date FROM event"
" WHERE id IN ("
" SELECT event_id FROM conference_notified_event WHERE event_id IN ("
......@@ -1126,6 +1155,9 @@ MainDb::MainDb (Core *core) : AbstractDb(*new MainDbPrivate) {
return list<shared_ptr<ChatRoom>>();
}
shared_ptr<Core> core = getCore();
L_ASSERT(core);
list<shared_ptr<ChatRoom>> chatRooms;
L_BEGIN_LOG_EXCEPTION
......@@ -1135,7 +1167,7 @@ MainDb::MainDb (Core *core) : AbstractDb(*new MainDbPrivate) {
soci::rowset<soci::row> rows = (session->prepare << query);
for (const auto &row : rows) {
string sipAddress = row.get<string>(0);
shared_ptr<ChatRoom> chatRoom = d->core->findChatRoom(Address(sipAddress));
shared_ptr<ChatRoom> chatRoom = core->findChatRoom(Address(sipAddress));
if (chatRoom) {
lInfo() << "Don't fetch chat room from database: `" << sipAddress << "`, it already exists.";
chatRooms.push_back(chatRoom);
......@@ -1155,10 +1187,10 @@ MainDb::MainDb (Core *core) : AbstractDb(*new MainDbPrivate) {
(void)lastNotifyId;
if (capabilities & static_cast<int>(ChatRoom::Capabilities::Basic)) {
chatRoom = d->core ? d->core->getPrivate()->createChatRoom(
chatRoom = core->getPrivate()->createChatRoom(
Address(sipAddress),
capabilities & static_cast<int>(ChatRoom::Capabilities::RealTimeText)
) : nullptr;
);
} else if (capabilities & static_cast<int>(ChatRoom::Capabilities::Conference)) {
// TODO: Set sip address and participants.
}
......@@ -1391,7 +1423,7 @@ MainDb::MainDb (Core *core) : AbstractDb(*new MainDbPrivate) {
list<shared_ptr<EventLog>> MainDb::getConferenceNotifiedEvents (
const string &peerAddress,
unsigned int notifyId
) {
) const {
return list<shared_ptr<EventLog>>();
}
......
......@@ -23,6 +23,7 @@
#include <list>
#include "abstract/abstract-db.h"
#include "core/core-accessor.h"
// =============================================================================
......@@ -34,7 +35,7 @@ class Core;
class EventLog;
class MainDbPrivate;
class LINPHONE_PUBLIC MainDb : public AbstractDb {
class LINPHONE_PUBLIC MainDb : public CoreAccessor, public AbstractDb {
public:
enum Filter {
NoFilter = 0x0,
......@@ -45,7 +46,7 @@ public:
typedef int FilterMask;
MainDb (Core *core);
MainDb (const std::shared_ptr<Core> &core);
// ---------------------------------------------------------------------------
// Generic.
......@@ -63,7 +64,7 @@ public:
std::list<std::shared_ptr<EventLog>> getConferenceNotifiedEvents (
const std::string &peerAddress,
unsigned int lastNotifyId
);
) const;
// ---------------------------------------------------------------------------
// Conference chat message events.
......
......@@ -31,11 +31,8 @@
LINPHONE_BEGIN_NAMESPACE
class ObjectPrivate : public BaseObjectPrivate {
friend class ObjectFactory;
private:
std::unordered_map<std::string, Variant> properties;
std::weak_ptr<Object> weak;
L_DECLARE_PUBLIC(Object);
};
......
......@@ -24,8 +24,6 @@
// =============================================================================
#define GET_SHARED_FROM_THIS_FATAL_ERROR "Object was not created with `ObjectFactory::create`."
using namespace std;
LINPHONE_BEGIN_NAMESPACE
......@@ -37,24 +35,13 @@ shared_ptr<Object> Object::getSharedFromThis () {
}
shared_ptr<const Object> Object::getSharedFromThis () const {
shared_ptr<const Object> object;
try {
object = getPrivate()->weak.lock();
if (!object)
lFatal() << GET_SHARED_FROM_THIS_FATAL_ERROR;
return shared_from_this();
} catch (const exception &) {
lFatal() << GET_SHARED_FROM_THIS_FATAL_ERROR;
lFatal() << "Object " << this << " was not created with make_shared.";
}
return object;
}
void ObjectFactory::setPublic (const shared_ptr<Object> &object) {
L_ASSERT(object);
ObjectPrivate *d = object->getPrivate();
d->mPublic = object.get();
d->weak = object;
return nullptr;
}
LINPHONE_END_NAMESPACE
......@@ -34,41 +34,26 @@ LINPHONE_BEGIN_NAMESPACE
* Supports properties and shared from this.
* Must be built with ObjectFactory.
*/
class LINPHONE_PUBLIC Object : public BaseObject, public PropertyContainer {
class LINPHONE_PUBLIC Object :
public std::enable_shared_from_this<Object>,
public BaseObject,
public PropertyContainer {
friend class ObjectFactory;
public:
virtual ~Object () = default;
protected:
explicit Object (ObjectPrivate &p);
std::shared_ptr<Object> getSharedFromThis ();
std::shared_ptr<const Object> getSharedFromThis () const;
protected:
explicit Object (ObjectPrivate &p);
private:
L_DECLARE_PRIVATE(Object);
L_DISABLE_COPY(Object);
};
class ObjectFactory {
public:
template<typename T, class ...Args>
static inline std::shared_ptr<T> create (Args &&...args) {
static_assert(std::is_base_of<Object, T>::value, "Not an object.");
std::shared_ptr<T> object = std::make_shared<T>(args...);
setPublic(object);
return object;
}
private:
ObjectFactory () = delete;
static void setPublic (const std::shared_ptr<Object> &object);
L_DISABLE_COPY(ObjectFactory);
};
LINPHONE_END_NAMESPACE
#endif // ifndef _OBJECT_H_