2012-08-06 17:00:38 -04:00
|
|
|
|
|
|
|
/*
|
|
|
|
* libretroshare/src/gxs: rsgenexchange.cc
|
|
|
|
*
|
|
|
|
* RetroShare Gxs exchange interface.
|
|
|
|
*
|
|
|
|
* Copyright 2012-2012 by Christopher Evi-Parker, Robert Fernie
|
|
|
|
*
|
|
|
|
* This library is free software; you can redistribute it and/or
|
|
|
|
* modify it under the terms of the GNU Library General Public
|
|
|
|
* License Version 2 as published by the Free Software Foundation.
|
|
|
|
*
|
|
|
|
* This library is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
|
|
|
* Library General Public License for more details.
|
|
|
|
*
|
|
|
|
* You should have received a copy of the GNU Library General Public
|
|
|
|
* License along with this library; if not, write to the Free Software
|
|
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
|
|
|
|
* USA.
|
|
|
|
*
|
|
|
|
* Please report all bugs and problems to "retroshare@lunamutt.com".
|
|
|
|
*
|
|
|
|
*/
|
|
|
|
|
2012-08-12 16:46:21 -04:00
|
|
|
#include <openssl/err.h>
|
|
|
|
#include <openssl/ssl.h>
|
|
|
|
#include <openssl/evp.h>
|
2012-08-19 18:15:37 -04:00
|
|
|
#include <openssl/rsa.h>
|
2012-08-12 16:46:21 -04:00
|
|
|
|
2012-05-21 18:07:43 -04:00
|
|
|
#include "rsgenexchange.h"
|
2012-08-12 16:46:21 -04:00
|
|
|
#include "gxssecurity.h"
|
2012-08-21 17:32:07 -04:00
|
|
|
#include "util/contentvalue.h"
|
2012-09-04 18:32:52 -04:00
|
|
|
#include "rsgxsflags.h"
|
2012-05-21 18:07:43 -04:00
|
|
|
|
2012-07-05 17:26:14 -04:00
|
|
|
RsGenExchange::RsGenExchange(RsGeneralDataService *gds,
|
2012-07-26 17:48:54 -04:00
|
|
|
RsNetworkExchangeService *ns, RsSerialType *serviceSerialiser, uint16_t servType)
|
|
|
|
: mGenMtx("GenExchange"), mDataStore(gds), mNetService(ns), mSerialiser(serviceSerialiser), mServType(servType)
|
2012-05-21 18:07:43 -04:00
|
|
|
{
|
2012-07-05 17:26:14 -04:00
|
|
|
|
2012-07-18 17:35:41 -04:00
|
|
|
mDataAccess = new RsGxsDataAccess(gds);
|
2012-07-05 17:26:14 -04:00
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
RsGenExchange::~RsGenExchange()
|
|
|
|
{
|
2012-07-26 17:48:54 -04:00
|
|
|
// need to destruct in a certain order (prob a bad thing!)
|
2012-07-05 17:26:14 -04:00
|
|
|
delete mNetService;
|
|
|
|
|
|
|
|
delete mDataAccess;
|
|
|
|
mDataAccess = NULL;
|
|
|
|
|
|
|
|
delete mDataStore;
|
|
|
|
mDataStore = NULL;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void RsGenExchange::tick()
|
|
|
|
{
|
2012-07-18 17:35:41 -04:00
|
|
|
mDataAccess->processRequests();
|
2012-07-26 17:48:54 -04:00
|
|
|
|
|
|
|
publishGrps();
|
|
|
|
|
|
|
|
publishMsgs();
|
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
processGrpMetaChanges();
|
|
|
|
|
|
|
|
processMsgMetaChanges();
|
|
|
|
|
2012-09-25 17:04:04 -04:00
|
|
|
processRecvdData();
|
|
|
|
|
|
|
|
if(!mNotifications.empty())
|
|
|
|
{
|
|
|
|
notifyChanges(mNotifications);
|
|
|
|
mNotifications.clear();
|
|
|
|
}
|
2012-08-06 17:00:38 -04:00
|
|
|
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
2012-08-18 06:01:35 -04:00
|
|
|
bool RsGenExchange::acknowledgeTokenMsg(const uint32_t& token,
|
2012-08-21 17:32:07 -04:00
|
|
|
RsGxsGrpMsgIdPair& msgId)
|
2012-08-18 06:01:35 -04:00
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
std::map<uint32_t, RsGxsGrpMsgIdPair >::iterator mit =
|
|
|
|
mMsgNotify.find(token);
|
2012-08-18 06:01:35 -04:00
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
if(mit == mMsgNotify.end())
|
|
|
|
{
|
|
|
|
return false;
|
|
|
|
}
|
2012-08-18 06:01:35 -04:00
|
|
|
|
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
msgId = mit->second;
|
|
|
|
|
|
|
|
// no dump token as client has ackowledged its completion
|
|
|
|
mDataAccess->disposeOfPublicToken(token);
|
2012-08-18 06:01:35 -04:00
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
bool RsGenExchange::acknowledgeTokenGrp(const uint32_t& token,
|
|
|
|
RsGxsGroupId& grpId)
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
|
|
|
std::map<uint32_t, RsGxsGroupId >::iterator mit =
|
2012-08-21 17:32:07 -04:00
|
|
|
mGrpNotify.find(token);
|
2012-08-18 06:01:35 -04:00
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
if(mit == mGrpNotify.end())
|
2012-08-18 06:01:35 -04:00
|
|
|
return false;
|
|
|
|
|
|
|
|
grpId = mit->second;
|
|
|
|
|
|
|
|
// no dump token as client has ackowledged its completion
|
|
|
|
mDataAccess->disposeOfPublicToken(token);
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2012-08-12 16:46:21 -04:00
|
|
|
void RsGenExchange::createGroup(RsNxsGrp *grp)
|
|
|
|
{
|
|
|
|
/* create Keys */
|
2012-08-18 06:01:35 -04:00
|
|
|
|
|
|
|
// admin keys
|
2012-08-12 16:46:21 -04:00
|
|
|
RSA *rsa_admin = RSA_generate_key(2048, 65537, NULL, NULL);
|
|
|
|
RSA *rsa_admin_pub = RSAPublicKey_dup(rsa_admin);
|
|
|
|
|
2012-08-18 06:01:35 -04:00
|
|
|
// publish keys
|
|
|
|
RSA *rsa_publish = RSA_generate_key(2048, 65537, NULL, NULL);
|
|
|
|
RSA *rsa_publish_pub = RSAPublicKey_dup(rsa_admin);
|
2012-08-12 16:46:21 -04:00
|
|
|
|
|
|
|
/* set keys */
|
2012-08-18 06:01:35 -04:00
|
|
|
RsTlvSecurityKey adminKey, privAdminKey;
|
|
|
|
|
|
|
|
/* set publish keys */
|
|
|
|
RsTlvSecurityKey pubKey, privPubKey;
|
|
|
|
|
2012-08-12 16:46:21 -04:00
|
|
|
GxsSecurity::setRSAPublicKey(adminKey, rsa_admin_pub);
|
2012-08-18 06:01:35 -04:00
|
|
|
GxsSecurity::setRSAPrivateKey(privAdminKey, rsa_admin);
|
|
|
|
|
|
|
|
GxsSecurity::setRSAPublicKey(pubKey, rsa_publish_pub);
|
|
|
|
GxsSecurity::setRSAPrivateKey(privPubKey, rsa_publish);
|
|
|
|
|
|
|
|
|
|
|
|
// for now all public
|
|
|
|
adminKey.keyFlags = RSTLV_KEY_DISTRIB_ADMIN | RSTLV_KEY_TYPE_PUBLIC_ONLY;
|
|
|
|
privAdminKey.keyFlags = RSTLV_KEY_DISTRIB_ADMIN | RSTLV_KEY_TYPE_FULL;
|
|
|
|
|
|
|
|
// for now all public
|
|
|
|
pubKey.keyFlags = RSTLV_KEY_DISTRIB_PUBLIC | RSTLV_KEY_TYPE_PUBLIC_ONLY;
|
|
|
|
privPubKey.keyFlags = RSTLV_KEY_DISTRIB_PRIVATE | RSTLV_KEY_TYPE_FULL;
|
2012-08-12 16:46:21 -04:00
|
|
|
|
|
|
|
adminKey.startTS = time(NULL);
|
|
|
|
adminKey.endTS = 0; /* no end */
|
|
|
|
RsGxsGrpMetaData* meta = grp->metaData;
|
2012-08-18 06:01:35 -04:00
|
|
|
|
|
|
|
/* add keys to grp */
|
|
|
|
|
2012-08-12 16:46:21 -04:00
|
|
|
meta->keys.keys[adminKey.keyId] = adminKey;
|
2012-08-18 06:01:35 -04:00
|
|
|
meta->keys.keys[privAdminKey.keyId] = privAdminKey;
|
|
|
|
meta->keys.keys[pubKey.keyId] = pubKey;
|
|
|
|
meta->keys.keys[privPubKey.keyId] = privPubKey;
|
|
|
|
|
2012-08-12 16:46:21 -04:00
|
|
|
meta->mGroupId = adminKey.keyId;
|
|
|
|
grp->grpId = meta->mGroupId;
|
|
|
|
|
|
|
|
adminKey.TlvClear();
|
2012-08-18 06:01:35 -04:00
|
|
|
privAdminKey.TlvClear();
|
|
|
|
privPubKey.TlvClear();
|
|
|
|
pubKey.TlvClear();
|
2012-08-12 16:46:21 -04:00
|
|
|
|
|
|
|
// free the private key for now, as it is not in use
|
|
|
|
RSA_free(rsa_admin);
|
2012-08-18 06:01:35 -04:00
|
|
|
RSA_free(rsa_admin_pub);
|
|
|
|
|
|
|
|
RSA_free(rsa_publish);
|
|
|
|
RSA_free(rsa_publish_pub);
|
|
|
|
}
|
|
|
|
|
|
|
|
bool RsGenExchange::createMessage(RsNxsMsg* msg)
|
|
|
|
{
|
|
|
|
const RsGxsGroupId& id = msg->grpId;
|
|
|
|
|
|
|
|
std::map<RsGxsGroupId, RsGxsGrpMetaData*> metaMap;
|
|
|
|
|
|
|
|
metaMap.insert(std::make_pair(id, (RsGxsGrpMetaData*)(NULL)));
|
|
|
|
mDataStore->retrieveGxsGrpMetaData(metaMap);
|
|
|
|
bool ok = true;
|
2012-08-19 18:15:37 -04:00
|
|
|
RSA* rsa_pub = NULL;
|
2012-08-18 06:01:35 -04:00
|
|
|
|
|
|
|
if(!metaMap[id])
|
|
|
|
{
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
|
|
|
|
// get publish key
|
|
|
|
RsGxsGrpMetaData* meta = metaMap[id];
|
|
|
|
|
|
|
|
// public and shared is publish key
|
|
|
|
RsTlvSecurityKeySet& keys = meta->keys;
|
|
|
|
RsTlvSecurityKey* pubKey;
|
|
|
|
|
|
|
|
std::map<std::string, RsTlvSecurityKey>::iterator mit =
|
|
|
|
keys.keys.begin(), mit_end = keys.keys.end();
|
|
|
|
bool pub_key_found = false;
|
|
|
|
for(; mit != mit_end; mit++)
|
|
|
|
{
|
|
|
|
|
2012-08-19 18:15:37 -04:00
|
|
|
pub_key_found = mit->second.keyFlags & (RSTLV_KEY_DISTRIB_PRIVATE | RSTLV_KEY_TYPE_FULL);
|
2012-08-18 06:01:35 -04:00
|
|
|
if(pub_key_found)
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
if(pub_key_found)
|
|
|
|
{
|
|
|
|
pubKey = &(mit->second);
|
2012-08-19 18:15:37 -04:00
|
|
|
rsa_pub = GxsSecurity::extractPrivateKey(*pubKey);
|
2012-08-18 06:01:35 -04:00
|
|
|
EVP_PKEY *key_pub = EVP_PKEY_new();
|
|
|
|
EVP_PKEY_assign_RSA(key_pub, rsa_pub);
|
|
|
|
|
|
|
|
/* calc and check signature */
|
|
|
|
EVP_MD_CTX *mdctx = EVP_MD_CTX_create();
|
|
|
|
|
|
|
|
ok = EVP_SignInit(mdctx, EVP_sha1()) == 1;
|
|
|
|
ok = EVP_SignUpdate(mdctx, msg->msg.bin_data, msg->msg.bin_len) == 1;
|
|
|
|
|
|
|
|
unsigned int siglen = EVP_PKEY_size(key_pub);
|
|
|
|
unsigned char sigbuf[siglen];
|
|
|
|
ok = EVP_SignFinal(mdctx, sigbuf, &siglen, key_pub) == 1;
|
|
|
|
|
|
|
|
RsGxsMsgMetaData &meta = *(msg->metaData);
|
|
|
|
meta.pubSign.signData.setBinData(sigbuf, siglen);
|
|
|
|
meta.pubSign.keyId = pubKey->keyId;
|
|
|
|
|
|
|
|
msg->metaData->mMsgId = msg->msgId = GxsSecurity::getBinDataSign(sigbuf, siglen);
|
|
|
|
|
|
|
|
// clean up
|
|
|
|
EVP_MD_CTX_destroy(mdctx);
|
2012-08-19 18:15:37 -04:00
|
|
|
//RSA_free(rsa_pub);
|
2012-08-18 06:01:35 -04:00
|
|
|
EVP_PKEY_free(key_pub);
|
2012-08-19 18:15:37 -04:00
|
|
|
// no need to free rsa key as evp key is considered parent key by SSL
|
2012-08-18 06:01:35 -04:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
ok = false;
|
|
|
|
}
|
|
|
|
|
|
|
|
delete meta;
|
|
|
|
}
|
|
|
|
|
|
|
|
return ok;
|
2012-08-12 16:46:21 -04:00
|
|
|
}
|
|
|
|
|
2012-07-05 17:26:14 -04:00
|
|
|
|
2012-07-22 17:38:15 -04:00
|
|
|
bool RsGenExchange::getGroupList(const uint32_t &token, std::list<RsGxsGroupId> &groupIds)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
2012-07-22 17:38:15 -04:00
|
|
|
return mDataAccess->getGroupList(token, groupIds);
|
2012-07-26 17:48:54 -04:00
|
|
|
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
bool RsGenExchange::getMsgList(const uint32_t &token,
|
2012-07-22 17:38:15 -04:00
|
|
|
GxsMsgIdResult &msgIds)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
2012-07-22 17:38:15 -04:00
|
|
|
return mDataAccess->getMsgList(token, msgIds);
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
bool RsGenExchange::getGroupMeta(const uint32_t &token, std::list<RsGroupMetaData> &groupInfo)
|
|
|
|
{
|
2012-07-22 17:38:15 -04:00
|
|
|
std::list<RsGxsGrpMetaData*> metaL;
|
|
|
|
bool ok = mDataAccess->getGroupSummary(token, metaL);
|
|
|
|
|
2012-07-26 17:48:54 -04:00
|
|
|
std::list<RsGxsGrpMetaData*>::iterator lit = metaL.begin();
|
2012-07-28 16:01:30 -04:00
|
|
|
RsGroupMetaData m;
|
2012-07-26 17:48:54 -04:00
|
|
|
for(; lit != metaL.end(); lit++)
|
|
|
|
{
|
2012-07-28 16:01:30 -04:00
|
|
|
RsGxsGrpMetaData& gMeta = *(*lit);
|
|
|
|
m = gMeta;
|
2012-07-26 17:48:54 -04:00
|
|
|
groupInfo.push_back(m);
|
2012-07-28 16:01:30 -04:00
|
|
|
delete (*lit);
|
2012-07-26 17:48:54 -04:00
|
|
|
}
|
|
|
|
|
2012-07-22 17:38:15 -04:00
|
|
|
return ok;
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
2012-07-22 17:38:15 -04:00
|
|
|
|
2012-07-05 17:26:14 -04:00
|
|
|
bool RsGenExchange::getMsgMeta(const uint32_t &token,
|
2012-07-22 17:38:15 -04:00
|
|
|
GxsMsgMetaMap &msgInfo)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
2012-07-22 17:38:15 -04:00
|
|
|
std::list<RsGxsMsgMetaData*> metaL;
|
|
|
|
GxsMsgMetaResult result;
|
|
|
|
bool ok = mDataAccess->getMsgSummary(token, result);
|
|
|
|
|
|
|
|
GxsMsgMetaResult::iterator mit = result.begin();
|
|
|
|
|
|
|
|
for(; mit != result.end(); mit++)
|
|
|
|
{
|
|
|
|
std::vector<RsGxsMsgMetaData*>& metaV = mit->second;
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
msgInfo[mit->first] = std::vector<RsMsgMetaData>();
|
|
|
|
std::vector<RsMsgMetaData>& msgInfoV = msgInfo[mit->first];
|
2012-07-05 17:26:14 -04:00
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
std::vector<RsGxsMsgMetaData*>::iterator vit = metaV.begin();
|
|
|
|
RsMsgMetaData meta;
|
2012-07-22 17:38:15 -04:00
|
|
|
for(; vit != metaV.end(); vit++)
|
|
|
|
{
|
2012-08-06 17:00:38 -04:00
|
|
|
RsGxsMsgMetaData& m = *(*vit);
|
|
|
|
meta = m;
|
|
|
|
msgInfoV.push_back(meta);
|
2012-07-22 17:38:15 -04:00
|
|
|
delete *vit;
|
|
|
|
}
|
2012-08-06 17:00:38 -04:00
|
|
|
metaV.clear();
|
2012-07-22 17:38:15 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
return ok;
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
2012-08-12 16:46:21 -04:00
|
|
|
bool RsGenExchange::getGroupData(const uint32_t &token, std::vector<RsGxsGrpItem *>& grpItem)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
2012-07-22 17:38:15 -04:00
|
|
|
|
|
|
|
std::list<RsNxsGrp*> nxsGrps;
|
|
|
|
bool ok = mDataAccess->getGroupData(token, nxsGrps);
|
|
|
|
|
|
|
|
std::list<RsNxsGrp*>::iterator lit = nxsGrps.begin();
|
|
|
|
|
2012-08-19 18:15:37 -04:00
|
|
|
if(ok)
|
2012-07-22 17:38:15 -04:00
|
|
|
{
|
|
|
|
for(; lit != nxsGrps.end(); lit++)
|
|
|
|
{
|
2012-07-26 17:48:54 -04:00
|
|
|
RsTlvBinaryData& data = (*lit)->grp;
|
2012-07-22 17:38:15 -04:00
|
|
|
RsItem* item = mSerialiser->deserialise(data.bin_data, &data.bin_len);
|
2012-08-06 17:00:38 -04:00
|
|
|
|
2012-08-19 18:15:37 -04:00
|
|
|
if(item != NULL)
|
|
|
|
{
|
2012-08-06 17:00:38 -04:00
|
|
|
RsGxsGrpItem* gItem = dynamic_cast<RsGxsGrpItem*>(item);
|
|
|
|
gItem->meta = *((*lit)->metaData);
|
|
|
|
grpItem.push_back(gItem);
|
|
|
|
delete *lit;
|
|
|
|
}
|
2012-07-22 17:38:15 -04:00
|
|
|
}
|
|
|
|
}
|
|
|
|
return ok;
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
bool RsGenExchange::getMsgData(const uint32_t &token,
|
2012-07-22 17:38:15 -04:00
|
|
|
GxsMsgDataMap &msgItems)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
2012-07-22 17:38:15 -04:00
|
|
|
NxsMsgDataResult msgResult;
|
|
|
|
bool ok = mDataAccess->getMsgData(token, msgResult);
|
|
|
|
NxsMsgDataResult::iterator mit = msgResult.begin();
|
|
|
|
|
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
for(; mit != msgResult.end(); mit++)
|
|
|
|
{
|
|
|
|
std::vector<RsGxsMsgItem*> gxsMsgItems;
|
2012-07-26 17:48:54 -04:00
|
|
|
const RsGxsGroupId& grpId = mit->first;
|
2012-07-22 17:38:15 -04:00
|
|
|
std::vector<RsNxsMsg*>& nxsMsgsV = mit->second;
|
|
|
|
std::vector<RsNxsMsg*>::iterator vit
|
|
|
|
= nxsMsgsV.begin();
|
|
|
|
for(; vit != nxsMsgsV.end(); vit++)
|
|
|
|
{
|
|
|
|
RsNxsMsg*& msg = *vit;
|
|
|
|
|
|
|
|
RsItem* item = mSerialiser->deserialise(msg->msg.bin_data,
|
|
|
|
&msg->msg.bin_len);
|
|
|
|
RsGxsMsgItem* mItem = dynamic_cast<RsGxsMsgItem*>(item);
|
2012-08-06 17:00:38 -04:00
|
|
|
mItem->meta = *((*vit)->metaData); // get meta info from nxs msg
|
2012-07-22 17:38:15 -04:00
|
|
|
gxsMsgItems.push_back(mItem);
|
|
|
|
delete msg;
|
|
|
|
}
|
|
|
|
msgItems[grpId] = gxsMsgItems;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return ok;
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2012-07-28 16:01:30 -04:00
|
|
|
RsTokenServiceV2* RsGenExchange::getTokenService()
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
|
|
|
return mDataAccess;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
void RsGenExchange::notifyNewGroups(std::vector<RsNxsGrp *> &groups)
|
|
|
|
{
|
|
|
|
std::vector<RsNxsGrp*>::iterator vit = groups.begin();
|
|
|
|
|
|
|
|
// store these for tick() to pick them up
|
|
|
|
for(; vit != groups.end(); vit++)
|
|
|
|
mReceivedGrps.push_back(*vit);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
void RsGenExchange::notifyNewMessages(std::vector<RsNxsMsg *>& messages)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
|
|
|
std::vector<RsNxsMsg*>::iterator vit = messages.begin();
|
|
|
|
|
|
|
|
// store these for tick() to pick them up
|
|
|
|
for(; vit != messages.end(); vit++)
|
|
|
|
mReceivedMsgs.push_back(*vit);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
void RsGenExchange::publishGroup(uint32_t& token, RsGxsGrpItem *grpItem)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
|
|
|
|
2012-08-18 06:01:35 -04:00
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
|
|
|
token = mDataAccess->generatePublicToken();
|
|
|
|
mGrpsToPublish.insert(std::make_pair(token, grpItem));
|
2012-08-21 17:32:07 -04:00
|
|
|
}
|
2012-07-26 17:48:54 -04:00
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
void RsGenExchange::publishMsg(uint32_t& token, RsGxsMsgItem *msgItem)
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
|
|
|
token = mDataAccess->generatePublicToken();
|
|
|
|
mMsgsToPublish.insert(std::make_pair(token, msgItem));
|
2012-07-05 17:26:14 -04:00
|
|
|
}
|
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
void RsGenExchange::setGroupSubscribeFlag(uint32_t& token, const RsGxsGroupId& grpId, const uint32_t& flag)
|
2012-07-05 17:26:14 -04:00
|
|
|
{
|
2012-08-21 17:32:07 -04:00
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
token = mDataAccess->generatePublicToken();
|
2012-07-26 17:48:54 -04:00
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
GrpLocMetaData g;
|
|
|
|
g.grpId = grpId;
|
|
|
|
g.val.put(RsGeneralDataService::GRP_META_SUBSCRIBE_FLAG, (int32_t)flag);
|
|
|
|
mGrpLocMetaMap.insert(std::make_pair(token, g));
|
|
|
|
}
|
2012-07-26 17:48:54 -04:00
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
void RsGenExchange::setGroupStatusFlag(uint32_t& token, const RsGxsGroupId& grpId, const uint32_t& status)
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
token = mDataAccess->generatePublicToken();
|
2012-08-18 06:01:35 -04:00
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
GrpLocMetaData g;
|
|
|
|
g.grpId = grpId;
|
|
|
|
g.val.put(RsGeneralDataService::GRP_META_STATUS, (int32_t)status);
|
|
|
|
mGrpLocMetaMap.insert(std::make_pair(token, g));
|
2012-07-26 17:48:54 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2012-08-21 17:32:07 -04:00
|
|
|
void RsGenExchange::setGroupServiceString(uint32_t& token, const RsGxsGroupId& grpId, const std::string& servString)
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
token = mDataAccess->generatePublicToken();
|
|
|
|
|
|
|
|
GrpLocMetaData g;
|
|
|
|
g.grpId = grpId;
|
|
|
|
g.val.put(RsGeneralDataService::GRP_META_SERV_STRING, servString);
|
|
|
|
mGrpLocMetaMap.insert(std::make_pair(token, g));
|
|
|
|
}
|
|
|
|
|
|
|
|
void RsGenExchange::setMsgStatusFlag(uint32_t& token, const RsGxsGrpMsgIdPair& msgId, const uint32_t& status)
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
token = mDataAccess->generatePublicToken();
|
|
|
|
|
|
|
|
MsgLocMetaData m;
|
|
|
|
m.val.put(RsGeneralDataService::MSG_META_STATUS, (int32_t)status);
|
|
|
|
m.msgId = msgId;
|
|
|
|
mMsgLocMetaMap.insert(std::make_pair(token, m));
|
|
|
|
}
|
|
|
|
|
|
|
|
void RsGenExchange::setMsgServiceString(uint32_t& token, const RsGxsGrpMsgIdPair& msgId, const std::string& servString )
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
token = mDataAccess->generatePublicToken();
|
|
|
|
|
|
|
|
MsgLocMetaData m;
|
|
|
|
m.val.put(RsGeneralDataService::MSG_META_SERV_STRING, servString);
|
|
|
|
m.msgId = msgId;
|
|
|
|
mMsgLocMetaMap.insert(std::make_pair(token, m));
|
|
|
|
}
|
|
|
|
|
|
|
|
void RsGenExchange::processMsgMetaChanges()
|
|
|
|
{
|
|
|
|
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
|
|
|
std::map<uint32_t, MsgLocMetaData>::iterator mit = mMsgLocMetaMap.begin(),
|
|
|
|
mit_end = mMsgLocMetaMap.end();
|
|
|
|
|
|
|
|
for(; mit != mit_end; mit++)
|
|
|
|
{
|
|
|
|
MsgLocMetaData& m = mit->second;
|
|
|
|
bool ok = mDataStore->updateMessageMetaData(m) == 1;
|
|
|
|
uint32_t token = mit->first;
|
|
|
|
|
|
|
|
if(ok)
|
|
|
|
{
|
2012-09-25 17:04:04 -04:00
|
|
|
mDataAccess->updatePublicRequestStatus(token, RsTokenServiceV2::GXS_REQUEST_V2_STATUS_COMPLETE);
|
2012-08-21 17:32:07 -04:00
|
|
|
}else
|
|
|
|
{
|
2012-09-25 17:04:04 -04:00
|
|
|
mDataAccess->updatePublicRequestStatus(token, RsTokenServiceV2::GXS_REQUEST_V2_STATUS_FAILED);
|
2012-08-21 17:32:07 -04:00
|
|
|
}
|
|
|
|
mMsgNotify.insert(std::make_pair(token, m.msgId));
|
|
|
|
}
|
|
|
|
|
|
|
|
mMsgLocMetaMap.clear();
|
|
|
|
}
|
|
|
|
|
|
|
|
void RsGenExchange::processGrpMetaChanges()
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
|
|
|
std::map<uint32_t, GrpLocMetaData>::iterator mit = mGrpLocMetaMap.begin(),
|
|
|
|
mit_end = mGrpLocMetaMap.end();
|
|
|
|
|
|
|
|
for(; mit != mit_end; mit++)
|
|
|
|
{
|
|
|
|
GrpLocMetaData& g = mit->second;
|
|
|
|
uint32_t token = mit->first;
|
|
|
|
bool ok = mDataStore->updateGroupMetaData(g) == 1;
|
|
|
|
|
|
|
|
if(ok)
|
|
|
|
{
|
2012-09-25 17:04:04 -04:00
|
|
|
mDataAccess->updatePublicRequestStatus(token, RsTokenServiceV2::GXS_REQUEST_V2_STATUS_COMPLETE);
|
2012-08-21 17:32:07 -04:00
|
|
|
}else
|
|
|
|
{
|
2012-09-25 17:04:04 -04:00
|
|
|
mDataAccess->updatePublicRequestStatus(token, RsTokenServiceV2::GXS_REQUEST_V2_STATUS_FAILED);
|
2012-08-21 17:32:07 -04:00
|
|
|
}
|
|
|
|
mGrpNotify.insert(std::make_pair(token, g.grpId));
|
|
|
|
}
|
|
|
|
|
|
|
|
mGrpLocMetaMap.clear();
|
|
|
|
}
|
|
|
|
|
2012-07-26 17:48:54 -04:00
|
|
|
void RsGenExchange::publishMsgs()
|
|
|
|
{
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
2012-08-18 06:01:35 -04:00
|
|
|
std::map<uint32_t, RsGxsMsgItem*>::iterator mit = mMsgsToPublish.begin();
|
2012-07-26 17:48:54 -04:00
|
|
|
|
2012-08-19 18:15:37 -04:00
|
|
|
for(; mit != mMsgsToPublish.end(); mit++)
|
2012-07-26 17:48:54 -04:00
|
|
|
{
|
|
|
|
|
|
|
|
RsNxsMsg* msg = new RsNxsMsg(mServType);
|
2012-08-18 06:01:35 -04:00
|
|
|
RsGxsMsgItem* msgItem = mit->second;
|
2012-08-19 18:15:37 -04:00
|
|
|
|
|
|
|
msg->grpId = msgItem->meta.mGroupId;
|
|
|
|
|
2012-07-26 17:48:54 -04:00
|
|
|
uint32_t size = mSerialiser->size(msgItem);
|
|
|
|
char mData[size];
|
|
|
|
bool ok = mSerialiser->serialise(msgItem, mData, &size);
|
|
|
|
|
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
msg->metaData = new RsGxsMsgMetaData();
|
2012-08-19 18:15:37 -04:00
|
|
|
msg->msg.setBinData(mData, size);
|
2012-08-25 11:48:55 -04:00
|
|
|
*(msg->metaData) = msgItem->meta;
|
2012-08-19 18:15:37 -04:00
|
|
|
size = msg->metaData->serial_size();
|
|
|
|
char metaDataBuff[size];
|
|
|
|
|
|
|
|
msg->metaData->serialise(metaDataBuff, &size);
|
|
|
|
msg->meta.setBinData(metaDataBuff, size);
|
|
|
|
|
2012-08-18 06:01:35 -04:00
|
|
|
ok = createMessage(msg);
|
2012-07-26 17:48:54 -04:00
|
|
|
|
2012-08-25 11:48:55 -04:00
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
msg->metaData->mPublishTs = time(NULL);
|
|
|
|
|
|
|
|
// empty orig msg id means this is the original
|
|
|
|
// msg
|
|
|
|
// TODO: a non empty msgid means one should at least
|
|
|
|
// have the msg on disk, after which this msg is signed
|
|
|
|
// based on the security settings
|
|
|
|
// public grp (sign by grp public pub key, private/id: signed by
|
|
|
|
// id
|
|
|
|
if(msg->metaData->mOrigMsgId.empty())
|
|
|
|
{
|
|
|
|
msg->metaData->mOrigMsgId = msg->metaData->mMsgId;
|
|
|
|
}
|
|
|
|
|
2012-08-19 18:15:37 -04:00
|
|
|
ok = mDataAccess->addMsgData(msg);
|
2012-08-25 11:48:55 -04:00
|
|
|
}
|
2012-08-18 06:01:35 -04:00
|
|
|
|
2012-08-19 18:15:37 -04:00
|
|
|
// add to published to allow acknowledgement
|
2012-08-21 17:32:07 -04:00
|
|
|
mMsgNotify.insert(std::make_pair(mit->first, std::make_pair(msg->grpId, msg->msgId)));
|
2012-09-25 17:04:04 -04:00
|
|
|
mDataAccess->updatePublicRequestStatus(mit->first, RsTokenServiceV2::GXS_REQUEST_V2_STATUS_COMPLETE);
|
2012-07-26 17:48:54 -04:00
|
|
|
}
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
// if addition failed then delete nxs message
|
2012-07-26 17:48:54 -04:00
|
|
|
if(!ok)
|
|
|
|
{
|
|
|
|
#ifdef GEN_EXCH_DEBUG
|
2012-08-18 06:01:35 -04:00
|
|
|
std::cerr << "RsGenExchange::publishMsgs() failed to publish msg " << std::endl;
|
2012-07-26 17:48:54 -04:00
|
|
|
#endif
|
2012-08-21 17:32:07 -04:00
|
|
|
mMsgNotify.insert(std::make_pair(mit->first, std::make_pair(RsGxsGroupId(""), RsGxsMessageId(""))));
|
2012-07-26 17:48:54 -04:00
|
|
|
delete msg;
|
|
|
|
continue;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
delete msgItem; // delete msg item as we're done with it
|
2012-07-26 17:48:54 -04:00
|
|
|
}
|
2012-08-06 17:00:38 -04:00
|
|
|
|
|
|
|
// clear msg list as we're done publishing them and entries
|
|
|
|
// are invalid
|
|
|
|
mMsgsToPublish.clear();
|
2012-07-26 17:48:54 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
void RsGenExchange::publishGrps()
|
|
|
|
{
|
|
|
|
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
2012-08-18 06:01:35 -04:00
|
|
|
std::map<uint32_t, RsGxsGrpItem*>::iterator mit = mGrpsToPublish.begin();
|
2012-07-26 17:48:54 -04:00
|
|
|
|
2012-08-18 06:01:35 -04:00
|
|
|
for(; mit != mGrpsToPublish.end(); mit++)
|
2012-07-26 17:48:54 -04:00
|
|
|
{
|
|
|
|
|
|
|
|
RsNxsGrp* grp = new RsNxsGrp(mServType);
|
2012-08-18 06:01:35 -04:00
|
|
|
RsGxsGrpItem* grpItem = mit->second;
|
2012-07-26 17:48:54 -04:00
|
|
|
uint32_t size = mSerialiser->size(grpItem);
|
|
|
|
|
|
|
|
char gData[size];
|
|
|
|
bool ok = mSerialiser->serialise(grpItem, gData, &size);
|
2012-08-12 16:46:21 -04:00
|
|
|
grp->grp.setBinData(gData, size);
|
2012-07-26 17:48:54 -04:00
|
|
|
|
|
|
|
if(ok)
|
|
|
|
{
|
2012-08-26 10:02:47 -04:00
|
|
|
grp->metaData = new RsGxsGrpMetaData();
|
|
|
|
grpItem->meta.mPublishTs = time(NULL);
|
|
|
|
*(grp->metaData) = grpItem->meta;
|
2012-09-25 17:04:04 -04:00
|
|
|
grp->metaData->mSubscribeFlags = GXS_SERV::GROUP_SUBSCRIBE_ADMIN;
|
2012-08-26 10:02:47 -04:00
|
|
|
createGroup(grp);
|
|
|
|
size = grp->metaData->serial_size();
|
|
|
|
char mData[size];
|
|
|
|
grp->metaData->mGroupId = grp->grpId;
|
|
|
|
ok = grp->metaData->serialise(mData, size);
|
|
|
|
grp->meta.setBinData(mData, size);
|
|
|
|
|
|
|
|
ok = mDataAccess->addGroupData(grp);
|
|
|
|
|
|
|
|
// add to published to allow acknowledgement
|
|
|
|
mGrpNotify.insert(std::make_pair(mit->first, grp->grpId));
|
2012-09-25 17:04:04 -04:00
|
|
|
mDataAccess->updatePublicRequestStatus(mit->first, RsTokenServiceV2::GXS_REQUEST_V2_STATUS_COMPLETE);
|
2012-07-26 17:48:54 -04:00
|
|
|
}
|
|
|
|
|
|
|
|
if(!ok)
|
|
|
|
{
|
|
|
|
|
|
|
|
#ifdef GEN_EXCH_DEBUG
|
|
|
|
std::cerr << "RsGenExchange::publishGrps() failed to publish grp " << std::endl;
|
|
|
|
#endif
|
|
|
|
delete grp;
|
2012-08-18 06:01:35 -04:00
|
|
|
|
|
|
|
// add to published to allow acknowledgement, grpid is empty as grp creation failed
|
2012-08-21 17:32:07 -04:00
|
|
|
mGrpNotify.insert(std::make_pair(mit->first, RsGxsGroupId("")));
|
2012-09-25 17:04:04 -04:00
|
|
|
mDataAccess->updatePublicRequestStatus(mit->first, RsTokenServiceV2::GXS_REQUEST_V2_STATUS_FAILED);
|
2012-07-26 17:48:54 -04:00
|
|
|
continue;
|
|
|
|
}
|
|
|
|
|
|
|
|
delete grpItem;
|
|
|
|
}
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
// clear grp list as we're done publishing them and entries
|
|
|
|
// are invalid
|
|
|
|
mGrpsToPublish.clear();
|
|
|
|
}
|
2012-08-19 18:15:37 -04:00
|
|
|
|
2012-09-25 17:04:04 -04:00
|
|
|
void RsGenExchange::createDummyGroup(RsGxsGrpItem *grpItem)
|
|
|
|
{
|
|
|
|
|
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
|
|
|
|
|
|
|
RsNxsGrp* grp = new RsNxsGrp(mServType);
|
|
|
|
uint32_t size = mSerialiser->size(grpItem);
|
|
|
|
char gData[size];
|
|
|
|
bool ok = mSerialiser->serialise(grpItem, gData, &size);
|
|
|
|
grp->grp.setBinData(gData, size);
|
|
|
|
|
|
|
|
if(ok)
|
|
|
|
{
|
|
|
|
grp->metaData = new RsGxsGrpMetaData();
|
|
|
|
grpItem->meta.mPublishTs = time(NULL);
|
|
|
|
*(grp->metaData) = grpItem->meta;
|
|
|
|
grp->metaData->mSubscribeFlags = ~GXS_SERV::GROUP_SUBSCRIBE_MASK;
|
|
|
|
createGroup(grp);
|
|
|
|
size = grp->metaData->serial_size();
|
|
|
|
char mData[size];
|
|
|
|
grp->metaData->mGroupId = grp->grpId;
|
|
|
|
ok = grp->metaData->serialise(mData, size);
|
|
|
|
grp->meta.setBinData(mData, size);
|
|
|
|
|
|
|
|
ok = mDataAccess->addGroupData(grp);
|
|
|
|
}
|
|
|
|
|
|
|
|
if(!ok)
|
|
|
|
{
|
|
|
|
|
|
|
|
#ifdef GEN_EXCH_DEBUG
|
|
|
|
std::cerr << "RsGenExchange::createDummyGroup(); failed to publish grp " << std::endl;
|
|
|
|
#endif
|
|
|
|
delete grp;
|
|
|
|
}
|
|
|
|
|
|
|
|
delete grpItem;
|
|
|
|
}
|
|
|
|
|
2012-08-19 18:15:37 -04:00
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
void RsGenExchange::processRecvdData()
|
|
|
|
{
|
2012-09-25 17:04:04 -04:00
|
|
|
processRecvdGroups();
|
2012-05-21 18:07:43 -04:00
|
|
|
}
|
2012-07-26 17:48:54 -04:00
|
|
|
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
void RsGenExchange::processRecvdMessages()
|
|
|
|
{
|
|
|
|
}
|
2012-07-26 17:48:54 -04:00
|
|
|
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
void RsGenExchange::processRecvdGroups()
|
|
|
|
{
|
2012-09-25 17:04:04 -04:00
|
|
|
RsStackMutex stack(mGenMtx);
|
|
|
|
|
|
|
|
std::vector<RsNxsGrp*>::iterator vit = mReceivedGrps.begin();
|
|
|
|
std::map<RsNxsGrp*, RsGxsGrpMetaData*> grps;
|
|
|
|
|
|
|
|
std::list<RsGxsGroupId> grpIds;
|
|
|
|
|
|
|
|
for(; vit != mReceivedGrps.end(); vit++)
|
|
|
|
{
|
|
|
|
RsNxsGrp* grp = *vit;
|
|
|
|
RsGxsGrpMetaData* meta = new RsGxsGrpMetaData();
|
|
|
|
meta->deserialise(grp->meta.bin_data, grp->meta.bin_len);
|
|
|
|
grps.insert(std::make_pair(grp, meta));
|
|
|
|
|
|
|
|
grpIds.push_back(grp->grpId);
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
if(!grpIds.empty())
|
|
|
|
{
|
|
|
|
RsGxsGroupChange* c = new RsGxsGroupChange();
|
|
|
|
c->grpIdList = grpIds;
|
|
|
|
mNotifications.push_back(c);
|
|
|
|
mDataStore->storeGroup(grps);
|
|
|
|
}
|
|
|
|
|
|
|
|
mReceivedGrps.clear();
|
|
|
|
|
2012-08-06 17:00:38 -04:00
|
|
|
}
|
2012-07-26 17:48:54 -04:00
|
|
|
|