diff options
author | Rajith Muditha Attapattu <rajith@apache.org> | 2011-05-27 15:44:23 +0000 |
---|---|---|
committer | Rajith Muditha Attapattu <rajith@apache.org> | 2011-05-27 15:44:23 +0000 |
commit | 66765100f4257159622cefe57bed50125a5ad017 (patch) | |
tree | a88ee23bb194eb91f0ebb2d9b23ff423e3ea8e37 /cpp/src/qmf | |
parent | 1aeaa7b16e5ce54f10c901d75c4d40f9f88b9db6 (diff) | |
parent | 88b98b2f4152ef59a671fad55a0d08338b6b78ca (diff) | |
download | qpid-python-rajith_jms_client.tar.gz |
Creating a branch for experimenting with some ideas for JMS client.rajith_jms_client
git-svn-id: https://svn.apache.org/repos/asf/qpid/branches/rajith_jms_client@1128369 13f79535-47bb-0310-9956-ffa450edef68
Diffstat (limited to 'cpp/src/qmf')
64 files changed, 0 insertions, 12661 deletions
diff --git a/cpp/src/qmf/Agent.cpp b/cpp/src/qmf/Agent.cpp deleted file mode 100644 index 915f2a1c88..0000000000 --- a/cpp/src/qmf/Agent.cpp +++ /dev/null @@ -1,657 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/AgentImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/ConsoleEventImpl.h" -#include "qmf/ConsoleSession.h" -#include "qmf/DataImpl.h" -#include "qmf/Query.h" -#include "qmf/SchemaImpl.h" -#include "qmf/agentCapability.h" -#include "qmf/constants.h" -#include "qpid/messaging/Sender.h" -#include "qpid/messaging/AddressParser.h" -#include "qpid/management/Buffer.h" -#include "qpid/log/Statement.h" -#include <boost/lexical_cast.hpp> - -using qpid::types::Variant; -using qpid::messaging::Duration; -using qpid::messaging::Message; -using qpid::messaging::Sender; -using namespace std; -using namespace qmf; - -typedef PrivateImplRef<Agent> PI; - -Agent::Agent(AgentImpl* impl) { PI::ctor(*this, impl); } -Agent::Agent(const Agent& s) : qmf::Handle<AgentImpl>() { PI::copy(*this, s); } -Agent::~Agent() { PI::dtor(*this); } -Agent& Agent::operator=(const Agent& s) { return PI::assign(*this, s); } -string Agent::getName() const { return isValid() ? impl->getName() : ""; } -uint32_t Agent::getEpoch() const { return isValid() ? impl->getEpoch() : 0; } -string Agent::getVendor() const { return isValid() ? impl->getVendor() : ""; } -string Agent::getProduct() const { return isValid() ? impl->getProduct() : ""; } -string Agent::getInstance() const { return isValid() ? impl->getInstance() : ""; } -const Variant& Agent::getAttribute(const string& k) const { return impl->getAttribute(k); } -const Variant::Map& Agent::getAttributes() const { return impl->getAttributes(); } -ConsoleEvent Agent::querySchema(Duration t) { return impl->querySchema(t); } -uint32_t Agent::querySchemaAsync() { return impl->querySchemaAsync(); } -ConsoleEvent Agent::query(const Query& q, Duration t) { return impl->query(q, t); } -ConsoleEvent Agent::query(const string& q, Duration t) { return impl->query(q, t); } -uint32_t Agent::queryAsync(const Query& q) { return impl->queryAsync(q); } -uint32_t Agent::queryAsync(const string& q) { return impl->queryAsync(q); } -ConsoleEvent Agent::callMethod(const string& m, const Variant::Map& a, const DataAddr& d, Duration t) { return impl->callMethod(m, a, d, t); } -uint32_t Agent::callMethodAsync(const string& m, const Variant::Map& a, const DataAddr& d) { return impl->callMethodAsync(m, a, d); } -uint32_t Agent::getPackageCount() const { return impl->getPackageCount(); } -const string& Agent::getPackage(uint32_t i) const { return impl->getPackage(i); } -uint32_t Agent::getSchemaIdCount(const string& p) const { return impl->getSchemaIdCount(p); } -SchemaId Agent::getSchemaId(const string& p, uint32_t i) const { return impl->getSchemaId(p, i); } -Schema Agent::getSchema(const SchemaId& s, Duration t) { return impl->getSchema(s, t); } - - - -AgentImpl::AgentImpl(const std::string& n, uint32_t e, ConsoleSessionImpl& s) : - name(n), directSubject(n), epoch(e), session(s), touched(true), untouchedCount(0), capability(0), - sender(session.directSender), nextCorrelator(1), schemaCache(s.schemaCache) -{ -} - -void AgentImpl::setAttribute(const std::string& k, const qpid::types::Variant& v) -{ - attributes[k] = v; - if (k == "qmf.agent_capability") - try { - capability = v.asUint32(); - } catch (std::exception&) {} - if (k == "_direct_subject") - try { - directSubject = v.asString(); - sender = session.topicSender; - } catch (std::exception&) {} -} - -const Variant& AgentImpl::getAttribute(const string& k) const -{ - Variant::Map::const_iterator iter = attributes.find(k); - if (iter == attributes.end()) - throw KeyNotFound(k); - return iter->second; -} - - -ConsoleEvent AgentImpl::query(const Query& query, Duration timeout) -{ - boost::shared_ptr<SyncContext> context(new SyncContext()); - uint32_t correlator; - ConsoleEvent result; - - { - qpid::sys::Mutex::ScopedLock l(lock); - correlator = nextCorrelator++; - contextMap[correlator] = context; - } - try { - sendQuery(query, correlator); - { - uint64_t milliseconds = timeout.getMilliseconds(); - qpid::sys::Mutex::ScopedLock cl(context->lock); - if (!context->response.isValid() || !context->response.isFinal()) - context->cond.wait(context->lock, - qpid::sys::AbsTime(qpid::sys::now(), - qpid::sys::Duration(milliseconds * qpid::sys::TIME_MSEC))); - if (context->response.isValid() && - ((context->response.getType() == CONSOLE_QUERY_RESPONSE && context->response.isFinal()) || - (context->response.getType() == CONSOLE_EXCEPTION))) - result = context->response; - else { - auto_ptr<ConsoleEventImpl> impl(new ConsoleEventImpl(CONSOLE_EXCEPTION)); - Data exception(new DataImpl()); - exception.setProperty("error_text", "Timed out waiting for the agent to respond"); - impl->addData(exception); - result = ConsoleEvent(impl.release()); - } - } - } catch (qpid::types::Exception&) { - } - - { - qpid::sys::Mutex::ScopedLock l(lock); - contextMap.erase(correlator); - } - - return result; -} - - -ConsoleEvent AgentImpl::query(const string& text, Duration timeout) -{ - return query(stringToQuery(text), timeout); -} - - -uint32_t AgentImpl::queryAsync(const Query& query) -{ - uint32_t correlator; - - { - qpid::sys::Mutex::ScopedLock l(lock); - correlator = nextCorrelator++; - } - - sendQuery(query, correlator); - return correlator; -} - - -uint32_t AgentImpl::queryAsync(const string& text) -{ - return queryAsync(stringToQuery(text)); -} - - -ConsoleEvent AgentImpl::callMethod(const string& method, const Variant::Map& args, const DataAddr& addr, Duration timeout) -{ - boost::shared_ptr<SyncContext> context(new SyncContext()); - uint32_t correlator; - ConsoleEvent result; - - { - qpid::sys::Mutex::ScopedLock l(lock); - correlator = nextCorrelator++; - contextMap[correlator] = context; - } - try { - sendMethod(method, args, addr, correlator); - { - uint64_t milliseconds = timeout.getMilliseconds(); - qpid::sys::Mutex::ScopedLock cl(context->lock); - if (!context->response.isValid()) - context->cond.wait(context->lock, - qpid::sys::AbsTime(qpid::sys::now(), - qpid::sys::Duration(milliseconds * qpid::sys::TIME_MSEC))); - if (context->response.isValid()) - result = context->response; - else { - auto_ptr<ConsoleEventImpl> impl(new ConsoleEventImpl(CONSOLE_EXCEPTION)); - Data exception(new DataImpl()); - exception.setProperty("error_text", "Timed out waiting for the agent to respond"); - impl->addData(exception); - result = ConsoleEvent(impl.release()); - } - } - } catch (qpid::types::Exception&) { - } - - { - qpid::sys::Mutex::ScopedLock l(lock); - contextMap.erase(correlator); - } - - return result; -} - - -uint32_t AgentImpl::callMethodAsync(const string& method, const Variant::Map& args, const DataAddr& addr) -{ - uint32_t correlator; - - { - qpid::sys::Mutex::ScopedLock l(lock); - correlator = nextCorrelator++; - } - - sendMethod(method, args, addr, correlator); - return correlator; -} - - -uint32_t AgentImpl::getPackageCount() const -{ - qpid::sys::Mutex::ScopedLock l(lock); - - // - // Populate the package set. - // - for (set<SchemaId>::const_iterator iter = schemaIdSet.begin(); iter != schemaIdSet.end(); iter++) - packageSet.insert(iter->getPackageName()); - - return packageSet.size(); -} - - -const string& AgentImpl::getPackage(uint32_t idx) const -{ - qpid::sys::Mutex::ScopedLock l(lock); - uint32_t count(0); - for (set<string>::const_iterator iter = packageSet.begin(); iter != packageSet.end(); iter++) { - if (idx == count) - return *iter; - count++; - } - throw IndexOutOfRange(); -} - - -uint32_t AgentImpl::getSchemaIdCount(const string& pname) const -{ - qpid::sys::Mutex::ScopedLock l(lock); - uint32_t count(0); - for (set<SchemaId>::const_iterator iter = schemaIdSet.begin(); iter != schemaIdSet.end(); iter++) - if (iter->getPackageName() == pname) - count++; - return count; -} - - -SchemaId AgentImpl::getSchemaId(const string& pname, uint32_t idx) const -{ - qpid::sys::Mutex::ScopedLock l(lock); - uint32_t count(0); - for (set<SchemaId>::const_iterator iter = schemaIdSet.begin(); iter != schemaIdSet.end(); iter++) { - if (iter->getPackageName() == pname) { - if (idx == count) - return *iter; - count++; - } - } - throw IndexOutOfRange(); -} - - -Schema AgentImpl::getSchema(const SchemaId& id, Duration timeout) -{ - if (!schemaCache->haveSchema(id)) - // - // The desired schema is not in the cache. We need to asynchronously query the remote - // agent for the information. The call to schemaCache->getSchema will block waiting for - // the response to be received. - // - sendSchemaRequest(id); - - return schemaCache->getSchema(id, timeout); -} - - -void AgentImpl::handleException(const Variant::Map& content, const Message& msg) -{ - const string& cid(msg.getCorrelationId()); - Variant::Map::const_iterator aIter; - uint32_t correlator; - boost::shared_ptr<SyncContext> context; - - try { correlator = boost::lexical_cast<uint32_t>(cid); } - catch(const boost::bad_lexical_cast&) { correlator = 0; } - - { - qpid::sys::Mutex::ScopedLock l(lock); - map<uint32_t, boost::shared_ptr<SyncContext> >::iterator iter = contextMap.find(correlator); - if (iter != contextMap.end()) - context = iter->second; - } - - if (context.get() != 0) { - // - // This exception is associated with a synchronous request. - // - qpid::sys::Mutex::ScopedLock cl(context->lock); - context->response = ConsoleEvent(new ConsoleEventImpl(CONSOLE_EXCEPTION)); - ConsoleEventImplAccess::get(context->response).addData(new DataImpl(content, this)); - ConsoleEventImplAccess::get(context->response).setAgent(this); - context->cond.notify(); - } else { - // - // This exception is associated with an asynchronous request. - // - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_EXCEPTION)); - eventImpl->setCorrelator(correlator); - eventImpl->setAgent(this); - eventImpl->addData(new DataImpl(content, this)); - session.enqueueEvent(eventImpl.release()); - } -} - - -void AgentImpl::handleMethodResponse(const Variant::Map& response, const Message& msg) -{ - const string& cid(msg.getCorrelationId()); - Variant::Map::const_iterator aIter; - Variant::Map argMap; - uint32_t correlator; - boost::shared_ptr<SyncContext> context; - - QPID_LOG(trace, "RCVD MethodResponse cid=" << cid << " map=" << response); - - aIter = response.find("_arguments"); - if (aIter != response.end()) - argMap = aIter->second.asMap(); - - try { correlator = boost::lexical_cast<uint32_t>(cid); } - catch(const boost::bad_lexical_cast&) { correlator = 0; } - - { - qpid::sys::Mutex::ScopedLock l(lock); - map<uint32_t, boost::shared_ptr<SyncContext> >::iterator iter = contextMap.find(correlator); - if (iter != contextMap.end()) - context = iter->second; - } - - if (context.get() != 0) { - // - // This response is associated with a synchronous request. - // - qpid::sys::Mutex::ScopedLock cl(context->lock); - context->response = ConsoleEvent(new ConsoleEventImpl(CONSOLE_METHOD_RESPONSE)); - ConsoleEventImplAccess::get(context->response).setArguments(argMap); - ConsoleEventImplAccess::get(context->response).setAgent(this); - context->cond.notify(); - } else { - // - // This response is associated with an asynchronous request. - // - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_METHOD_RESPONSE)); - eventImpl->setCorrelator(correlator); - eventImpl->setAgent(this); - eventImpl->setArguments(argMap); - session.enqueueEvent(eventImpl.release()); - } -} - - -void AgentImpl::handleDataIndication(const Variant::List& list, const Message& msg) -{ - Variant::Map::const_iterator aIter; - const Variant::Map& props(msg.getProperties()); - boost::shared_ptr<SyncContext> context; - - aIter = props.find("qmf.content"); - if (aIter == props.end()) - return; - - string content_type(aIter->second.asString()); - if (content_type != "_event") - return; - - for (Variant::List::const_iterator lIter = list.begin(); lIter != list.end(); lIter++) { - const Variant::Map& eventMap(lIter->asMap()); - Data data(new DataImpl(eventMap, this)); - int severity(SEV_NOTICE); - uint64_t timestamp(0); - - aIter = eventMap.find("_severity"); - if (aIter != eventMap.end()) - severity = int(aIter->second.asInt8()); - - aIter = eventMap.find("_timestamp"); - if (aIter != eventMap.end()) - timestamp = aIter->second.asUint64(); - - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_EVENT)); - eventImpl->setAgent(this); - eventImpl->addData(data); - eventImpl->setSeverity(severity); - eventImpl->setTimestamp(timestamp); - if (data.hasSchema()) - learnSchemaId(data.getSchemaId()); - session.enqueueEvent(eventImpl.release()); - } -} - - -void AgentImpl::handleQueryResponse(const Variant::List& list, const Message& msg) -{ - const string& cid(msg.getCorrelationId()); - Variant::Map::const_iterator aIter; - const Variant::Map& props(msg.getProperties()); - uint32_t correlator; - bool final(false); - boost::shared_ptr<SyncContext> context; - - aIter = props.find("partial"); - if (aIter == props.end()) - final = true; - - aIter = props.find("qmf.content"); - if (aIter == props.end()) - return; - - string content_type(aIter->second.asString()); - if (content_type != "_schema" && content_type != "_schema_id" && content_type != "_data") - return; - - try { correlator = boost::lexical_cast<uint32_t>(cid); } - catch(const boost::bad_lexical_cast&) { correlator = 0; } - - { - qpid::sys::Mutex::ScopedLock l(lock); - map<uint32_t, boost::shared_ptr<SyncContext> >::iterator iter = contextMap.find(correlator); - if (iter != contextMap.end()) - context = iter->second; - } - - if (context.get() != 0) { - // - // This response is associated with a synchronous request. - // - qpid::sys::Mutex::ScopedLock cl(context->lock); - if (!context->response.isValid()) - context->response = ConsoleEvent(new ConsoleEventImpl(CONSOLE_QUERY_RESPONSE)); - - if (content_type == "_data") - for (Variant::List::const_iterator lIter = list.begin(); lIter != list.end(); lIter++) { - Data data(new DataImpl(lIter->asMap(), this)); - ConsoleEventImplAccess::get(context->response).addData(data); - if (data.hasSchema()) - learnSchemaId(data.getSchemaId()); - } - else if (content_type == "_schema_id") - for (Variant::List::const_iterator lIter = list.begin(); lIter != list.end(); lIter++) { - SchemaId schemaId(new SchemaIdImpl(lIter->asMap())); - ConsoleEventImplAccess::get(context->response).addSchemaId(schemaId); - learnSchemaId(schemaId); - } - else if (content_type == "_schema") - for (Variant::List::const_iterator lIter = list.begin(); lIter != list.end(); lIter++) { - Schema schema(new SchemaImpl(lIter->asMap())); - schemaCache->declareSchema(schema); - } - - if (final) { - ConsoleEventImplAccess::get(context->response).setFinal(); - ConsoleEventImplAccess::get(context->response).setAgent(this); - context->cond.notify(); - } - } else { - // - // This response is associated with an asynchronous request. - // - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_QUERY_RESPONSE)); - eventImpl->setCorrelator(correlator); - eventImpl->setAgent(this); - - if (content_type == "_data") - for (Variant::List::const_iterator lIter = list.begin(); lIter != list.end(); lIter++) { - Data data(new DataImpl(lIter->asMap(), this)); - eventImpl->addData(data); - if (data.hasSchema()) - learnSchemaId(data.getSchemaId()); - } - else if (content_type == "_schema_id") - for (Variant::List::const_iterator lIter = list.begin(); lIter != list.end(); lIter++) { - SchemaId schemaId(new SchemaIdImpl(lIter->asMap())); - eventImpl->addSchemaId(schemaId); - learnSchemaId(schemaId); - } - else if (content_type == "_schema") - for (Variant::List::const_iterator lIter = list.begin(); lIter != list.end(); lIter++) { - Schema schema(new SchemaImpl(lIter->asMap())); - schemaCache->declareSchema(schema); - } - - if (final) - eventImpl->setFinal(); - if (content_type != "_schema") - session.enqueueEvent(eventImpl.release()); - } -} - - -Query AgentImpl::stringToQuery(const std::string& text) -{ - qpid::messaging::AddressParser parser(text); - Variant::Map map; - Variant::Map::const_iterator iter; - string className; - string packageName; - - parser.parseMap(map); - - iter = map.find("class"); - if (iter != map.end()) - className = iter->second.asString(); - - iter = map.find("package"); - if (iter != map.end()) - packageName = iter->second.asString(); - - Query query(QUERY_OBJECT, className, packageName); - - iter = map.find("where"); - if (iter != map.end()) - query.setPredicate(iter->second.asList()); - - return query; -} - - -void AgentImpl::sendQuery(const Query& query, uint32_t correlator) -{ - Message msg; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_REQUEST; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_QUERY_REQUEST; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - msg.setReplyTo(session.replyAddress); - msg.setCorrelationId(boost::lexical_cast<string>(correlator)); - msg.setSubject(directSubject); - string userId(session.connection.getAuthenticatedUsername()); - if (!userId.empty()) - msg.setUserId(userId); - encode(QueryImplAccess::get(query).asMap(), msg); - if (sender.isValid()) { - sender.send(msg); - QPID_LOG(trace, "SENT QueryRequest to=" << sender.getName() << "/" << directSubject << " cid=" << correlator); - } -} - - -void AgentImpl::sendMethod(const string& method, const Variant::Map& args, const DataAddr& addr, uint32_t correlator) -{ - Message msg; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_REQUEST; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_METHOD_REQUEST; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - map["_method_name"] = method; - map["_object_id"] = addr.asMap(); - map["_arguments"] = args; - - msg.setReplyTo(session.replyAddress); - msg.setCorrelationId(boost::lexical_cast<string>(correlator)); - msg.setSubject(directSubject); - string userId(session.connection.getAuthenticatedUsername()); - if (!userId.empty()) - msg.setUserId(userId); - encode(map, msg); - if (sender.isValid()) { - sender.send(msg); - QPID_LOG(trace, "SENT MethodRequest method=" << method << " to=" << sender.getName() << "/" << directSubject << " content=" << map << " cid=" << correlator); - } -} - -void AgentImpl::sendSchemaRequest(const SchemaId& id) -{ - uint32_t correlator; - - { - qpid::sys::Mutex::ScopedLock l(lock); - correlator = nextCorrelator++; - } - - if (capability >= AGENT_CAPABILITY_V2_SCHEMA) { - Query query(QUERY_SCHEMA, id); - sendQuery(query, correlator); - return; - } - -#define RAW_BUFFER_SIZE 1024 - char rawBuffer[RAW_BUFFER_SIZE]; - qpid::management::Buffer buffer(rawBuffer, RAW_BUFFER_SIZE); - - buffer.putOctet('A'); - buffer.putOctet('M'); - buffer.putOctet('2'); - buffer.putOctet('S'); - buffer.putLong(correlator); - buffer.putShortString(id.getPackageName()); - buffer.putShortString(id.getName()); - buffer.putBin128(id.getHash().data()); - - string content(rawBuffer, buffer.getPosition()); - - Message msg; - msg.setReplyTo(session.replyAddress); - msg.setContent(content); - msg.setSubject(directSubject); - string userId(session.connection.getAuthenticatedUsername()); - if (!userId.empty()) - msg.setUserId(userId); - if (sender.isValid()) { - sender.send(msg); - QPID_LOG(trace, "SENT V1SchemaRequest to=" << sender.getName() << "/" << directSubject); - } -} - - -void AgentImpl::learnSchemaId(const SchemaId& id) -{ - schemaCache->declareSchemaId(id); - schemaIdSet.insert(id); -} - - -AgentImpl& AgentImplAccess::get(Agent& item) -{ - return *item.impl; -} - - -const AgentImpl& AgentImplAccess::get(const Agent& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/AgentEvent.cpp b/cpp/src/qmf/AgentEvent.cpp deleted file mode 100644 index 2dc24ecac1..0000000000 --- a/cpp/src/qmf/AgentEvent.cpp +++ /dev/null @@ -1,85 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/AgentEventImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/SchemaImpl.h" - -using namespace std; -using namespace qmf; -using qpid::types::Variant; - -typedef PrivateImplRef<AgentEvent> PI; - -AgentEvent::AgentEvent(AgentEventImpl* impl) { PI::ctor(*this, impl); } -AgentEvent::AgentEvent(const AgentEvent& s) : qmf::Handle<AgentEventImpl>() { PI::copy(*this, s); } -AgentEvent::~AgentEvent() { PI::dtor(*this); } -AgentEvent& AgentEvent::operator=(const AgentEvent& s) { return PI::assign(*this, s); } - -AgentEventCode AgentEvent::getType() const { return impl->getType(); } -const string& AgentEvent::getUserId() const { return impl->getUserId(); } -Query AgentEvent::getQuery() const { return impl->getQuery(); } -bool AgentEvent::hasDataAddr() const { return impl->hasDataAddr(); } -DataAddr AgentEvent::getDataAddr() const { return impl->getDataAddr(); } -const string& AgentEvent::getMethodName() const { return impl->getMethodName(); } -qpid::types::Variant::Map& AgentEvent::getArguments() { return impl->getArguments(); } -qpid::types::Variant::Map& AgentEvent::getArgumentSubtypes() { return impl->getArgumentSubtypes(); } -void AgentEvent::addReturnArgument(const std::string& k, const qpid::types::Variant& v, const std::string& s) { impl->addReturnArgument(k, v, s); } - -uint32_t AgentEventImpl::enqueueData(const Data& data) -{ - qpid::sys::Mutex::ScopedLock l(lock); - dataQueue.push(data); - return dataQueue.size(); -} - - -Data AgentEventImpl::dequeueData() -{ - qpid::sys::Mutex::ScopedLock l(lock); - if (dataQueue.empty()) - return Data(); - Data data(dataQueue.front()); - dataQueue.pop(); - return data; -} - - -void AgentEventImpl::addReturnArgument(const string& key, const Variant& val, const string& subtype) -{ - if (schema.isValid() && !SchemaImplAccess::get(schema).isValidMethodOutArg(methodName, key, val)) - throw QmfException("Output argument is unknown or the type is incompatible"); - outArguments[key] = val; - if (!subtype.empty()) - outArgumentSubtypes[key] = subtype; -} - - -AgentEventImpl& AgentEventImplAccess::get(AgentEvent& item) -{ - return *item.impl; -} - - -const AgentEventImpl& AgentEventImplAccess::get(const AgentEvent& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/AgentEventImpl.h b/cpp/src/qmf/AgentEventImpl.h deleted file mode 100644 index 1ecb41775a..0000000000 --- a/cpp/src/qmf/AgentEventImpl.h +++ /dev/null @@ -1,96 +0,0 @@ -#ifndef _QMF_AGENT_EVENT_IMPL_H_ -#define _QMF_AGENT_EVENT_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qpid/sys/Mutex.h" -#include "qpid/sys/IntegerTypes.h" -#include "qpid/messaging/Address.h" -#include "qmf/AgentEvent.h" -#include "qmf/Query.h" -#include "qmf/DataAddr.h" -#include "qmf/Data.h" -#include "qmf/Schema.h" -#include <queue> - -namespace qmf { - class AgentEventImpl : public virtual qpid::RefCounted { - public: - // - // Impl-only methods - // - AgentEventImpl(AgentEventCode e) : eventType(e) {} - void setUserId(const std::string& u) { userId = u; } - void setQuery(const Query& q) { query = q; } - void setDataAddr(const DataAddr& d) { dataAddr = d; } - void setMethodName(const std::string& m) { methodName = m; } - void setArguments(const qpid::types::Variant::Map& a) { arguments = a; } - void setArgumentSubtypes(const qpid::types::Variant::Map& a) { argumentSubtypes = a; } - void setReplyTo(const qpid::messaging::Address& r) { replyTo = r; } - void setSchema(const Schema& s) { schema = s; } - const qpid::messaging::Address& getReplyTo() { return replyTo; } - void setCorrelationId(const std::string& c) { correlationId = c; } - const std::string& getCorrelationId() { return correlationId; } - const qpid::types::Variant::Map& getReturnArguments() const { return outArguments; } - const qpid::types::Variant::Map& getReturnArgumentSubtypes() const { return outArgumentSubtypes; } - uint32_t enqueueData(const Data&); - Data dequeueData(); - - // - // Methods from API handle - // - AgentEventCode getType() const { return eventType; } - const std::string& getUserId() const { return userId; } - Query getQuery() const { return query; } - bool hasDataAddr() const { return dataAddr.isValid(); } - DataAddr getDataAddr() const { return dataAddr; } - const std::string& getMethodName() const { return methodName; } - qpid::types::Variant::Map& getArguments() { return arguments; } - qpid::types::Variant::Map& getArgumentSubtypes() { return argumentSubtypes; } - void addReturnArgument(const std::string&, const qpid::types::Variant&, const std::string&); - - private: - const AgentEventCode eventType; - std::string userId; - qpid::messaging::Address replyTo; - std::string correlationId; - Query query; - DataAddr dataAddr; - Schema schema; - std::string methodName; - qpid::types::Variant::Map arguments; - qpid::types::Variant::Map argumentSubtypes; - qpid::types::Variant::Map outArguments; - qpid::types::Variant::Map outArgumentSubtypes; - - qpid::sys::Mutex lock; - std::queue<Data> dataQueue; - }; - - struct AgentEventImplAccess - { - static AgentEventImpl& get(AgentEvent&); - static const AgentEventImpl& get(const AgentEvent&); - }; -} - -#endif diff --git a/cpp/src/qmf/AgentImpl.h b/cpp/src/qmf/AgentImpl.h deleted file mode 100644 index 7fa4f4373a..0000000000 --- a/cpp/src/qmf/AgentImpl.h +++ /dev/null @@ -1,123 +0,0 @@ -#ifndef _QMF_AGENT_IMPL_H_ -#define _QMF_AGENT_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/Agent.h" -#include "qmf/ConsoleEventImpl.h" -#include "qmf/ConsoleSessionImpl.h" -#include "qmf/QueryImpl.h" -#include "qmf/SchemaCache.h" -#include "qpid/messaging/Session.h" -#include "qpid/messaging/Message.h" -#include "qpid/messaging/Sender.h" -#include "qpid/sys/Mutex.h" -#include "qpid/sys/Condition.h" -#include <boost/shared_ptr.hpp> -#include <map> -#include <set> - -namespace qmf { - class AgentImpl : public virtual qpid::RefCounted { - public: - // - // Impl-only methods - // - AgentImpl(const std::string& n, uint32_t e, ConsoleSessionImpl& s); - void setAttribute(const std::string& k, const qpid::types::Variant& v); - void setAttribute(const std::string& k, const std::string& v) { attributes[k] = v; } - void touch() { touched = true; } - uint32_t age() { untouchedCount = touched ? 0 : untouchedCount + 1; touched = false; return untouchedCount; } - uint32_t getCapability() const { return capability; } - void handleException(const qpid::types::Variant::Map&, const qpid::messaging::Message&); - void handleMethodResponse(const qpid::types::Variant::Map&, const qpid::messaging::Message&); - void handleDataIndication(const qpid::types::Variant::List&, const qpid::messaging::Message&); - void handleQueryResponse(const qpid::types::Variant::List&, const qpid::messaging::Message&); - - // - // Methods from API handle - // - const std::string& getName() const { return name; } - uint32_t getEpoch() const { return epoch; } - void setEpoch(uint32_t e) { epoch = e; } - std::string getVendor() const { return getAttribute("_vendor").asString(); } - std::string getProduct() const { return getAttribute("_product").asString(); } - std::string getInstance() const { return getAttribute("_instance").asString(); } - const qpid::types::Variant& getAttribute(const std::string& k) const; - const qpid::types::Variant::Map& getAttributes() const { return attributes; } - - ConsoleEvent querySchema(qpid::messaging::Duration t) { return query(Query(QUERY_SCHEMA_ID), t); } - uint32_t querySchemaAsync() { return queryAsync(Query(QUERY_SCHEMA_ID)); } - - ConsoleEvent query(const Query& q, qpid::messaging::Duration t); - ConsoleEvent query(const std::string& q, qpid::messaging::Duration t); - uint32_t queryAsync(const Query& q); - uint32_t queryAsync(const std::string& q); - - ConsoleEvent callMethod(const std::string& m, const qpid::types::Variant::Map& a, const DataAddr&, qpid::messaging::Duration t); - uint32_t callMethodAsync(const std::string& m, const qpid::types::Variant::Map& a, const DataAddr&); - - uint32_t getPackageCount() const; - const std::string& getPackage(uint32_t i) const; - uint32_t getSchemaIdCount(const std::string& p) const; - SchemaId getSchemaId(const std::string& p, uint32_t i) const; - Schema getSchema(const SchemaId& s, qpid::messaging::Duration t); - - private: - struct SyncContext { - qpid::sys::Mutex lock; - qpid::sys::Condition cond; - ConsoleEvent response; - }; - - mutable qpid::sys::Mutex lock; - std::string name; - std::string directSubject; - uint32_t epoch; - ConsoleSessionImpl& session; - bool touched; - uint32_t untouchedCount; - uint32_t capability; - qpid::messaging::Sender sender; - qpid::types::Variant::Map attributes; - uint32_t nextCorrelator; - std::map<uint32_t, boost::shared_ptr<SyncContext> > contextMap; - boost::shared_ptr<SchemaCache> schemaCache; - mutable std::set<std::string> packageSet; - std::set<SchemaId, SchemaIdCompare> schemaIdSet; - - Query stringToQuery(const std::string&); - void sendQuery(const Query&, uint32_t); - void sendSchemaIdQuery(uint32_t); - void sendMethod(const std::string&, const qpid::types::Variant::Map&, const DataAddr&, uint32_t); - void sendSchemaRequest(const SchemaId&); - void learnSchemaId(const SchemaId&); - }; - - struct AgentImplAccess - { - static AgentImpl& get(Agent&); - static const AgentImpl& get(const Agent&); - }; -} - -#endif diff --git a/cpp/src/qmf/AgentSession.cpp b/cpp/src/qmf/AgentSession.cpp deleted file mode 100644 index 71d369325f..0000000000 --- a/cpp/src/qmf/AgentSession.cpp +++ /dev/null @@ -1,1072 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" -#include "qmf/AgentSession.h" -#include "qmf/AgentEventImpl.h" -#include "qmf/SchemaIdImpl.h" -#include "qmf/SchemaImpl.h" -#include "qmf/DataAddrImpl.h" -#include "qmf/DataImpl.h" -#include "qmf/QueryImpl.h" -#include "qmf/agentCapability.h" -#include "qmf/constants.h" -#include "qpid/sys/Mutex.h" -#include "qpid/sys/Condition.h" -#include "qpid/sys/Thread.h" -#include "qpid/sys/Runnable.h" -#include "qpid/log/Statement.h" -#include "qpid/messaging/Connection.h" -#include "qpid/messaging/Session.h" -#include "qpid/messaging/Receiver.h" -#include "qpid/messaging/Sender.h" -#include "qpid/messaging/Message.h" -#include "qpid/messaging/AddressParser.h" -#include "qpid/management/Buffer.h" -#include <queue> -#include <map> -#include <set> -#include <iostream> -#include <memory> - -using namespace std; -using namespace qpid::messaging; -using namespace qmf; -using qpid::types::Variant; - -namespace qmf { - class AgentSessionImpl : public virtual qpid::RefCounted, public qpid::sys::Runnable { - public: - ~AgentSessionImpl(); - - // - // Methods from API handle - // - AgentSessionImpl(Connection& c, const string& o); - void setDomain(const string& d) { checkOpen(); domain = d; } - void setVendor(const string& v) { checkOpen(); attributes["_vendor"] = v; } - void setProduct(const string& p) { checkOpen(); attributes["_product"] = p; } - void setInstance(const string& i) { checkOpen(); attributes["_instance"] = i; } - void setAttribute(const string& k, const qpid::types::Variant& v) { checkOpen(); attributes[k] = v; } - const string& getName() const { return agentName; } - void open(); - void close(); - bool nextEvent(AgentEvent& e, Duration t); - int pendingEvents() const; - - void registerSchema(Schema& s); - DataAddr addData(Data& d, const string& n, bool persist); - void delData(const DataAddr&); - - void authAccept(AgentEvent& e); - void authReject(AgentEvent& e, const string& m); - void raiseException(AgentEvent& e, const string& s); - void raiseException(AgentEvent& e, const Data& d); - void response(AgentEvent& e, const Data& d); - void complete(AgentEvent& e); - void methodSuccess(AgentEvent& e); - void raiseEvent(const Data& d); - void raiseEvent(const Data& d, int s); - - private: - typedef map<DataAddr, Data, DataAddrCompare> DataIndex; - typedef map<SchemaId, Schema, SchemaIdCompare> SchemaMap; - - mutable qpid::sys::Mutex lock; - qpid::sys::Condition cond; - Connection connection; - Session session; - Sender directSender; - Sender topicSender; - string domain; - Variant::Map attributes; - Variant::Map options; - string agentName; - bool opened; - queue<AgentEvent> eventQueue; - qpid::sys::Thread* thread; - bool threadCanceled; - uint32_t bootSequence; - uint32_t interval; - uint64_t lastHeartbeat; - uint64_t lastVisit; - bool forceHeartbeat; - bool externalStorage; - bool autoAllowQueries; - bool autoAllowMethods; - uint32_t maxSubscriptions; - uint32_t minSubInterval; - uint32_t subLifetime; - bool publicEvents; - bool listenOnDirect; - bool strictSecurity; - uint64_t schemaUpdateTime; - string directBase; - string topicBase; - - SchemaMap schemata; - DataIndex globalIndex; - map<SchemaId, DataIndex, SchemaIdCompareNoHash> schemaIndex; - - void checkOpen(); - void setAgentName(); - void enqueueEvent(const AgentEvent&); - void handleLocateRequest(const Variant::List& content, const Message& msg); - void handleMethodRequest(const Variant::Map& content, const Message& msg); - void handleQueryRequest(const Variant::Map& content, const Message& msg); - void handleSchemaRequest(AgentEvent&); - void handleV1SchemaRequest(qpid::management::Buffer&, uint32_t, const Message&); - void dispatch(Message); - void sendHeartbeat(); - void send(Message, const Address&); - void flushResponses(AgentEvent&, bool); - void periodicProcessing(uint64_t); - void run(); - }; -} - -typedef qmf::PrivateImplRef<AgentSession> PI; - -AgentSession::AgentSession(AgentSessionImpl* impl) { PI::ctor(*this, impl); } -AgentSession::AgentSession(const AgentSession& s) : qmf::Handle<AgentSessionImpl>() { PI::copy(*this, s); } -AgentSession::~AgentSession() { PI::dtor(*this); } -AgentSession& AgentSession::operator=(const AgentSession& s) { return PI::assign(*this, s); } - -AgentSession::AgentSession(Connection& c, const string& o) { PI::ctor(*this, new AgentSessionImpl(c, o)); } -void AgentSession::setDomain(const string& d) { impl->setDomain(d); } -void AgentSession::setVendor(const string& v) { impl->setVendor(v); } -void AgentSession::setProduct(const string& p) { impl->setProduct(p); } -void AgentSession::setInstance(const string& i) { impl->setInstance(i); } -void AgentSession::setAttribute(const string& k, const qpid::types::Variant& v) { impl->setAttribute(k, v); } -const string& AgentSession::getName() const { return impl->getName(); } -void AgentSession::open() { impl->open(); } -void AgentSession::close() { impl->close(); } -bool AgentSession::nextEvent(AgentEvent& e, Duration t) { return impl->nextEvent(e, t); } -int AgentSession::pendingEvents() const { return impl->pendingEvents(); } -void AgentSession::registerSchema(Schema& s) { impl->registerSchema(s); } -DataAddr AgentSession::addData(Data& d, const string& n, bool p) { return impl->addData(d, n, p); } -void AgentSession::delData(const DataAddr& a) { impl->delData(a); } -void AgentSession::authAccept(AgentEvent& e) { impl->authAccept(e); } -void AgentSession::authReject(AgentEvent& e, const string& m) { impl->authReject(e, m); } -void AgentSession::raiseException(AgentEvent& e, const string& s) { impl->raiseException(e, s); } -void AgentSession::raiseException(AgentEvent& e, const Data& d) { impl->raiseException(e, d); } -void AgentSession::response(AgentEvent& e, const Data& d) { impl->response(e, d); } -void AgentSession::complete(AgentEvent& e) { impl->complete(e); } -void AgentSession::methodSuccess(AgentEvent& e) { impl->methodSuccess(e); } -void AgentSession::raiseEvent(const Data& d) { impl->raiseEvent(d); } -void AgentSession::raiseEvent(const Data& d, int s) { impl->raiseEvent(d, s); } - -//======================================================================================== -// Impl Method Bodies -//======================================================================================== - -AgentSessionImpl::AgentSessionImpl(Connection& c, const string& options) : - connection(c), domain("default"), opened(false), thread(0), threadCanceled(false), - bootSequence(1), interval(60), lastHeartbeat(0), lastVisit(0), forceHeartbeat(false), - externalStorage(false), autoAllowQueries(true), autoAllowMethods(true), - maxSubscriptions(64), minSubInterval(3000), subLifetime(300), publicEvents(true), - listenOnDirect(true), strictSecurity(false), - schemaUpdateTime(uint64_t(qpid::sys::Duration(qpid::sys::EPOCH, qpid::sys::now()))) -{ - // - // Set Agent Capability Level - // - attributes["qmf.agent_capability"] = AGENT_CAPABILITY_0_8; - - if (!options.empty()) { - qpid::messaging::AddressParser parser(options); - Variant::Map optMap; - Variant::Map::const_iterator iter; - - parser.parseMap(optMap); - - iter = optMap.find("domain"); - if (iter != optMap.end()) - domain = iter->second.asString(); - - iter = optMap.find("interval"); - if (iter != optMap.end()) { - interval = iter->second.asUint32(); - if (interval < 1) - interval = 1; - } - - iter = optMap.find("external"); - if (iter != optMap.end()) - externalStorage = iter->second.asBool(); - - iter = optMap.find("allow-queries"); - if (iter != optMap.end()) - autoAllowQueries = iter->second.asBool(); - - iter = optMap.find("allow-methods"); - if (iter != optMap.end()) - autoAllowMethods = iter->second.asBool(); - - iter = optMap.find("max-subscriptions"); - if (iter != optMap.end()) - maxSubscriptions = iter->second.asUint32(); - - iter = optMap.find("min-sub-interval"); - if (iter != optMap.end()) - minSubInterval = iter->second.asUint32(); - - iter = optMap.find("sub-lifetime"); - if (iter != optMap.end()) - subLifetime = iter->second.asUint32(); - - iter = optMap.find("public-events"); - if (iter != optMap.end()) - publicEvents = iter->second.asBool(); - - iter = optMap.find("listen-on-direct"); - if (iter != optMap.end()) - listenOnDirect = iter->second.asBool(); - - iter = optMap.find("strict-security"); - if (iter != optMap.end()) - strictSecurity = iter->second.asBool(); - } -} - - -AgentSessionImpl::~AgentSessionImpl() -{ - if (opened) - close(); -} - - -void AgentSessionImpl::open() -{ - if (opened) - throw QmfException("The session is already open"); - - const string addrArgs(";{create:never,node:{type:topic}}"); - const string routableAddr("direct-agent.route." + qpid::types::Uuid(true).str()); - attributes["_direct_subject"] = routableAddr; - - // Establish messaging addresses - setAgentName(); - directBase = "qmf." + domain + ".direct"; - topicBase = "qmf." + domain + ".topic"; - - // Create AMQP session, receivers, and senders - session = connection.createSession(); - Receiver directRx; - Receiver routableDirectRx = session.createReceiver(topicBase + "/" + routableAddr + addrArgs); - Receiver topicRx = session.createReceiver(topicBase + "/console.#" + addrArgs); - - if (listenOnDirect && !strictSecurity) { - directRx = session.createReceiver(directBase + "/" + agentName + addrArgs); - directRx.setCapacity(64); - } - - routableDirectRx.setCapacity(64); - topicRx.setCapacity(64); - - if (!strictSecurity) - directSender = session.createSender(directBase + addrArgs); - topicSender = session.createSender(topicBase + addrArgs); - - // Start the receiver thread - threadCanceled = false; - opened = true; - thread = new qpid::sys::Thread(*this); - - // Send an initial agent heartbeat message - sendHeartbeat(); -} - - -void AgentSessionImpl::close() -{ - if (!opened) - return; - - // Stop and join the receiver thread - threadCanceled = true; - thread->join(); - delete thread; - - // Close the AMQP session - session.close(); - opened = false; -} - - -bool AgentSessionImpl::nextEvent(AgentEvent& event, Duration timeout) -{ - uint64_t milliseconds = timeout.getMilliseconds(); - qpid::sys::Mutex::ScopedLock l(lock); - - if (eventQueue.empty() && milliseconds > 0) - cond.wait(lock, qpid::sys::AbsTime(qpid::sys::now(), - qpid::sys::Duration(milliseconds * qpid::sys::TIME_MSEC))); - - if (!eventQueue.empty()) { - event = eventQueue.front(); - eventQueue.pop(); - return true; - } - - return false; -} - - -int AgentSessionImpl::pendingEvents() const -{ - qpid::sys::Mutex::ScopedLock l(lock); - return eventQueue.size(); -} - - -void AgentSessionImpl::registerSchema(Schema& schema) -{ - if (!schema.isFinalized()) - schema.finalize(); - const SchemaId& schemaId(schema.getSchemaId()); - - qpid::sys::Mutex::ScopedLock l(lock); - schemata[schemaId] = schema; - schemaIndex[schemaId] = DataIndex(); - - // - // Get the news out at the next periodic interval that there is new schema information. - // - schemaUpdateTime = uint64_t(qpid::sys::Duration(qpid::sys::EPOCH, qpid::sys::now())); - forceHeartbeat = true; -} - - -DataAddr AgentSessionImpl::addData(Data& data, const string& name, bool persistent) -{ - if (externalStorage) - throw QmfException("addData() must not be called when the 'external' option is enabled."); - - string dataName; - if (name.empty()) - dataName = qpid::types::Uuid(true).str(); - else - dataName = name; - - DataAddr addr(dataName, agentName, persistent ? 0 : bootSequence); - data.setAddr(addr); - - { - qpid::sys::Mutex::ScopedLock l(lock); - DataIndex::const_iterator iter = globalIndex.find(addr); - if (iter != globalIndex.end()) - throw QmfException("Duplicate Data Address"); - - globalIndex[addr] = data; - if (data.hasSchema()) - schemaIndex[data.getSchemaId()][addr] = data; - } - - // - // TODO: Survey active subscriptions to see if they need to hear about this new data. - // - - return addr; -} - - -void AgentSessionImpl::delData(const DataAddr& addr) -{ - { - qpid::sys::Mutex::ScopedLock l(lock); - DataIndex::iterator iter = globalIndex.find(addr); - if (iter == globalIndex.end()) - return; - if (iter->second.hasSchema()) { - const SchemaId& schemaId(iter->second.getSchemaId()); - schemaIndex[schemaId].erase(addr); - } - globalIndex.erase(iter); - } - - // - // TODO: Survey active subscriptions to see if they need to hear about this deleted data. - // -} - - -void AgentSessionImpl::authAccept(AgentEvent& authEvent) -{ - auto_ptr<AgentEventImpl> eventImpl(new AgentEventImpl(AGENT_QUERY)); - eventImpl->setQuery(authEvent.getQuery()); - eventImpl->setUserId(authEvent.getUserId()); - eventImpl->setReplyTo(AgentEventImplAccess::get(authEvent).getReplyTo()); - eventImpl->setCorrelationId(AgentEventImplAccess::get(authEvent).getCorrelationId()); - AgentEvent event(eventImpl.release()); - - if (externalStorage) { - enqueueEvent(event); - return; - } - - const Query& query(authEvent.getQuery()); - if (query.getDataAddr().isValid()) { - { - qpid::sys::Mutex::ScopedLock l(lock); - DataIndex::const_iterator iter = globalIndex.find(query.getDataAddr()); - if (iter != globalIndex.end()) - response(event, iter->second); - } - complete(event); - return; - } - - if (query.getSchemaId().isValid()) { - { - qpid::sys::Mutex::ScopedLock l(lock); - map<SchemaId, DataIndex>::const_iterator iter = schemaIndex.find(query.getSchemaId()); - if (iter != schemaIndex.end()) - for (DataIndex::const_iterator dIter = iter->second.begin(); dIter != iter->second.end(); dIter++) - if (query.matchesPredicate(dIter->second.getProperties())) - response(event, dIter->second); - } - complete(event); - return; - } - - raiseException(event, "Query is Invalid"); -} - - -void AgentSessionImpl::authReject(AgentEvent& event, const string& error) -{ - raiseException(event, "Action Forbidden - " + error); -} - - -void AgentSessionImpl::raiseException(AgentEvent& event, const string& error) -{ - Data exception(new DataImpl()); - exception.setProperty("error_text", error); - raiseException(event, exception); -} - - -void AgentSessionImpl::raiseException(AgentEvent& event, const Data& data) -{ - Message msg; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_RESPONSE; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_EXCEPTION; - headers[protocol::HEADER_KEY_CONTENT] = protocol::HEADER_CONTENT_DATA; - headers[protocol::HEADER_KEY_AGENT] = agentName; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - AgentEventImpl& eventImpl(AgentEventImplAccess::get(event)); - const DataImpl& dataImpl(DataImplAccess::get(data)); - - msg.setCorrelationId(eventImpl.getCorrelationId()); - encode(dataImpl.asMap(), msg); - send(msg, eventImpl.getReplyTo()); - - QPID_LOG(trace, "SENT Exception to=" << eventImpl.getReplyTo()); -} - - -void AgentSessionImpl::response(AgentEvent& event, const Data& data) -{ - AgentEventImpl& impl(AgentEventImplAccess::get(event)); - uint32_t count = impl.enqueueData(data); - if (count >= 8) - flushResponses(event, false); -} - - -void AgentSessionImpl::complete(AgentEvent& event) -{ - flushResponses(event, true); -} - - -void AgentSessionImpl::methodSuccess(AgentEvent& event) -{ - Message msg; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_RESPONSE; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_METHOD_RESPONSE; - headers[protocol::HEADER_KEY_AGENT] = agentName; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - AgentEventImpl& eventImpl(AgentEventImplAccess::get(event)); - - const Variant::Map& outArgs(eventImpl.getReturnArguments()); - const Variant::Map& outSubtypes(eventImpl.getReturnArgumentSubtypes()); - - map["_arguments"] = outArgs; - if (!outSubtypes.empty()) - map["_subtypes"] = outSubtypes; - - msg.setCorrelationId(eventImpl.getCorrelationId()); - encode(map, msg); - send(msg, eventImpl.getReplyTo()); - - QPID_LOG(trace, "SENT MethodResponse to=" << eventImpl.getReplyTo()); -} - - -void AgentSessionImpl::raiseEvent(const Data& data) -{ - int severity(SEV_NOTICE); - if (data.hasSchema()) { - const Schema& schema(DataImplAccess::get(data).getSchema()); - if (schema.isValid()) - severity = schema.getDefaultSeverity(); - } - - raiseEvent(data, severity); -} - - -void AgentSessionImpl::raiseEvent(const Data& data, int severity) -{ - Message msg; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - string subject("agent.ind.event"); - - if (data.hasSchema()) { - const SchemaId& schemaId(data.getSchemaId()); - if (schemaId.getType() != SCHEMA_TYPE_EVENT) - throw QmfException("Cannot call raiseEvent on data that is not an Event"); - subject = subject + "." + schemaId.getPackageName() + "." + schemaId.getName(); - } - - if (severity < SEV_EMERG || severity > SEV_DEBUG) - throw QmfException("Invalid severity value"); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_INDICATION; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_DATA_INDICATION; - headers[protocol::HEADER_KEY_CONTENT] = protocol::HEADER_CONTENT_EVENT; - headers[protocol::HEADER_KEY_AGENT] = agentName; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - msg.setSubject(subject); - - Variant::List list; - Variant::Map dataAsMap(DataImplAccess::get(data).asMap()); - dataAsMap["_severity"] = severity; - dataAsMap["_timestamp"] = uint64_t(qpid::sys::Duration(qpid::sys::EPOCH, qpid::sys::now())); - list.push_back(dataAsMap); - encode(list, msg); - topicSender.send(msg); - - QPID_LOG(trace, "SENT EventIndication to=" << topicSender.getName() << "/" << subject); -} - - -void AgentSessionImpl::checkOpen() -{ - if (opened) - throw QmfException("Operation must be performed before calling open()"); -} - - -void AgentSessionImpl::enqueueEvent(const AgentEvent& event) -{ - qpid::sys::Mutex::ScopedLock l(lock); - bool notify = eventQueue.empty(); - eventQueue.push(event); - if (notify) - cond.notify(); -} - - -void AgentSessionImpl::setAgentName() -{ - Variant::Map::iterator iter; - string vendor; - string product; - string instance; - - iter = attributes.find("_vendor"); - if (iter == attributes.end()) - attributes["_vendor"] = vendor; - else - vendor = iter->second.asString(); - - iter = attributes.find("_product"); - if (iter == attributes.end()) - attributes["_product"] = product; - else - product = iter->second.asString(); - - iter = attributes.find("_instance"); - if (iter == attributes.end()) { - instance = qpid::types::Uuid(true).str(); - attributes["_instance"] = instance; - } else - instance = iter->second.asString(); - - agentName = vendor + ":" + product + ":" + instance; - attributes["_name"] = agentName; -} - - -void AgentSessionImpl::handleLocateRequest(const Variant::List& predicate, const Message& msg) -{ - QPID_LOG(trace, "RCVD AgentLocateRequest from=" << msg.getReplyTo()); - - if (!predicate.empty()) { - Query agentQuery(QUERY_OBJECT); - agentQuery.setPredicate(predicate); - if (!agentQuery.matchesPredicate(attributes)) { - QPID_LOG(trace, "AgentLocate predicate does not match this agent, ignoring"); - return; - } - } - - Message reply; - Variant::Map map; - Variant::Map& headers(reply.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_INDICATION; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_AGENT_LOCATE_RESPONSE; - headers[protocol::HEADER_KEY_AGENT] = agentName; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - map["_values"] = attributes; - map["_values"].asMap()[protocol::AGENT_ATTR_TIMESTAMP] = uint64_t(qpid::sys::Duration(qpid::sys::EPOCH, qpid::sys::now())); - map["_values"].asMap()[protocol::AGENT_ATTR_HEARTBEAT_INTERVAL] = interval; - map["_values"].asMap()[protocol::AGENT_ATTR_EPOCH] = bootSequence; - map["_values"].asMap()[protocol::AGENT_ATTR_SCHEMA_UPDATED_TIMESTAMP] = schemaUpdateTime; - - encode(map, reply); - send(reply, msg.getReplyTo()); - QPID_LOG(trace, "SENT AgentLocateResponse to=" << msg.getReplyTo()); -} - - -void AgentSessionImpl::handleMethodRequest(const Variant::Map& content, const Message& msg) -{ - QPID_LOG(trace, "RCVD MethodRequest map=" << content << " from=" << msg.getReplyTo() << " cid=" << msg.getCorrelationId()); - - // - // Construct an AgentEvent to be sent to the application. - // - auto_ptr<AgentEventImpl> eventImpl(new AgentEventImpl(AGENT_METHOD)); - eventImpl->setUserId(msg.getUserId()); - eventImpl->setReplyTo(msg.getReplyTo()); - eventImpl->setCorrelationId(msg.getCorrelationId()); - - Variant::Map::const_iterator iter; - - iter = content.find("_method_name"); - if (iter == content.end()) { - AgentEvent event(eventImpl.release()); - raiseException(event, "Malformed MethodRequest: missing _method_name field"); - return; - } - eventImpl->setMethodName(iter->second.asString()); - - iter = content.find("_arguments"); - if (iter != content.end()) - eventImpl->setArguments(iter->second.asMap()); - - iter = content.find("_subtypes"); - if (iter != content.end()) - eventImpl->setArgumentSubtypes(iter->second.asMap()); - - iter = content.find("_object_id"); - if (iter != content.end()) { - DataAddr addr(new DataAddrImpl(iter->second.asMap())); - eventImpl->setDataAddr(addr); - DataIndex::const_iterator iter(globalIndex.find(addr)); - if (iter == globalIndex.end()) { - AgentEvent event(eventImpl.release()); - raiseException(event, "No data object found with the specified address"); - return; - } - - const Schema& schema(DataImplAccess::get(iter->second).getSchema()); - if (schema.isValid()) { - eventImpl->setSchema(schema); - for (Variant::Map::const_iterator aIter = eventImpl->getArguments().begin(); - aIter != eventImpl->getArguments().end(); aIter++) { - const Schema& schema(DataImplAccess::get(iter->second).getSchema()); - if (!SchemaImplAccess::get(schema).isValidMethodInArg(eventImpl->getMethodName(), aIter->first, aIter->second)) { - AgentEvent event(eventImpl.release()); - raiseException(event, "Invalid argument: " + aIter->first); - return; - } - } - } - } - - enqueueEvent(AgentEvent(eventImpl.release())); -} - - -void AgentSessionImpl::handleQueryRequest(const Variant::Map& content, const Message& msg) -{ - QPID_LOG(trace, "RCVD QueryRequest query=" << content << " from=" << msg.getReplyTo() << " cid=" << msg.getCorrelationId()); - - // - // Construct an AgentEvent to be sent to the application or directly handled by the agent. - // - auto_ptr<QueryImpl> queryImpl(new QueryImpl(content)); - auto_ptr<AgentEventImpl> eventImpl(new AgentEventImpl(AGENT_AUTH_QUERY)); - eventImpl->setUserId(msg.getUserId()); - eventImpl->setReplyTo(msg.getReplyTo()); - eventImpl->setCorrelationId(msg.getCorrelationId()); - eventImpl->setQuery(queryImpl.release()); - AgentEvent ae(eventImpl.release()); - - if (ae.getQuery().getTarget() == QUERY_SCHEMA_ID || ae.getQuery().getTarget() == QUERY_SCHEMA) { - handleSchemaRequest(ae); - return; - } - - if (autoAllowQueries) - authAccept(ae); - else - enqueueEvent(ae); -} - - -void AgentSessionImpl::handleSchemaRequest(AgentEvent& event) -{ - SchemaMap::const_iterator iter; - string error; - const Query& query(event.getQuery()); - - Message msg; - Variant::List content; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_RESPONSE; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_QUERY_RESPONSE; - headers[protocol::HEADER_KEY_AGENT] = agentName; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - { - qpid::sys::Mutex::ScopedLock l(lock); - if (query.getTarget() == QUERY_SCHEMA_ID) { - headers[protocol::HEADER_KEY_CONTENT] = "_schema_id"; - for (iter = schemata.begin(); iter != schemata.end(); iter++) - content.push_back(SchemaIdImplAccess::get(iter->first).asMap()); - } else if (query.getSchemaId().isValid()) { - headers[protocol::HEADER_KEY_CONTENT] = "_schema"; - iter = schemata.find(query.getSchemaId()); - if (iter != schemata.end()) - content.push_back(SchemaImplAccess::get(iter->second).asMap()); - } else { - error = "Invalid Schema Query: Requests for SCHEMA must supply a valid schema ID."; - } - } - - if (!error.empty()) { - raiseException(event, error); - return; - } - - AgentEventImpl& eventImpl(AgentEventImplAccess::get(event)); - - msg.setCorrelationId(eventImpl.getCorrelationId()); - encode(content, msg); - send(msg, eventImpl.getReplyTo()); - - QPID_LOG(trace, "SENT QueryResponse(Schema) to=" << eventImpl.getReplyTo()); -} - - -void AgentSessionImpl::handleV1SchemaRequest(qpid::management::Buffer& buffer, uint32_t seq, const Message& msg) -{ - string packageName; - string className; - uint8_t hashBits[16]; - - buffer.getShortString(packageName); - buffer.getShortString(className); - buffer.getBin128(hashBits); - - QPID_LOG(trace, "RCVD QMFv1 SchemaRequest for " << packageName << ":" << className); - - qpid::types::Uuid hash(hashBits); - map<SchemaId, Schema>::const_iterator iter; - string replyContent; - - SchemaId dataId(SCHEMA_TYPE_DATA, packageName, className); - dataId.setHash(hash); - - { - qpid::sys::Mutex::ScopedLock l(lock); - iter = schemata.find(dataId); - if (iter != schemata.end()) - replyContent = SchemaImplAccess::get(iter->second).asV1Content(seq); - else { - SchemaId eventId(SCHEMA_TYPE_EVENT, packageName, className); - eventId.setHash(hash); - iter = schemata.find(dataId); - if (iter != schemata.end()) - replyContent = SchemaImplAccess::get(iter->second).asV1Content(seq); - else - return; - } - } - - Message reply; - Variant::Map& headers(reply.getProperties()); - - headers[protocol::HEADER_KEY_AGENT] = agentName; - reply.setContent(replyContent); - - send(reply, msg.getReplyTo()); - QPID_LOG(trace, "SENT QMFv1 SchemaResponse to=" << msg.getReplyTo()); -} - - -void AgentSessionImpl::dispatch(Message msg) -{ - const Variant::Map& properties(msg.getProperties()); - Variant::Map::const_iterator iter; - - // - // If strict-security is enabled, make sure that reply-to address complies with the - // strict-security addressing pattern (i.e. start with 'qmf.<domain>.topic/direct-console.'). - // - if (strictSecurity && msg.getReplyTo()) { - if (msg.getReplyTo().getName() != topicBase || msg.getReplyTo().getSubject().find("direct-console.") != 0) { - QPID_LOG(warning, "Reply-to violates strict-security policy: " << msg.getReplyTo().str()); - return; - } - } - - iter = properties.find(protocol::HEADER_KEY_APP_ID); - if (iter != properties.end() && iter->second.asString() == protocol::HEADER_APP_ID_QMF) { - // - // Dispatch a QMFv2 formatted message - // - iter = properties.find(protocol::HEADER_KEY_OPCODE); - if (iter == properties.end()) { - QPID_LOG(trace, "Message received with no 'qmf.opcode' header"); - return; - } - - const string& opcode = iter->second.asString(); - - if (msg.getContentType() == "amqp/list") { - Variant::List content; - decode(msg, content); - - if (opcode == protocol::HEADER_OPCODE_AGENT_LOCATE_REQUEST) handleLocateRequest(content, msg); - else { - QPID_LOG(trace, "Unexpected QMFv2 opcode with 'amqp/list' content: " << opcode); - } - - } else if (msg.getContentType() == "amqp/map") { - Variant::Map content; - decode(msg, content); - - if (opcode == protocol::HEADER_OPCODE_METHOD_REQUEST) handleMethodRequest(content, msg); - else if (opcode == protocol::HEADER_OPCODE_QUERY_REQUEST) handleQueryRequest(content, msg); - else { - QPID_LOG(trace, "Unexpected QMFv2 opcode with 'amqp/map' content: " << opcode); - } - } else { - QPID_LOG(trace, "Unexpected QMFv2 content type. Expected amqp/list or amqp/map"); - } - - } else { - // - // Dispatch a QMFv1 formatted message - // - const string& body(msg.getContent()); - if (body.size() < 8) - return; - qpid::management::Buffer buffer(const_cast<char*>(body.c_str()), body.size()); - - if (buffer.getOctet() != 'A') return; - if (buffer.getOctet() != 'M') return; - if (buffer.getOctet() != '2') return; - char v1Opcode(buffer.getOctet()); - uint32_t seq(buffer.getLong()); - - if (v1Opcode == 'S') handleV1SchemaRequest(buffer, seq, msg); - else { - QPID_LOG(trace, "Unknown or Unsupported QMFv1 opcode: " << v1Opcode); - } - } -} - - -void AgentSessionImpl::sendHeartbeat() -{ - Message msg; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - std::stringstream address; - - address << "agent.ind.heartbeat"; - - // append .<vendor>.<product> to address key if present. - Variant::Map::const_iterator v; - if ((v = attributes.find("_vendor")) != attributes.end() && !v->second.getString().empty()) { - address << "." << v->second.getString(); - if ((v = attributes.find("_product")) != attributes.end() && !v->second.getString().empty()) { - address << "." << v->second.getString(); - } - } - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_INDICATION; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_AGENT_HEARTBEAT_INDICATION; - headers[protocol::HEADER_KEY_AGENT] = agentName; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - msg.setSubject(address.str()); - - map["_values"] = attributes; - map["_values"].asMap()[protocol::AGENT_ATTR_TIMESTAMP] = uint64_t(qpid::sys::Duration(qpid::sys::EPOCH, qpid::sys::now())); - map["_values"].asMap()[protocol::AGENT_ATTR_HEARTBEAT_INTERVAL] = interval; - map["_values"].asMap()[protocol::AGENT_ATTR_EPOCH] = bootSequence; - map["_values"].asMap()[protocol::AGENT_ATTR_SCHEMA_UPDATED_TIMESTAMP] = schemaUpdateTime; - - encode(map, msg); - topicSender.send(msg); - QPID_LOG(trace, "SENT AgentHeartbeat name=" << agentName); -} - - -void AgentSessionImpl::send(Message msg, const Address& to) -{ - Sender sender; - - if (strictSecurity && to.getName() != topicBase) { - QPID_LOG(warning, "Address violates strict-security policy: " << to); - return; - } - - if (to.getName() == directBase) { - msg.setSubject(to.getSubject()); - sender = directSender; - } else if (to.getName() == topicBase) { - msg.setSubject(to.getSubject()); - sender = topicSender; - } else - sender = session.createSender(to); - - sender.send(msg); -} - - -void AgentSessionImpl::flushResponses(AgentEvent& event, bool final) -{ - Message msg; - Variant::Map map; - Variant::Map& headers(msg.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_RESPONSE; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_QUERY_RESPONSE; - headers[protocol::HEADER_KEY_CONTENT] = protocol::HEADER_CONTENT_DATA; - headers[protocol::HEADER_KEY_AGENT] = agentName; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - if (!final) - headers[protocol::HEADER_KEY_PARTIAL] = Variant(); - - Variant::List body; - AgentEventImpl& eventImpl(AgentEventImplAccess::get(event)); - Data data(eventImpl.dequeueData()); - while (data.isValid()) { - DataImpl& dataImpl(DataImplAccess::get(data)); - body.push_back(dataImpl.asMap()); - data = eventImpl.dequeueData(); - } - - msg.setCorrelationId(eventImpl.getCorrelationId()); - encode(body, msg); - send(msg, eventImpl.getReplyTo()); - - QPID_LOG(trace, "SENT QueryResponse to=" << eventImpl.getReplyTo()); -} - - -void AgentSessionImpl::periodicProcessing(uint64_t seconds) -{ - // - // The granularity of this timer is seconds. Don't waste time looking for work if - // it's been less than a second since we last visited. - // - if (seconds == lastVisit) - return; - //uint64_t thisInterval(seconds - lastVisit); - lastVisit = seconds; - - // - // First time through, set lastHeartbeat to the current time. - // - if (lastHeartbeat == 0) - lastHeartbeat = seconds; - - // - // If the hearbeat interval has elapsed, send a heartbeat. - // - if (forceHeartbeat || (seconds - lastHeartbeat >= interval)) { - lastHeartbeat = seconds; - forceHeartbeat = false; - sendHeartbeat(); - } - - // - // TODO: process any active subscriptions on their intervals. - // -} - - -void AgentSessionImpl::run() -{ - QPID_LOG(debug, "AgentSession thread started for agent " << agentName); - - try { - while (!threadCanceled) { - periodicProcessing((uint64_t) qpid::sys::Duration(qpid::sys::EPOCH, qpid::sys::now()) / qpid::sys::TIME_SEC); - - Receiver rx; - bool valid = session.nextReceiver(rx, Duration::SECOND); - if (threadCanceled) - break; - if (valid) { - try { - dispatch(rx.fetch()); - } catch (qpid::types::Exception& e) { - QPID_LOG(error, "Exception caught in message dispatch: " << e.what()); - } - session.acknowledge(); - } - } - } catch (qpid::types::Exception& e) { - QPID_LOG(error, "Exception caught in message thread - exiting: " << e.what()); - enqueueEvent(AgentEvent(new AgentEventImpl(AGENT_THREAD_FAILED))); - } - - QPID_LOG(debug, "AgentSession thread exiting for agent " << agentName); -} - diff --git a/cpp/src/qmf/AgentSubscription.cpp b/cpp/src/qmf/AgentSubscription.cpp deleted file mode 100644 index 4dc5cb74a4..0000000000 --- a/cpp/src/qmf/AgentSubscription.cpp +++ /dev/null @@ -1,51 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/AgentSubscription.h" - -using namespace qmf; - -AgentSubscription::AgentSubscription(uint64_t _id, uint64_t _interval, uint64_t _life, - const std::string& _replyTo, const std::string& _cid, Query _query) : - id(_id), interval(_interval), lifetime(_life), timeSincePublish(0), timeSinceKeepalive(0), - replyTo(_replyTo), cid(_cid), query(_query) -{ -} - - -AgentSubscription::~AgentSubscription() -{ -} - - -bool AgentSubscription::tick(uint64_t seconds) -{ - timeSinceKeepalive += seconds; - if (timeSinceKeepalive >= lifetime) - return false; - - timeSincePublish += seconds; - if (timeSincePublish >= interval) { - } - - return true; -} - diff --git a/cpp/src/qmf/AgentSubscription.h b/cpp/src/qmf/AgentSubscription.h deleted file mode 100644 index 01e8f43e9f..0000000000 --- a/cpp/src/qmf/AgentSubscription.h +++ /dev/null @@ -1,52 +0,0 @@ -#ifndef _QMF_AGENT_SUBSCRIPTION_H_ -#define _QMF_AGENT_SUBSCRIPTION_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/sys/IntegerTypes.h" -#include "qpid/types/Variant.h" -#include "qmf/Query.h" -#include "qmf/Data.h" -#include <boost/shared_ptr.hpp> - -namespace qmf { - class AgentSubscription { - public: - AgentSubscription(uint64_t _id, uint64_t _interval, uint64_t _life, - const std::string& _replyTo, const std::string& _cid, Query _query); - ~AgentSubscription(); - bool tick(uint64_t seconds); - void keepalive() { timeSinceKeepalive = 0; } - - private: - uint64_t id; - uint64_t interval; - uint64_t lifetime; - uint64_t timeSincePublish; - uint64_t timeSinceKeepalive; - const std::string replyTo; - const std::string cid; - Query query; - }; - -} - -#endif diff --git a/cpp/src/qmf/ConsoleEvent.cpp b/cpp/src/qmf/ConsoleEvent.cpp deleted file mode 100644 index b2a5e321c7..0000000000 --- a/cpp/src/qmf/ConsoleEvent.cpp +++ /dev/null @@ -1,82 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/ConsoleEventImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" - -using namespace std; -using namespace qmf; -using qpid::types::Variant; - -typedef PrivateImplRef<ConsoleEvent> PI; - -ConsoleEvent::ConsoleEvent(ConsoleEventImpl* impl) { PI::ctor(*this, impl); } -ConsoleEvent::ConsoleEvent(const ConsoleEvent& s) : qmf::Handle<ConsoleEventImpl>() { PI::copy(*this, s); } -ConsoleEvent::~ConsoleEvent() { PI::dtor(*this); } -ConsoleEvent& ConsoleEvent::operator=(const ConsoleEvent& s) { return PI::assign(*this, s); } - -ConsoleEventCode ConsoleEvent::getType() const { return impl->getType(); } -uint32_t ConsoleEvent::getCorrelator() const { return impl->getCorrelator(); } -Agent ConsoleEvent::getAgent() const { return impl->getAgent(); } -AgentDelReason ConsoleEvent::getAgentDelReason() const { return impl->getAgentDelReason(); } -uint32_t ConsoleEvent::getSchemaIdCount() const { return impl->getSchemaIdCount(); } -SchemaId ConsoleEvent::getSchemaId(uint32_t i) const { return impl->getSchemaId(i); } -uint32_t ConsoleEvent::getDataCount() const { return impl->getDataCount(); } -Data ConsoleEvent::getData(uint32_t i) const { return impl->getData(i); } -bool ConsoleEvent::isFinal() const { return impl->isFinal(); } -const Variant::Map& ConsoleEvent::getArguments() const { return impl->getArguments(); } -int ConsoleEvent::getSeverity() const { return impl->getSeverity(); } -uint64_t ConsoleEvent::getTimestamp() const { return impl->getTimestamp(); } - - -SchemaId ConsoleEventImpl::getSchemaId(uint32_t i) const -{ - uint32_t count = 0; - for (list<SchemaId>::const_iterator iter = newSchemaIds.begin(); iter != newSchemaIds.end(); iter++) { - if (count++ == i) - return *iter; - } - throw IndexOutOfRange(); -} - - -Data ConsoleEventImpl::getData(uint32_t i) const -{ - uint32_t count = 0; - for (list<Data>::const_iterator iter = dataList.begin(); iter != dataList.end(); iter++) { - if (count++ == i) - return *iter; - } - throw IndexOutOfRange(); -} - - -ConsoleEventImpl& ConsoleEventImplAccess::get(ConsoleEvent& item) -{ - return *item.impl; -} - - -const ConsoleEventImpl& ConsoleEventImplAccess::get(const ConsoleEvent& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/ConsoleEventImpl.h b/cpp/src/qmf/ConsoleEventImpl.h deleted file mode 100644 index 9843971456..0000000000 --- a/cpp/src/qmf/ConsoleEventImpl.h +++ /dev/null @@ -1,84 +0,0 @@ -#ifndef _QMF_CONSOLE_EVENT_IMPL_H_ -#define _QMF_CONSOLE_EVENT_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/ConsoleEvent.h" -#include "qmf/Agent.h" -#include "qmf/Data.h" -#include "qpid/types/Variant.h" -#include <list> - -namespace qmf { - class ConsoleEventImpl : public virtual qpid::RefCounted { - public: - // - // Impl-only methods - // - ConsoleEventImpl(ConsoleEventCode e, AgentDelReason r = AGENT_DEL_AGED) : - eventType(e), delReason(r), correlator(0), final(false) {} - void setCorrelator(uint32_t c) { correlator = c; } - void setAgent(const Agent& a) { agent = a; } - void addData(const Data& d) { dataList.push_back(Data(d)); } - void addSchemaId(const SchemaId& s) { newSchemaIds.push_back(SchemaId(s)); } - void setFinal() { final = true; } - void setArguments(const qpid::types::Variant::Map& a) { arguments = a; } - void setSeverity(int s) { severity = s; } - void setTimestamp(uint64_t t) { timestamp = t; } - - // - // Methods from API handle - // - ConsoleEventCode getType() const { return eventType; } - uint32_t getCorrelator() const { return correlator; } - Agent getAgent() const { return agent; } - AgentDelReason getAgentDelReason() const { return delReason; } - uint32_t getSchemaIdCount() const { return newSchemaIds.size(); } - SchemaId getSchemaId(uint32_t) const; - uint32_t getDataCount() const { return dataList.size(); } - Data getData(uint32_t i) const; - bool isFinal() const { return final; } - const qpid::types::Variant::Map& getArguments() const { return arguments; } - int getSeverity() const { return severity; } - uint64_t getTimestamp() const { return timestamp; } - - private: - const ConsoleEventCode eventType; - const AgentDelReason delReason; - uint32_t correlator; - Agent agent; - bool final; - std::list<Data> dataList; - std::list<SchemaId> newSchemaIds; - qpid::types::Variant::Map arguments; - int severity; - uint64_t timestamp; - }; - - struct ConsoleEventImplAccess - { - static ConsoleEventImpl& get(ConsoleEvent&); - static const ConsoleEventImpl& get(const ConsoleEvent&); - }; -} - -#endif diff --git a/cpp/src/qmf/ConsoleSession.cpp b/cpp/src/qmf/ConsoleSession.cpp deleted file mode 100644 index 7b839930e1..0000000000 --- a/cpp/src/qmf/ConsoleSession.cpp +++ /dev/null @@ -1,618 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/PrivateImplRef.h" -#include "qmf/ConsoleSessionImpl.h" -#include "qmf/AgentImpl.h" -#include "qmf/SchemaId.h" -#include "qmf/SchemaImpl.h" -#include "qmf/ConsoleEventImpl.h" -#include "qmf/constants.h" -#include "qpid/log/Statement.h" -#include "qpid/messaging/AddressParser.h" -#include "qpid/messaging/Sender.h" -#include "qpid/messaging/Receiver.h" - -using namespace std; -using namespace qmf; -using qpid::messaging::Address; -using qpid::messaging::Connection; -using qpid::messaging::Receiver; -using qpid::messaging::Sender; -using qpid::messaging::Duration; -using qpid::messaging::Message; -using qpid::types::Variant; - -typedef qmf::PrivateImplRef<ConsoleSession> PI; - -ConsoleSession::ConsoleSession(ConsoleSessionImpl* impl) { PI::ctor(*this, impl); } -ConsoleSession::ConsoleSession(const ConsoleSession& s) : qmf::Handle<ConsoleSessionImpl>() { PI::copy(*this, s); } -ConsoleSession::~ConsoleSession() { PI::dtor(*this); } -ConsoleSession& ConsoleSession::operator=(const ConsoleSession& s) { return PI::assign(*this, s); } - -ConsoleSession::ConsoleSession(Connection& c, const string& o) { PI::ctor(*this, new ConsoleSessionImpl(c, o)); } -void ConsoleSession::setDomain(const string& d) { impl->setDomain(d); } -void ConsoleSession::setAgentFilter(const string& f) { impl->setAgentFilter(f); } -void ConsoleSession::open() { impl->open(); } -void ConsoleSession::close() { impl->close(); } -bool ConsoleSession::nextEvent(ConsoleEvent& e, Duration t) { return impl->nextEvent(e, t); } -int ConsoleSession::pendingEvents() const { return impl->pendingEvents(); } -uint32_t ConsoleSession::getAgentCount() const { return impl->getAgentCount(); } -Agent ConsoleSession::getAgent(uint32_t i) const { return impl->getAgent(i); } -Agent ConsoleSession::getConnectedBrokerAgent() const { return impl->getConnectedBrokerAgent(); } -Subscription ConsoleSession::subscribe(const Query& q, const string& f, const string& o) { return impl->subscribe(q, f, o); } -Subscription ConsoleSession::subscribe(const string& q, const string& f, const string& o) { return impl->subscribe(q, f, o); } - -//======================================================================================== -// Impl Method Bodies -//======================================================================================== - -ConsoleSessionImpl::ConsoleSessionImpl(Connection& c, const string& options) : - connection(c), domain("default"), maxAgentAgeMinutes(5), - opened(false), thread(0), threadCanceled(false), lastVisit(0), lastAgePass(0), - connectedBrokerInAgentList(false), schemaCache(new SchemaCache()) -{ - if (!options.empty()) { - qpid::messaging::AddressParser parser(options); - Variant::Map optMap; - Variant::Map::const_iterator iter; - - parser.parseMap(optMap); - - iter = optMap.find("domain"); - if (iter != optMap.end()) - domain = iter->second.asString(); - - iter = optMap.find("max-agent-age"); - if (iter != optMap.end()) - maxAgentAgeMinutes = iter->second.asUint32(); - - iter = optMap.find("listen-on-direct"); - if (iter != optMap.end()) - listenOnDirect = iter->second.asBool(); - - iter = optMap.find("strict-security"); - if (iter != optMap.end()) - strictSecurity = iter->second.asBool(); - } -} - - -ConsoleSessionImpl::~ConsoleSessionImpl() -{ - if (opened) - close(); -} - - -void ConsoleSessionImpl::setAgentFilter(const string& predicate) -{ - agentQuery = Query(QUERY_OBJECT, predicate); - - // - // Purge the agent list of any agents that don't match the filter. - // - { - qpid::sys::Mutex::ScopedLock l(lock); - map<string, Agent> toDelete; - for (map<string, Agent>::iterator iter = agents.begin(); iter != agents.end(); iter++) - if (!agentQuery.matchesPredicate(iter->second.getAttributes())) { - toDelete[iter->first] = iter->second; - if (iter->second.getName() == connectedBrokerAgent.getName()) - connectedBrokerInAgentList = false; - } - - for (map<string, Agent>::iterator iter = toDelete.begin(); iter != toDelete.end(); iter++) { - agents.erase(iter->first); - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_AGENT_DEL, AGENT_DEL_FILTER)); - eventImpl->setAgent(iter->second); - enqueueEventLH(eventImpl.release()); - } - - if (!connectedBrokerInAgentList && connectedBrokerAgent.isValid() && - agentQuery.matchesPredicate(connectedBrokerAgent.getAttributes())) { - agents[connectedBrokerAgent.getName()] = connectedBrokerAgent; - connectedBrokerInAgentList = true; - - // - // Enqueue a notification of the new agent. - // - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_AGENT_ADD)); - eventImpl->setAgent(connectedBrokerAgent); - enqueueEventLH(ConsoleEvent(eventImpl.release())); - } - } - - // - // Broadcast an agent locate request with our new criteria. - // - if (opened) - sendAgentLocate(); -} - - -void ConsoleSessionImpl::open() -{ - if (opened) - throw QmfException("The session is already open"); - - // Establish messaging addresses - directBase = "qmf." + domain + ".direct"; - topicBase = "qmf." + domain + ".topic"; - - string myKey("direct-console." + qpid::types::Uuid(true).str()); - - replyAddress = Address(topicBase + "/" + myKey + ";{node:{type:topic}}"); - - // Create AMQP session, receivers, and senders - session = connection.createSession(); - Receiver directRx = session.createReceiver(replyAddress); - Receiver topicRx = session.createReceiver(topicBase + "/agent.#"); // TODO: be more discriminating - if (!strictSecurity) { - Receiver legacyRx = session.createReceiver("amq.direct/" + myKey + ";{node:{type:topic}}"); - legacyRx.setCapacity(64); - directSender = session.createSender(directBase + ";{create:never,node:{type:topic}}"); - directSender.setCapacity(128); - } - - directRx.setCapacity(64); - topicRx.setCapacity(128); - - topicSender = session.createSender(topicBase + ";{create:never,node:{type:topic}}"); - - topicSender.setCapacity(128); - - // Start the receiver thread - threadCanceled = false; - thread = new qpid::sys::Thread(*this); - - // Send an agent_locate to direct address 'broker' to identify the connected-broker-agent. - sendBrokerLocate(); - if (agentQuery) - sendAgentLocate(); - - opened = true; -} - - -void ConsoleSessionImpl::close() -{ - if (!opened) - throw QmfException("The session is already closed"); - - // Stop and join the receiver thread - threadCanceled = true; - thread->join(); - delete thread; - - // Close the AMQP session - session.close(); - opened = false; -} - - -bool ConsoleSessionImpl::nextEvent(ConsoleEvent& event, Duration timeout) -{ - uint64_t milliseconds = timeout.getMilliseconds(); - qpid::sys::Mutex::ScopedLock l(lock); - - if (eventQueue.empty() && milliseconds > 0) - cond.wait(lock, qpid::sys::AbsTime(qpid::sys::now(), - qpid::sys::Duration(milliseconds * qpid::sys::TIME_MSEC))); - - if (!eventQueue.empty()) { - event = eventQueue.front(); - eventQueue.pop(); - return true; - } - - return false; -} - - -int ConsoleSessionImpl::pendingEvents() const -{ - qpid::sys::Mutex::ScopedLock l(lock); - return eventQueue.size(); -} - - -uint32_t ConsoleSessionImpl::getAgentCount() const -{ - qpid::sys::Mutex::ScopedLock l(lock); - return agents.size(); -} - - -Agent ConsoleSessionImpl::getAgent(uint32_t i) const -{ - qpid::sys::Mutex::ScopedLock l(lock); - uint32_t count = 0; - for (map<string, Agent>::const_iterator iter = agents.begin(); iter != agents.end(); iter++) - if (count++ == i) - return iter->second; - throw IndexOutOfRange(); -} - - -Subscription ConsoleSessionImpl::subscribe(const Query&, const string&, const string&) -{ - return Subscription(); -} - - -Subscription ConsoleSessionImpl::subscribe(const string&, const string&, const string&) -{ - return Subscription(); -} - - -void ConsoleSessionImpl::enqueueEvent(const ConsoleEvent& event) -{ - qpid::sys::Mutex::ScopedLock l(lock); - enqueueEventLH(event); -} - - -void ConsoleSessionImpl::enqueueEventLH(const ConsoleEvent& event) -{ - bool notify = eventQueue.empty(); - eventQueue.push(event); - if (notify) - cond.notify(); -} - - -void ConsoleSessionImpl::dispatch(Message msg) -{ - const Variant::Map& properties(msg.getProperties()); - Variant::Map::const_iterator iter; - Variant::Map::const_iterator oiter; - - oiter = properties.find(protocol::HEADER_KEY_OPCODE); - iter = properties.find(protocol::HEADER_KEY_APP_ID); - if (iter == properties.end()) - iter = properties.find("app_id"); - if (iter != properties.end() && iter->second.asString() == protocol::HEADER_APP_ID_QMF && oiter != properties.end()) { - // - // Dispatch a QMFv2 formatted message - // - const string& opcode = oiter->second.asString(); - - iter = properties.find(protocol::HEADER_KEY_AGENT); - if (iter == properties.end()) { - QPID_LOG(trace, "Message received with no 'qmf.agent' header"); - return; - } - const string& agentName = iter->second.asString(); - - Agent agent; - { - qpid::sys::Mutex::ScopedLock l(lock); - map<string, Agent>::iterator aIter = agents.find(agentName); - if (aIter != agents.end()) { - agent = aIter->second; - AgentImplAccess::get(agent).touch(); - } - } - - if (msg.getContentType() == "amqp/map" && - (opcode == protocol::HEADER_OPCODE_AGENT_HEARTBEAT_INDICATION || opcode == protocol::HEADER_OPCODE_AGENT_LOCATE_RESPONSE)) { - // - // This is the one case where it's ok (necessary actually) to receive a QMFv2 - // message from an unknown agent (how else are they going to get known?) - // - Variant::Map content; - decode(msg, content); - handleAgentUpdate(agentName, content, msg); - return; - } - - if (!agent.isValid()) - return; - - AgentImpl& agentImpl(AgentImplAccess::get(agent)); - - if (msg.getContentType() == "amqp/map") { - Variant::Map content; - decode(msg, content); - - if (opcode == protocol::HEADER_OPCODE_EXCEPTION) agentImpl.handleException(content, msg); - else if (opcode == protocol::HEADER_OPCODE_METHOD_RESPONSE) agentImpl.handleMethodResponse(content, msg); - else - QPID_LOG(error, "Received a map-formatted QMFv2 message with opcode=" << opcode); - - return; - } - - if (msg.getContentType() == "amqp/list") { - Variant::List content; - decode(msg, content); - - if (opcode == protocol::HEADER_OPCODE_QUERY_RESPONSE) agentImpl.handleQueryResponse(content, msg); - else if (opcode == protocol::HEADER_OPCODE_DATA_INDICATION) agentImpl.handleDataIndication(content, msg); - else - QPID_LOG(error, "Received a list-formatted QMFv2 message with opcode=" << opcode); - - return; - } - } else { - // - // Dispatch a QMFv1 formatted message - // - const string& body(msg.getContent()); - if (body.size() < 8) - return; - qpid::management::Buffer buffer(const_cast<char*>(body.c_str()), body.size()); - - if (buffer.getOctet() != 'A') return; - if (buffer.getOctet() != 'M') return; - if (buffer.getOctet() != '2') return; - char v1Opcode(buffer.getOctet()); - uint32_t seq(buffer.getLong()); - - if (v1Opcode == 's') handleV1SchemaResponse(buffer, seq, msg); - else { - QPID_LOG(trace, "Unknown or Unsupported QMFv1 opcode: " << v1Opcode); - } - } -} - - -void ConsoleSessionImpl::sendBrokerLocate() -{ - Message msg; - Variant::Map& headers(msg.getProperties()); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_REQUEST; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_AGENT_LOCATE_REQUEST; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - msg.setReplyTo(replyAddress); - msg.setCorrelationId("broker-locate"); - msg.setSubject("broker"); - - Sender sender = session.createSender(directBase + ";{create:never,node:{type:topic}}"); - sender.send(msg); - sender.close(); - - QPID_LOG(trace, "SENT AgentLocate to broker"); -} - - -void ConsoleSessionImpl::sendAgentLocate() -{ - Message msg; - Variant::Map& headers(msg.getProperties()); - static const string subject("console.request.agent_locate"); - - headers[protocol::HEADER_KEY_METHOD] = protocol::HEADER_METHOD_REQUEST; - headers[protocol::HEADER_KEY_OPCODE] = protocol::HEADER_OPCODE_AGENT_LOCATE_REQUEST; - headers[protocol::HEADER_KEY_APP_ID] = protocol::HEADER_APP_ID_QMF; - - msg.setReplyTo(replyAddress); - msg.setCorrelationId("agent-locate"); - msg.setSubject(subject); - encode(agentQuery.getPredicate(), msg); - - topicSender.send(msg); - - QPID_LOG(trace, "SENT AgentLocate to=" << topicSender.getName() << "/" << subject); -} - - -void ConsoleSessionImpl::handleAgentUpdate(const string& agentName, const Variant::Map& content, const Message& msg) -{ - Variant::Map::const_iterator iter; - Agent agent; - uint32_t epoch(0); - string cid(msg.getCorrelationId()); - - iter = content.find("_values"); - if (iter == content.end()) - return; - const Variant::Map& in_attrs(iter->second.asMap()); - Variant::Map attrs; - - // - // Copy the map from the message to "attrs". Translate any old-style - // keys to their new key values in the process. - // - for (iter = in_attrs.begin(); iter != in_attrs.end(); iter++) { - if (iter->first == "epoch") - attrs[protocol::AGENT_ATTR_EPOCH] = iter->second; - else if (iter->first == "timestamp") - attrs[protocol::AGENT_ATTR_TIMESTAMP] = iter->second; - else if (iter->first == "heartbeat_interval") - attrs[protocol::AGENT_ATTR_HEARTBEAT_INTERVAL] = iter->second; - else - attrs[iter->first] = iter->second; - } - - iter = attrs.find(protocol::AGENT_ATTR_EPOCH); - if (iter != attrs.end()) - epoch = iter->second.asUint32(); - - if (cid == "broker-locate") { - qpid::sys::Mutex::ScopedLock l(lock); - auto_ptr<AgentImpl> impl(new AgentImpl(agentName, epoch, *this)); - for (iter = attrs.begin(); iter != attrs.end(); iter++) - if (iter->first != protocol::AGENT_ATTR_EPOCH) - impl->setAttribute(iter->first, iter->second); - agent = Agent(impl.release()); - connectedBrokerAgent = agent; - if (!agentQuery || agentQuery.matchesPredicate(attrs)) { - connectedBrokerInAgentList = true; - agents[agentName] = agent; - - // - // Enqueue a notification of the new agent. - // - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_AGENT_ADD)); - eventImpl->setAgent(agent); - enqueueEventLH(ConsoleEvent(eventImpl.release())); - } - return; - } - - // - // Check this agent against the agent filter. Exit if it doesn't match. - // (only if this isn't the connected broker agent) - // - if (agentQuery && (!agentQuery.matchesPredicate(attrs))) - return; - - QPID_LOG(trace, "RCVD AgentHeartbeat from an agent matching our filter: " << agentName); - - { - qpid::sys::Mutex::ScopedLock l(lock); - map<string, Agent>::iterator aIter = agents.find(agentName); - if (aIter == agents.end()) { - // - // This is a new agent. We have no current record of its existence. - // - auto_ptr<AgentImpl> impl(new AgentImpl(agentName, epoch, *this)); - for (iter = attrs.begin(); iter != attrs.end(); iter++) - if (iter->first != protocol::AGENT_ATTR_EPOCH) - impl->setAttribute(iter->first, iter->second); - agent = Agent(impl.release()); - agents[agentName] = agent; - - // - // Enqueue a notification of the new agent. - // - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_AGENT_ADD)); - eventImpl->setAgent(agent); - enqueueEventLH(ConsoleEvent(eventImpl.release())); - } else { - // - // This is a refresh of an agent we are already tracking. - // - bool detectedRestart(false); - agent = aIter->second; - AgentImpl& impl(AgentImplAccess::get(agent)); - impl.touch(); - if (impl.getEpoch() != epoch) { - // - // The agent has restarted since the last time we heard from it. - // Enqueue a notification. - // - impl.setEpoch(epoch); - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_AGENT_RESTART)); - eventImpl->setAgent(agent); - enqueueEventLH(ConsoleEvent(eventImpl.release())); - detectedRestart = true; - } - - iter = attrs.find(protocol::AGENT_ATTR_SCHEMA_UPDATED_TIMESTAMP); - if (iter != attrs.end()) { - uint64_t ts(iter->second.asUint64()); - if (ts > impl.getAttribute(protocol::AGENT_ATTR_SCHEMA_UPDATED_TIMESTAMP).asUint64()) { - // - // The agent has added new schema entries since we last heard from it. - // Update the attribute and, if this doesn't accompany a restart, enqueue a notification. - // - if (!detectedRestart) { - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_AGENT_SCHEMA_UPDATE)); - eventImpl->setAgent(agent); - enqueueEventLH(ConsoleEvent(eventImpl.release())); - } - impl.setAttribute(protocol::AGENT_ATTR_SCHEMA_UPDATED_TIMESTAMP, iter->second); - } - } - } - } -} - - -void ConsoleSessionImpl::handleV1SchemaResponse(qpid::management::Buffer& buffer, uint32_t, const Message&) -{ - QPID_LOG(trace, "RCVD V1SchemaResponse"); - Schema schema(new SchemaImpl(buffer)); - schemaCache->declareSchema(schema); -} - - -void ConsoleSessionImpl::periodicProcessing(uint64_t seconds) -{ - // - // The granularity of this timer is seconds. Don't waste time looking for work if - // it's been less than a second since we last visited. - // - if (seconds == lastVisit) - return; - lastVisit = seconds; - - // - // Handle the aging of agent records - // - if (lastAgePass == 0) - lastAgePass = seconds; - if (seconds - lastAgePass >= 60) { - lastAgePass = seconds; - map<string, Agent> toDelete; - qpid::sys::Mutex::ScopedLock l(lock); - - for (map<string, Agent>::iterator iter = agents.begin(); iter != agents.end(); iter++) - if ((iter->second.getName() != connectedBrokerAgent.getName()) && - (AgentImplAccess::get(iter->second).age() > maxAgentAgeMinutes)) - toDelete[iter->first] = iter->second; - - for (map<string, Agent>::iterator iter = toDelete.begin(); iter != toDelete.end(); iter++) { - agents.erase(iter->first); - auto_ptr<ConsoleEventImpl> eventImpl(new ConsoleEventImpl(CONSOLE_AGENT_DEL, AGENT_DEL_AGED)); - eventImpl->setAgent(iter->second); - enqueueEventLH(eventImpl.release()); - } - } -} - - -void ConsoleSessionImpl::run() -{ - QPID_LOG(debug, "ConsoleSession thread started"); - - try { - while (!threadCanceled) { - periodicProcessing((uint64_t) qpid::sys::Duration(qpid::sys::EPOCH, qpid::sys::now()) / - qpid::sys::TIME_SEC); - - Receiver rx; - bool valid = session.nextReceiver(rx, Duration::SECOND); - if (threadCanceled) - break; - if (valid) { - try { - dispatch(rx.fetch()); - } catch (qpid::types::Exception& e) { - QPID_LOG(error, "Exception caught in message dispatch: " << e.what()); - } - session.acknowledge(); - } - } - } catch (qpid::types::Exception& e) { - QPID_LOG(error, "Exception caught in message thread - exiting: " << e.what()); - enqueueEvent(ConsoleEvent(new ConsoleEventImpl(CONSOLE_THREAD_FAILED))); - } - - QPID_LOG(debug, "ConsoleSession thread exiting"); -} - diff --git a/cpp/src/qmf/ConsoleSessionImpl.h b/cpp/src/qmf/ConsoleSessionImpl.h deleted file mode 100644 index 411b3f016a..0000000000 --- a/cpp/src/qmf/ConsoleSessionImpl.h +++ /dev/null @@ -1,108 +0,0 @@ -#ifndef _QMF_CONSOLE_SESSION_IMPL_H_ -#define _QMF_CONSOLE_SESSION_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/ConsoleSession.h" -#include "qmf/AgentImpl.h" -#include "qmf/SchemaId.h" -#include "qmf/Schema.h" -#include "qmf/ConsoleEventImpl.h" -#include "qmf/SchemaCache.h" -#include "qmf/Query.h" -#include "qpid/sys/Mutex.h" -#include "qpid/sys/Condition.h" -#include "qpid/sys/Thread.h" -#include "qpid/sys/Runnable.h" -#include "qpid/log/Statement.h" -#include "qpid/messaging/Message.h" -#include "qpid/messaging/Connection.h" -#include "qpid/messaging/Session.h" -#include "qpid/messaging/Sender.h" -#include "qpid/messaging/Address.h" -#include "qpid/management/Buffer.h" -#include "qpid/types/Variant.h" -#include <map> -#include <queue> - -namespace qmf { - class ConsoleSessionImpl : public virtual qpid::RefCounted, public qpid::sys::Runnable { - public: - ~ConsoleSessionImpl(); - - // - // Methods from API handle - // - ConsoleSessionImpl(qpid::messaging::Connection& c, const std::string& o); - void setDomain(const std::string& d) { domain = d; } - void setAgentFilter(const std::string& f); - void open(); - void close(); - bool nextEvent(ConsoleEvent& e, qpid::messaging::Duration t); - int pendingEvents() const; - uint32_t getAgentCount() const; - Agent getAgent(uint32_t i) const; - Agent getConnectedBrokerAgent() const { return connectedBrokerAgent; } - Subscription subscribe(const Query&, const std::string& agentFilter, const std::string& options); - Subscription subscribe(const std::string&, const std::string& agentFilter, const std::string& options); - - protected: - mutable qpid::sys::Mutex lock; - qpid::sys::Condition cond; - qpid::messaging::Connection connection; - qpid::messaging::Session session; - qpid::messaging::Sender directSender; - qpid::messaging::Sender topicSender; - std::string domain; - uint32_t maxAgentAgeMinutes; - bool listenOnDirect; - bool strictSecurity; - Query agentQuery; - bool opened; - std::queue<ConsoleEvent> eventQueue; - qpid::sys::Thread* thread; - bool threadCanceled; - uint64_t lastVisit; - uint64_t lastAgePass; - std::map<std::string, Agent> agents; - Agent connectedBrokerAgent; - bool connectedBrokerInAgentList; - qpid::messaging::Address replyAddress; - std::string directBase; - std::string topicBase; - boost::shared_ptr<SchemaCache> schemaCache; - - void enqueueEvent(const ConsoleEvent&); - void enqueueEventLH(const ConsoleEvent&); - void dispatch(qpid::messaging::Message); - void sendBrokerLocate(); - void sendAgentLocate(); - void handleAgentUpdate(const std::string&, const qpid::types::Variant::Map&, const qpid::messaging::Message&); - void handleV1SchemaResponse(qpid::management::Buffer&, uint32_t, const qpid::messaging::Message&); - void periodicProcessing(uint64_t); - void run(); - - friend class AgentImpl; - }; -} - -#endif diff --git a/cpp/src/qmf/Data.cpp b/cpp/src/qmf/Data.cpp deleted file mode 100644 index c503bab445..0000000000 --- a/cpp/src/qmf/Data.cpp +++ /dev/null @@ -1,130 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/DataImpl.h" -#include "qmf/DataAddrImpl.h" -#include "qmf/SchemaImpl.h" -#include "qmf/SchemaIdImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/SchemaProperty.h" - -using namespace std; -using namespace qmf; -using qpid::types::Variant; - -typedef PrivateImplRef<Data> PI; - -Data::Data(DataImpl* impl) { PI::ctor(*this, impl); } -Data::Data(const Data& s) : qmf::Handle<DataImpl>() { PI::copy(*this, s); } -Data::~Data() { PI::dtor(*this); } -Data& Data::operator=(const Data& s) { return PI::assign(*this, s); } - -Data::Data(const Schema& s) { PI::ctor(*this, new DataImpl(s)); } -void Data::setAddr(const DataAddr& a) { impl->setAddr(a); } -void Data::setProperty(const string& k, const qpid::types::Variant& v) { impl->setProperty(k, v); } -void Data::overwriteProperties(const qpid::types::Variant::Map& m) { impl->overwriteProperties(m); } -bool Data::hasSchema() const { return impl->hasSchema(); } -bool Data::hasAddr() const { return impl->hasAddr(); } -const SchemaId& Data::getSchemaId() const { return impl->getSchemaId(); } -const DataAddr& Data::getAddr() const { return impl->getAddr(); } -const Variant& Data::getProperty(const string& k) const { return impl->getProperty(k); } -const Variant::Map& Data::getProperties() const { return impl->getProperties(); } -bool Data::hasAgent() const { return impl->hasAgent(); } -const Agent& Data::getAgent() const { return impl->getAgent(); } - - -void DataImpl::overwriteProperties(const Variant::Map& m) { - for (Variant::Map::const_iterator iter = m.begin(); iter != m.end(); iter++) - properties[iter->first] = iter->second; -} - -const Variant& DataImpl::getProperty(const string& k) const { - Variant::Map::const_iterator iter = properties.find(k); - if (iter == properties.end()) - throw KeyNotFound(k); - return iter->second; -} - - -DataImpl::DataImpl(const qpid::types::Variant::Map& map, const Agent& a) -{ - Variant::Map::const_iterator iter; - - agent = a; - - iter = map.find("_values"); - if (iter != map.end()) - properties = iter->second.asMap(); - - iter = map.find("_object_id"); - if (iter != map.end()) - dataAddr = DataAddr(new DataAddrImpl(iter->second.asMap())); - - iter = map.find("_schema_id"); - if (iter != map.end()) - schemaId = SchemaId(new SchemaIdImpl(iter->second.asMap())); -} - - -Variant::Map DataImpl::asMap() const -{ - Variant::Map result; - - result["_values"] = properties; - - if (hasAddr()) { - const DataAddrImpl& aImpl(DataAddrImplAccess::get(getAddr())); - result["_object_id"] = aImpl.asMap(); - } - - if (hasSchema()) { - const SchemaIdImpl& sImpl(SchemaIdImplAccess::get(getSchemaId())); - result["_schema_id"] = sImpl.asMap(); - } - - return result; -} - - -void DataImpl::setProperty(const std::string& k, const qpid::types::Variant& v) -{ - if (schema.isValid()) { - // - // If we have a valid schema, make sure that the property is included in the - // schema and that the variant type is compatible with the schema type. - // - if (!SchemaImplAccess::get(schema).isValidProperty(k, v)) - throw QmfException("Property '" + k + "' either not in the schema or value is of incompatible type"); - } - properties[k] = v; -} - - -DataImpl& DataImplAccess::get(Data& item) -{ - return *item.impl; -} - - -const DataImpl& DataImplAccess::get(const Data& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/DataAddr.cpp b/cpp/src/qmf/DataAddr.cpp deleted file mode 100644 index fb51d5787f..0000000000 --- a/cpp/src/qmf/DataAddr.cpp +++ /dev/null @@ -1,106 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/DataAddrImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/DataAddr.h" -#include <iostream> - -using namespace std; -using namespace qmf; -using qpid::types::Variant; - -typedef PrivateImplRef<DataAddr> PI; - -DataAddr::DataAddr(DataAddrImpl* impl) { PI::ctor(*this, impl); } -DataAddr::DataAddr(const DataAddr& s) : qmf::Handle<DataAddrImpl>() { PI::copy(*this, s); } -DataAddr::~DataAddr() { PI::dtor(*this); } -DataAddr& DataAddr::operator=(const DataAddr& s) { return PI::assign(*this, s); } - -bool DataAddr::operator==(const DataAddr& o) { return *impl == *o.impl; } -bool DataAddr::operator<(const DataAddr& o) { return *impl < *o.impl; } - -DataAddr::DataAddr(const qpid::types::Variant::Map& m) { PI::ctor(*this, new DataAddrImpl(m)); } -DataAddr::DataAddr(const string& n, const string& a, uint32_t e) { PI::ctor(*this, new DataAddrImpl(n, a, e)); } -const string& DataAddr::getName() const { return impl->getName(); } -const string& DataAddr::getAgentName() const { return impl->getAgentName(); } -uint32_t DataAddr::getAgentEpoch() const { return impl->getAgentEpoch(); } -Variant::Map DataAddr::asMap() const { return impl->asMap(); } - -bool DataAddrImpl::operator==(const DataAddrImpl& other) -{ - return - agentName == other.agentName && - name == other.name && - agentEpoch == other.agentEpoch; -} - - -bool DataAddrImpl::operator<(const DataAddrImpl& other) -{ - if (agentName < other.agentName) return true; - if (agentName > other.agentName) return false; - if (name < other.name) return true; - if (name > other.name) return false; - return agentEpoch < other.agentEpoch; -} - - -DataAddrImpl::DataAddrImpl(const Variant::Map& map) -{ - Variant::Map::const_iterator iter; - - iter = map.find("_agent_name"); - if (iter != map.end()) - agentName = iter->second.asString(); - - iter = map.find("_object_name"); - if (iter != map.end()) - name = iter->second.asString(); - - iter = map.find("_agent_epoch"); - if (iter != map.end()) - agentEpoch = (uint32_t) iter->second.asUint64(); -} - - -Variant::Map DataAddrImpl::asMap() const -{ - Variant::Map result; - - result["_agent_name"] = agentName; - result["_object_name"] = name; - if (agentEpoch > 0) - result["_agent_epoch"] = agentEpoch; - return result; -} - - -DataAddrImpl& DataAddrImplAccess::get(DataAddr& item) -{ - return *item.impl; -} - - -const DataAddrImpl& DataAddrImplAccess::get(const DataAddr& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/DataAddrImpl.h b/cpp/src/qmf/DataAddrImpl.h deleted file mode 100644 index 3f9cae9453..0000000000 --- a/cpp/src/qmf/DataAddrImpl.h +++ /dev/null @@ -1,73 +0,0 @@ -#ifndef _QMF_DATA_ADDR_IMPL_H_ -#define _QMF_DATA_ADDR_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qpid/sys/IntegerTypes.h" -#include "qpid/types/Variant.h" -#include "qmf/DataAddr.h" - -namespace qmf { - class DataAddrImpl : public virtual qpid::RefCounted { - public: - // - // Impl-only methods - // - void setName(const std::string& n) { name = n; } - void setAgent(const std::string& n, uint32_t e=0) { agentName = n; agentEpoch = e; } - - // - // Methods from API handle - // - bool operator==(const DataAddrImpl&); - bool operator<(const DataAddrImpl&); - DataAddrImpl(const qpid::types::Variant::Map&); - DataAddrImpl(const std::string& _name, const std::string& _agentName, uint32_t _agentEpoch=0) : - agentName(_agentName), name(_name), agentEpoch(_agentEpoch) {} - const std::string& getName() const { return name; } - const std::string& getAgentName() const { return agentName; } - uint32_t getAgentEpoch() const { return agentEpoch; } - qpid::types::Variant::Map asMap() const; - - private: - std::string agentName; - std::string name; - uint32_t agentEpoch; - }; - - struct DataAddrImplAccess - { - static DataAddrImpl& get(DataAddr&); - static const DataAddrImpl& get(const DataAddr&); - }; - - struct DataAddrCompare { - bool operator() (const DataAddr& lhs, const DataAddr& rhs) const - { - if (lhs.getName() != rhs.getName()) - return lhs.getName() < rhs.getName(); - return lhs.getAgentName() < rhs.getAgentName(); - } - }; -} - -#endif diff --git a/cpp/src/qmf/DataImpl.h b/cpp/src/qmf/DataImpl.h deleted file mode 100644 index 4ac3197da0..0000000000 --- a/cpp/src/qmf/DataImpl.h +++ /dev/null @@ -1,84 +0,0 @@ -#ifndef _QMF_DATA_IMPL_H_ -#define _QMF_DATA_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/Data.h" -#include "qmf/SchemaId.h" -#include "qmf/Schema.h" -#include "qmf/DataAddr.h" -#include "qmf/Agent.h" -#include "qmf/AgentSubscription.h" -#include "qpid/types/Variant.h" - -namespace qmf { - class DataImpl : public virtual qpid::RefCounted { - public: - // - // Public impl-only methods - // - DataImpl(const qpid::types::Variant::Map&, const Agent&); - qpid::types::Variant::Map asMap() const; - DataImpl() {} - void addSubscription(boost::shared_ptr<AgentSubscription>); - void delSubscription(uint64_t); - qpid::types::Variant::Map publishSubscription(uint64_t); - const Schema& getSchema() const { return schema; } - - // - // Methods from API handle - // - DataImpl(const Schema& s) : schema(s) {} - void setAddr(const DataAddr& a) { dataAddr = a; } - void setProperty(const std::string& k, const qpid::types::Variant& v); - void overwriteProperties(const qpid::types::Variant::Map& m); - bool hasSchema() const { return schemaId.isValid() || schema.isValid(); } - bool hasAddr() const { return dataAddr.isValid(); } - const SchemaId& getSchemaId() const { if (schema.isValid()) return schema.getSchemaId(); else return schemaId; } - const DataAddr& getAddr() const { return dataAddr; } - const qpid::types::Variant& getProperty(const std::string& k) const; - const qpid::types::Variant::Map& getProperties() const { return properties; } - bool hasAgent() const { return agent.isValid(); } - const Agent& getAgent() const { return agent; } - - private: - struct Subscr { - boost::shared_ptr<AgentSubscription> subscription; - qpid::types::Variant::Map deltas; - }; - std::map<uint64_t, boost::shared_ptr<Subscr> > subscriptions; - - SchemaId schemaId; - Schema schema; - DataAddr dataAddr; - qpid::types::Variant::Map properties; - Agent agent; - }; - - struct DataImplAccess - { - static DataImpl& get(Data&); - static const DataImpl& get(const Data&); - }; -} - -#endif diff --git a/cpp/src/qmf/Expression.cpp b/cpp/src/qmf/Expression.cpp deleted file mode 100644 index 7d48678c15..0000000000 --- a/cpp/src/qmf/Expression.cpp +++ /dev/null @@ -1,441 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/exceptions.h" -#include "qmf/Expression.h" -#include <iostream> - -using namespace std; -using namespace qmf; -using namespace qpid::types; - -Expression::Expression(const Variant::List& expr) -{ - static int level(0); - level++; - Variant::List::const_iterator iter(expr.begin()); - string op(iter->asString()); - iter++; - - if (op == "not") logicalOp = LOGICAL_NOT; - else if (op == "and") logicalOp = LOGICAL_AND; - else if (op == "or") logicalOp = LOGICAL_OR; - else { - logicalOp = LOGICAL_ID; - if (op == "eq") boolOp = BOOL_EQ; - else if (op == "ne") boolOp = BOOL_NE; - else if (op == "lt") boolOp = BOOL_LT; - else if (op == "le") boolOp = BOOL_LE; - else if (op == "gt") boolOp = BOOL_GT; - else if (op == "ge") boolOp = BOOL_GE; - else if (op == "re_match") boolOp = BOOL_RE_MATCH; - else if (op == "exists") boolOp = BOOL_EXISTS; - else if (op == "true") boolOp = BOOL_TRUE; - else if (op == "false") boolOp = BOOL_FALSE; - else - throw QmfException("Invalid operator in predicate expression"); - } - - if (logicalOp == LOGICAL_ID) { - switch (boolOp) { - case BOOL_EQ: - case BOOL_NE: - case BOOL_LT: - case BOOL_LE: - case BOOL_GT: - case BOOL_GE: - case BOOL_RE_MATCH: - // - // Binary operator: get two operands. - // - operandCount = 2; - break; - - case BOOL_EXISTS: - // - // Unary operator: get one operand. - // - operandCount = 1; - break; - - case BOOL_TRUE: - case BOOL_FALSE: - // - // Literal operator: no operands. - // - operandCount = 0; - break; - } - - for (int idx = 0; idx < operandCount; idx++) { - if (iter == expr.end()) - throw QmfException("Too few operands for operation: " + op); - if (iter->getType() == VAR_STRING) { - quoted[idx] = false; - operands[idx] = *iter; - } else if (iter->getType() == VAR_LIST) { - const Variant::List& sublist(iter->asList()); - Variant::List::const_iterator subIter(sublist.begin()); - if (subIter != sublist.end() && subIter->asString() == "quote") { - quoted[idx] = true; - subIter++; - if (subIter != sublist.end()) { - operands[idx] = *subIter; - subIter++; - if (subIter != sublist.end()) - throw QmfException("Extra tokens at end of 'quote'"); - } - } else - throw QmfException("Expected '[quote, <token>]'"); - } else - throw QmfException("Expected string or list as operand for: " + op); - iter++; - } - - if (iter != expr.end()) - throw QmfException("Too many operands for operation: " + op); - - } else { - // - // This is a logical expression, collect sub-expressions - // - while (iter != expr.end()) { - if (iter->getType() != VAR_LIST) - throw QmfException("Operands of " + op + " must be lists"); - expressionList.push_back(boost::shared_ptr<Expression>(new Expression(iter->asList()))); - iter++; - } - } - level--; -} - - -bool Expression::evaluate(const Variant::Map& data) const -{ - list<boost::shared_ptr<Expression> >::const_iterator iter; - - switch (logicalOp) { - case LOGICAL_ID: - return boolEval(data); - - case LOGICAL_NOT: - for (iter = expressionList.begin(); iter != expressionList.end(); iter++) - if ((*iter)->evaluate(data)) - return false; - return true; - - case LOGICAL_AND: - for (iter = expressionList.begin(); iter != expressionList.end(); iter++) - if (!(*iter)->evaluate(data)) - return false; - return true; - - case LOGICAL_OR: - for (iter = expressionList.begin(); iter != expressionList.end(); iter++) - if ((*iter)->evaluate(data)) - return true; - return false; - } - - return false; -} - - -bool Expression::boolEval(const Variant::Map& data) const -{ - Variant val[2]; - bool exists[2]; - - for (int idx = 0; idx < operandCount; idx++) { - if (quoted[idx]) { - exists[idx] = true; - val[idx] = operands[idx]; - } else { - Variant::Map::const_iterator mIter(data.find(operands[idx].asString())); - if (mIter == data.end()) { - exists[idx] = false; - } else { - exists[idx] = true; - val[idx] = mIter->second; - } - } - } - - switch (boolOp) { - case BOOL_EQ: return (exists[0] && exists[1] && (val[0].asString() == val[1].asString())); - case BOOL_NE: return (exists[0] && exists[1] && (val[0].asString() != val[1].asString())); - case BOOL_LT: return (exists[0] && exists[1] && lessThan(val[0], val[1])); - case BOOL_LE: return (exists[0] && exists[1] && lessEqual(val[0], val[1])); - case BOOL_GT: return (exists[0] && exists[1] && greaterThan(val[0], val[1])); - case BOOL_GE: return (exists[0] && exists[1] && greaterEqual(val[0], val[1])); - case BOOL_RE_MATCH: return false; // TODO - case BOOL_EXISTS: return exists[0]; - case BOOL_TRUE: return true; - case BOOL_FALSE: return false; - } - - return false; -} - -bool Expression::lessThan(const Variant& left, const Variant& right) const -{ - switch (left.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - return left.asInt64() < right.asInt64(); - case VAR_STRING: - try { - return left.asInt64() < right.asInt64(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_FLOAT: case VAR_DOUBLE: - switch (right.getType()) { - case VAR_FLOAT: case VAR_DOUBLE: - return left.asDouble() < right.asDouble(); - case VAR_STRING: - try { - return left.asDouble() < right.asDouble(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_STRING: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - try { - return left.asInt64() < right.asInt64(); - } catch (std::exception&) {} - break; - - case VAR_FLOAT: case VAR_DOUBLE: - try { - return left.asDouble() < right.asDouble(); - } catch (std::exception&) {} - break; - - case VAR_STRING: - return left.asString() < right.asString(); - default: - break; - } - default: - break; - } - - return false; -} - - -bool Expression::lessEqual(const Variant& left, const Variant& right) const -{ - switch (left.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - return left.asInt64() <= right.asInt64(); - case VAR_STRING: - try { - return left.asInt64() <= right.asInt64(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_FLOAT: case VAR_DOUBLE: - switch (right.getType()) { - case VAR_FLOAT: case VAR_DOUBLE: - return left.asDouble() <= right.asDouble(); - case VAR_STRING: - try { - return left.asDouble() <= right.asDouble(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_STRING: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - try { - return left.asInt64() <= right.asInt64(); - } catch (std::exception&) {} - break; - - case VAR_FLOAT: case VAR_DOUBLE: - try { - return left.asDouble() <= right.asDouble(); - } catch (std::exception&) {} - break; - - case VAR_STRING: - return left.asString() <= right.asString(); - default: - break; - } - default: - break; - } - - return false; -} - - -bool Expression::greaterThan(const Variant& left, const Variant& right) const -{ - switch (left.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - return left.asInt64() > right.asInt64(); - case VAR_STRING: - try { - return left.asInt64() > right.asInt64(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_FLOAT: case VAR_DOUBLE: - switch (right.getType()) { - case VAR_FLOAT: case VAR_DOUBLE: - return left.asDouble() > right.asDouble(); - case VAR_STRING: - try { - return left.asDouble() > right.asDouble(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_STRING: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - try { - return left.asInt64() > right.asInt64(); - } catch (std::exception&) {} - break; - - case VAR_FLOAT: case VAR_DOUBLE: - try { - return left.asDouble() > right.asDouble(); - } catch (std::exception&) {} - break; - - case VAR_STRING: - return left.asString() > right.asString(); - default: - break; - } - default: - break; - } - - return false; -} - - -bool Expression::greaterEqual(const Variant& left, const Variant& right) const -{ - switch (left.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - return left.asInt64() >= right.asInt64(); - case VAR_STRING: - try { - return left.asInt64() >= right.asInt64(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_FLOAT: case VAR_DOUBLE: - switch (right.getType()) { - case VAR_FLOAT: case VAR_DOUBLE: - return left.asDouble() >= right.asDouble(); - case VAR_STRING: - try { - return left.asDouble() >= right.asDouble(); - } catch (std::exception&) {} - break; - default: - break; - } - break; - - case VAR_STRING: - switch (right.getType()) { - case VAR_UINT8: case VAR_UINT16: case VAR_UINT32: case VAR_UINT64: - case VAR_INT8: case VAR_INT16: case VAR_INT32: case VAR_INT64: - try { - return left.asInt64() >= right.asInt64(); - } catch (std::exception&) {} - break; - - case VAR_FLOAT: case VAR_DOUBLE: - try { - return left.asDouble() >= right.asDouble(); - } catch (std::exception&) {} - break; - - case VAR_STRING: - return left.asString() >= right.asString(); - default: - break; - } - default: - break; - } - - return false; -} - - diff --git a/cpp/src/qmf/Expression.h b/cpp/src/qmf/Expression.h deleted file mode 100644 index 6fbfdbc4ba..0000000000 --- a/cpp/src/qmf/Expression.h +++ /dev/null @@ -1,73 +0,0 @@ -#ifndef _QMF_EXPRESSION_H_ -#define _QMF_EXPRESSION_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/types/Variant.h" -#include <string> -#include <list> -#include <boost/shared_ptr.hpp> - -namespace qmf { - - enum LogicalOp { - LOGICAL_ID = 1, - LOGICAL_NOT = 2, - LOGICAL_AND = 3, - LOGICAL_OR = 4 - }; - - enum BooleanOp { - BOOL_EQ = 1, - BOOL_NE = 2, - BOOL_LT = 3, - BOOL_LE = 4, - BOOL_GT = 5, - BOOL_GE = 6, - BOOL_RE_MATCH = 7, - BOOL_EXISTS = 8, - BOOL_TRUE = 9, - BOOL_FALSE = 10 - }; - - class Expression { - public: - Expression(const qpid::types::Variant::List& expr); - bool evaluate(const qpid::types::Variant::Map& data) const; - private: - LogicalOp logicalOp; - BooleanOp boolOp; - int operandCount; - qpid::types::Variant operands[2]; - bool quoted[2]; - std::list<boost::shared_ptr<Expression> > expressionList; - - bool boolEval(const qpid::types::Variant::Map& data) const; - bool lessThan(const qpid::types::Variant& left, const qpid::types::Variant& right) const; - bool lessEqual(const qpid::types::Variant& left, const qpid::types::Variant& right) const; - bool greaterThan(const qpid::types::Variant& left, const qpid::types::Variant& right) const; - bool greaterEqual(const qpid::types::Variant& left, const qpid::types::Variant& right) const; - }; - -} - -#endif - diff --git a/cpp/src/qmf/Hash.cpp b/cpp/src/qmf/Hash.cpp deleted file mode 100644 index 86738dda2f..0000000000 --- a/cpp/src/qmf/Hash.cpp +++ /dev/null @@ -1,45 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/Hash.h" - -using namespace qmf; - -Hash::Hash() -{ - data[0] = 0x5A5A5A5A5A5A5A5ALL; - data[1] = 0x5A5A5A5A5A5A5A5ALL; -} - -void Hash::update(const char* s, uint32_t len) -{ - uint64_t* first = &data[0]; - uint64_t* second = &data[1]; - - for (uint32_t idx = 0; idx < len; idx++) { - uint64_t recycle = ((*second & 0xff00000000000000LL) >> 56); - *second = *second << 8; - *second |= ((*first & 0xFF00000000000000LL) >> 56); - *first = *first << 8; - *first = *first + (uint64_t) s[idx] + recycle; - } -} - diff --git a/cpp/src/qmf/Hash.h b/cpp/src/qmf/Hash.h deleted file mode 100644 index e1eff84117..0000000000 --- a/cpp/src/qmf/Hash.h +++ /dev/null @@ -1,44 +0,0 @@ -#ifndef QMF_HASH_H -#define QMF_HASH_H -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/sys/IntegerTypes.h" -#include "qpid/types/Uuid.h" -#include <string> - -namespace qmf { - class Hash { - public: - Hash(); - qpid::types::Uuid asUuid() const { return qpid::types::Uuid((unsigned char*) data); } - void update(const char* s, uint32_t len); - void update(uint8_t v) { update((char*) &v, sizeof(v)); } - void update(uint32_t v) { update((char*) &v, sizeof(v)); } - void update(const std::string& v) { update(const_cast<char*>(v.c_str()), v.size()); } - void update(bool v) { update(uint8_t(v ? 1 : 0)); } - - private: - uint64_t data[2]; - }; -} - -#endif diff --git a/cpp/src/qmf/PrivateImplRef.h b/cpp/src/qmf/PrivateImplRef.h deleted file mode 100644 index 960cbb2e09..0000000000 --- a/cpp/src/qmf/PrivateImplRef.h +++ /dev/null @@ -1,93 +0,0 @@ -#ifndef QMF_PRIVATEIMPL_H -#define QMF_PRIVATEIMPL_H - -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/ImportExport.h" -#include "qpid/RefCounted.h" -#include <boost/intrusive_ptr.hpp> - -namespace qmf { - -/** - * Helper class to implement a class with a private, reference counted - * implementation and reference semantics. - * - * Such classes are used in the public API to hide implementation, they - * should. Example of use: - * - * === Foo.h - * - * template <class T> PrivateImplRef; - * class FooImpl; - * - * Foo : public Handle<FooImpl> { - * public: - * Foo(FooImpl* = 0); - * Foo(const Foo&); - * ~Foo(); - * Foo& operator=(const Foo&); - * - * int fooDo(); // and other Foo functions... - * - * private: - * typedef FooImpl Impl; - * Impl* impl; - * friend class PrivateImplRef<Foo>; - * - * === Foo.cpp - * - * typedef PrivateImplRef<Foo> PI; - * Foo::Foo(FooImpl* p) { PI::ctor(*this, p); } - * Foo::Foo(const Foo& c) : Handle<FooImpl>() { PI::copy(*this, c); } - * Foo::~Foo() { PI::dtor(*this); } - * Foo& Foo::operator=(const Foo& c) { return PI::assign(*this, c); } - * - * int foo::fooDo() { return impl->fooDo(); } - * - */ -template <class T> class PrivateImplRef { - public: - typedef typename T::Impl Impl; - typedef boost::intrusive_ptr<Impl> intrusive_ptr; - - /** Get the implementation pointer from a handle */ - static intrusive_ptr get(const T& t) { return intrusive_ptr(t.impl); } - - /** Set the implementation pointer in a handle */ - static void set(T& t, const intrusive_ptr& p) { - if (t.impl == p) return; - if (t.impl) boost::intrusive_ptr_release(t.impl); - t.impl = p.get(); - if (t.impl) boost::intrusive_ptr_add_ref(t.impl); - } - - // Helper functions to implement the ctor, dtor, copy, assign - static void ctor(T& t, Impl* p) { t.impl = p; if (p) boost::intrusive_ptr_add_ref(p); } - static void copy(T& t, const T& x) { if (&t == &x) return; t.impl = 0; assign(t, x); } - static void dtor(T& t) { if(t.impl) boost::intrusive_ptr_release(t.impl); } - static T& assign(T& t, const T& x) { set(t, get(x)); return t;} -}; - -} // namespace qmf - -#endif /*!QMF_PRIVATEIMPL_H*/ diff --git a/cpp/src/qmf/Query.cpp b/cpp/src/qmf/Query.cpp deleted file mode 100644 index ee8ca38e59..0000000000 --- a/cpp/src/qmf/Query.cpp +++ /dev/null @@ -1,153 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" -#include "qmf/QueryImpl.h" -#include "qmf/DataAddrImpl.h" -#include "qmf/SchemaIdImpl.h" -#include "qpid/messaging/AddressParser.h" - -using namespace std; -using namespace qmf; -using qpid::types::Variant; - -typedef PrivateImplRef<Query> PI; - -Query::Query(QueryImpl* impl) { PI::ctor(*this, impl); } -Query::Query(const Query& s) : qmf::Handle<QueryImpl>() { PI::copy(*this, s); } -Query::~Query() { PI::dtor(*this); } -Query& Query::operator=(const Query& s) { return PI::assign(*this, s); } - -Query::Query(QueryTarget t, const string& pr) { PI::ctor(*this, new QueryImpl(t, pr)); } -Query::Query(QueryTarget t, const string& c, const string& p, const string& pr) { PI::ctor(*this, new QueryImpl(t, c, p, pr)); } -Query::Query(QueryTarget t, const SchemaId& s, const string& pr) { PI::ctor(*this, new QueryImpl(t, s, pr)); } -Query::Query(const DataAddr& a) { PI::ctor(*this, new QueryImpl(a)); } - -QueryTarget Query::getTarget() const { return impl->getTarget(); } -const DataAddr& Query::getDataAddr() const { return impl->getDataAddr(); } -const SchemaId& Query::getSchemaId() const { return impl->getSchemaId(); } -void Query::setPredicate(const Variant::List& pr) { impl->setPredicate(pr); } -const Variant::List& Query::getPredicate() const { return impl->getPredicate(); } -bool Query::matchesPredicate(const qpid::types::Variant::Map& map) const { return impl->matchesPredicate(map); } - - -QueryImpl::QueryImpl(const Variant::Map& map) : predicateCompiled(false) -{ - Variant::Map::const_iterator iter; - - iter = map.find("_what"); - if (iter == map.end()) - throw QmfException("Query missing _what element"); - - const string& targetString(iter->second.asString()); - if (targetString == "OBJECT") target = QUERY_OBJECT; - else if (targetString == "OBJECT_ID") target = QUERY_OBJECT_ID; - else if (targetString == "SCHEMA") target = QUERY_SCHEMA; - else if (targetString == "SCHEMA_ID") target = QUERY_SCHEMA_ID; - else - throw QmfException("Query with invalid _what value: " + targetString); - - iter = map.find("_object_id"); - if (iter != map.end()) { - auto_ptr<DataAddrImpl> addrImpl(new DataAddrImpl(iter->second.asMap())); - dataAddr = DataAddr(addrImpl.release()); - } - - iter = map.find("_schema_id"); - if (iter != map.end()) { - auto_ptr<SchemaIdImpl> sidImpl(new SchemaIdImpl(iter->second.asMap())); - schemaId = SchemaId(sidImpl.release()); - } - - iter = map.find("_where"); - if (iter != map.end()) - predicate = iter->second.asList(); -} - - -Variant::Map QueryImpl::asMap() const -{ - Variant::Map map; - string targetString; - - switch (target) { - case QUERY_OBJECT : targetString = "OBJECT"; break; - case QUERY_OBJECT_ID : targetString = "OBJECT_ID"; break; - case QUERY_SCHEMA : targetString = "SCHEMA"; break; - case QUERY_SCHEMA_ID : targetString = "SCHEMA_ID"; break; - } - - map["_what"] = targetString; - - if (dataAddr.isValid()) - map["_object_id"] = DataAddrImplAccess::get(dataAddr).asMap(); - - if (schemaId.isValid()) - map["_schema_id"] = SchemaIdImplAccess::get(schemaId).asMap(); - - if (!predicate.empty()) - map["_where"] = predicate; - - return map; -} - - -bool QueryImpl::matchesPredicate(const qpid::types::Variant::Map& data) const -{ - if (predicate.empty()) - return true; - - if (!predicateCompiled) { - expression.reset(new Expression(predicate)); - predicateCompiled = true; - } - - return expression->evaluate(data); -} - - -void QueryImpl::parsePredicate(const string& pred) -{ - if (pred.empty()) - return; - - if (pred[0] == '[') { - // - // Parse this as an AddressParser list. - // - qpid::messaging::AddressParser parser(pred); - parser.parseList(predicate); - } else - throw QmfException("Invalid predicate format"); -} - - -QueryImpl& QueryImplAccess::get(Query& item) -{ - return *item.impl; -} - - -const QueryImpl& QueryImplAccess::get(const Query& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/QueryImpl.h b/cpp/src/qmf/QueryImpl.h deleted file mode 100644 index 27ec427684..0000000000 --- a/cpp/src/qmf/QueryImpl.h +++ /dev/null @@ -1,77 +0,0 @@ -#ifndef _QMF_QUERY_IMPL_H_ -#define _QMF_QUERY_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/Query.h" -#include "qmf/DataAddr.h" -#include "qmf/SchemaId.h" -#include "qmf/Expression.h" -#include "qpid/types/Variant.h" -#include <boost/shared_ptr.hpp> - -namespace qmf { - class QueryImpl : public virtual qpid::RefCounted { - public: - // - // Public impl-only methods - // - QueryImpl(const qpid::types::Variant::Map&); - qpid::types::Variant::Map asMap() const; - - // - // Methods from API handle - // - QueryImpl(QueryTarget t, const std::string& pr) : target(t), predicateCompiled(false) { parsePredicate(pr); } - QueryImpl(QueryTarget t, const std::string& c, const std::string& p, const std::string& pr) : - target(t), schemaId(SCHEMA_TYPE_DATA, p, c), predicateCompiled(false) { parsePredicate(pr); } - QueryImpl(QueryTarget t, const SchemaId& s, const std::string& pr) : - target(t), schemaId(s), predicateCompiled(false) { parsePredicate(pr); } - QueryImpl(const DataAddr& a) : target(QUERY_OBJECT), dataAddr(a), predicateCompiled(false) {} - - QueryTarget getTarget() const { return target; } - const DataAddr& getDataAddr() const { return dataAddr; } - const SchemaId& getSchemaId() const { return schemaId; } - void setPredicate(const qpid::types::Variant::List& pr) { predicate = pr; } - const qpid::types::Variant::List& getPredicate() const { return predicate; } - bool matchesPredicate(const qpid::types::Variant::Map& map) const; - - private: - QueryTarget target; - SchemaId schemaId; - DataAddr dataAddr; - qpid::types::Variant::List predicate; - mutable bool predicateCompiled; - mutable boost::shared_ptr<Expression> expression; - - void parsePredicate(const std::string& s); - }; - - struct QueryImplAccess - { - static QueryImpl& get(Query&); - static const QueryImpl& get(const Query&); - }; -} - -#endif - diff --git a/cpp/src/qmf/Schema.cpp b/cpp/src/qmf/Schema.cpp deleted file mode 100644 index 872aad724c..0000000000 --- a/cpp/src/qmf/Schema.cpp +++ /dev/null @@ -1,358 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/SchemaImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" -#include "qmf/SchemaTypes.h" -#include "qmf/SchemaIdImpl.h" -#include "qmf/SchemaPropertyImpl.h" -#include "qmf/SchemaMethodImpl.h" -#include "qmf/Hash.h" -#include "qpid/log/Statement.h" -#include "qpid/management/Buffer.h" -#include <list> - -using namespace std; -using qpid::types::Variant; -using namespace qmf; - -typedef PrivateImplRef<Schema> PI; - -Schema::Schema(SchemaImpl* impl) { PI::ctor(*this, impl); } -Schema::Schema(const Schema& s) : qmf::Handle<SchemaImpl>() { PI::copy(*this, s); } -Schema::~Schema() { PI::dtor(*this); } -Schema& Schema::operator=(const Schema& s) { return PI::assign(*this, s); } - -Schema::Schema(int t, const string& p, const string& c) { PI::ctor(*this, new SchemaImpl(t, p, c)); } -const SchemaId& Schema::getSchemaId() const { return impl->getSchemaId(); } -void Schema::finalize() { impl->finalize(); } -bool Schema::isFinalized() const { return impl->isFinalized(); } -void Schema::addProperty(const SchemaProperty& p) { impl->addProperty(p); } -void Schema::addMethod(const SchemaMethod& m) { impl->addMethod(m); } -void Schema::setDesc(const string& d) { impl->setDesc(d); } -const string& Schema::getDesc() const { return impl->getDesc(); } -void Schema::setDefaultSeverity(int s) { impl->setDefaultSeverity(s); } -int Schema::getDefaultSeverity() const { return impl->getDefaultSeverity(); } -uint32_t Schema::getPropertyCount() const { return impl->getPropertyCount(); } -SchemaProperty Schema::getProperty(uint32_t i) const { return impl->getProperty(i); } -uint32_t Schema::getMethodCount() const { return impl->getMethodCount(); } -SchemaMethod Schema::getMethod(uint32_t i) const { return impl->getMethod(i); } - -//======================================================================================== -// Impl Method Bodies -//======================================================================================== - -SchemaImpl::SchemaImpl(const Variant::Map& map) : finalized(false) -{ - Variant::Map::const_iterator iter; - Variant::List::const_iterator lIter; - - iter = map.find("_schema_id"); - if (iter == map.end()) - throw QmfException("Schema map missing _schema_id element"); - schemaId = SchemaId(new SchemaIdImpl(iter->second.asMap())); - - iter = map.find("_desc"); - if (iter != map.end()) - description = iter->second.asString(); - - iter = map.find("_default_severity"); - if (iter != map.end()) - defaultSeverity = int(iter->second.asUint32()); - - iter = map.find("_properties"); - if (iter != map.end()) { - const Variant::List& props(iter->second.asList()); - for (lIter = props.begin(); lIter != props.end(); lIter++) - addProperty(SchemaProperty(new SchemaPropertyImpl(lIter->asMap()))); - } - - iter = map.find("_methods"); - if (iter != map.end()) { - const Variant::List& meths(iter->second.asList()); - for (lIter = meths.begin(); lIter != meths.end(); lIter++) - addMethod(SchemaMethod(new SchemaMethodImpl(lIter->asMap()))); - } - - finalized = true; -} - - -Variant::Map SchemaImpl::asMap() const -{ - Variant::Map map; - Variant::List propList; - Variant::List methList; - - checkNotFinal(); - - map["_schema_id"] = SchemaIdImplAccess::get(schemaId).asMap(); - if (!description.empty()) - map["_desc"] = description; - if (schemaId.getType() == SCHEMA_TYPE_EVENT) - map["_default_severity"] = uint32_t(defaultSeverity); - - for (list<SchemaProperty>::const_iterator pIter = properties.begin(); pIter != properties.end(); pIter++) - propList.push_back(SchemaPropertyImplAccess::get(*pIter).asMap()); - - for (list<SchemaMethod>::const_iterator mIter = methods.begin(); mIter != methods.end(); mIter++) - methList.push_back(SchemaMethodImplAccess::get(*mIter).asMap()); - - map["_properties"] = propList; - map["_methods"] = methList; - return map; -} - - -SchemaImpl::SchemaImpl(qpid::management::Buffer& buffer) : finalized(false) -{ - int schemaType; - string packageName; - string className; - uint8_t hash[16]; - - schemaType = int(buffer.getOctet()); - buffer.getShortString(packageName); - buffer.getShortString(className); - buffer.getBin128(hash); - schemaId = SchemaId(schemaType, packageName, className); - schemaId.setHash(qpid::types::Uuid(hash)); - - if (schemaType == SCHEMA_TYPE_DATA) { - uint16_t propCount(buffer.getShort()); - uint16_t statCount(buffer.getShort()); - uint16_t methCount(buffer.getShort()); - for (uint16_t idx = 0; idx < propCount + statCount; idx++) - addProperty(new SchemaPropertyImpl(buffer)); - for (uint16_t idx = 0; idx < methCount; idx++) - addMethod(new SchemaMethodImpl(buffer)); - } - - finalized = true; -} - - -string SchemaImpl::asV1Content(uint32_t sequence) const -{ -#define RAW_BUF_SIZE 65536 - char rawBuf[RAW_BUF_SIZE]; - qpid::management::Buffer buffer(rawBuf, RAW_BUF_SIZE); - - // - // Encode the QMFv1 Header - // - buffer.putOctet('A'); - buffer.putOctet('M'); - buffer.putOctet('2'); - buffer.putOctet('s'); - buffer.putLong(sequence); - - // - // Encode the common schema information - // - buffer.putOctet(uint8_t(schemaId.getType())); - buffer.putShortString(schemaId.getPackageName()); - buffer.putShortString(schemaId.getName()); - buffer.putBin128(schemaId.getHash().data()); - - if (schemaId.getType() == SCHEMA_TYPE_DATA) { - buffer.putShort(properties.size()); - buffer.putShort(0); - buffer.putShort(methods.size()); - for (list<SchemaProperty>::const_iterator pIter = properties.begin(); pIter != properties.end(); pIter++) - SchemaPropertyImplAccess::get(*pIter).encodeV1(buffer, false, false); - for (list<SchemaMethod>::const_iterator mIter = methods.begin(); mIter != methods.end(); mIter++) - SchemaMethodImplAccess::get(*mIter).encodeV1(buffer); - } else { - buffer.putShort(properties.size()); - for (list<SchemaProperty>::const_iterator pIter = properties.begin(); pIter != properties.end(); pIter++) - SchemaPropertyImplAccess::get(*pIter).encodeV1(buffer, true, false); - } - - return string(rawBuf, buffer.getPosition()); -} - - -bool SchemaImpl::isValidProperty(const std::string& k, const Variant& v) const -{ - for (list<SchemaProperty>::const_iterator iter = properties.begin(); iter != properties.end(); iter++) - if (iter->getName() == k) - return (isCompatibleType(iter->getType(), v.getType())); - return false; -} - - -bool SchemaImpl::isValidMethodInArg(const std::string& m, const std::string& k, const Variant& v) const -{ - for (list<SchemaMethod>::const_iterator mIter = methods.begin(); mIter != methods.end(); mIter++) { - if (mIter->getName() == m) { - uint32_t count(mIter->getArgumentCount()); - for (uint32_t i = 0; i < count; i++) { - const SchemaProperty prop(mIter->getArgument(i)); - if (prop.getName() == k) { - if (prop.getDirection() == DIR_IN || prop.getDirection() == DIR_IN_OUT) - return (isCompatibleType(prop.getType(), v.getType())); - else - return false; - } - } - } - } - return false; -} - - -bool SchemaImpl::isValidMethodOutArg(const std::string& m, const std::string& k, const Variant& v) const -{ - for (list<SchemaMethod>::const_iterator mIter = methods.begin(); mIter != methods.end(); mIter++) { - if (mIter->getName() == m) { - uint32_t count(mIter->getArgumentCount()); - for (uint32_t i = 0; i < count; i++) { - const SchemaProperty prop(mIter->getArgument(i)); - if (prop.getName() == k) { - if (prop.getDirection() == DIR_OUT || prop.getDirection() == DIR_IN_OUT) - return (isCompatibleType(prop.getType(), v.getType())); - else - return false; - } - } - } - } - return false; -} - - -void SchemaImpl::finalize() -{ - Hash hash; - - hash.update((uint8_t) schemaId.getType()); - hash.update(schemaId.getPackageName()); - hash.update(schemaId.getName()); - - for (list<SchemaProperty>::const_iterator pIter = properties.begin(); pIter != properties.end(); pIter++) - SchemaPropertyImplAccess::get(*pIter).updateHash(hash); - for (list<SchemaMethod>::const_iterator mIter = methods.begin(); mIter != methods.end(); mIter++) - SchemaMethodImplAccess::get(*mIter).updateHash(hash); - - schemaId.setHash(hash.asUuid()); - QPID_LOG(debug, "Schema Finalized: " << schemaId.getPackageName() << ":" << schemaId.getName() << ":" << - schemaId.getHash()); - - finalized = true; -} - - -SchemaProperty SchemaImpl::getProperty(uint32_t i) const -{ - uint32_t count = 0; - for (list<SchemaProperty>::const_iterator iter = properties.begin(); iter != properties.end(); iter++) - if (count++ == i) - return *iter; - throw IndexOutOfRange(); -} - - -SchemaMethod SchemaImpl::getMethod(uint32_t i) const -{ - uint32_t count = 0; - for (list<SchemaMethod>::const_iterator iter = methods.begin(); iter != methods.end(); iter++) - if (count++ == i) - return *iter; - throw IndexOutOfRange(); -} - -void SchemaImpl::checkFinal() const -{ - if (finalized) - throw QmfException("Modification of a finalized schema is forbidden"); -} - - -void SchemaImpl::checkNotFinal() const -{ - if (!finalized) - throw QmfException("Schema is not yet finalized/registered"); -} - - -bool SchemaImpl::isCompatibleType(int qmfType, qpid::types::VariantType qpidType) const -{ - bool typeValid(false); - - switch (qpidType) { - case qpid::types::VAR_VOID: - if (qmfType == SCHEMA_DATA_VOID) - typeValid = true; - break; - case qpid::types::VAR_BOOL: - if (qmfType == SCHEMA_DATA_BOOL) - typeValid = true; - break; - case qpid::types::VAR_UINT8: - case qpid::types::VAR_UINT16: - case qpid::types::VAR_UINT32: - case qpid::types::VAR_UINT64: - case qpid::types::VAR_INT8: - case qpid::types::VAR_INT16: - case qpid::types::VAR_INT32: - case qpid::types::VAR_INT64: - if (qmfType == SCHEMA_DATA_INT) - typeValid = true; - break; - case qpid::types::VAR_FLOAT: - case qpid::types::VAR_DOUBLE: - if (qmfType == SCHEMA_DATA_FLOAT) - typeValid = true; - break; - case qpid::types::VAR_STRING: - if (qmfType == SCHEMA_DATA_STRING) - typeValid = true; - break; - case qpid::types::VAR_MAP: - if (qmfType == SCHEMA_DATA_MAP) - typeValid = true; - break; - case qpid::types::VAR_LIST: - if (qmfType == SCHEMA_DATA_LIST) - typeValid = true; - break; - case qpid::types::VAR_UUID: - if (qmfType == SCHEMA_DATA_UUID) - typeValid = true; - break; - } - - return typeValid; -} - - -SchemaImpl& SchemaImplAccess::get(Schema& item) -{ - return *item.impl; -} - - -const SchemaImpl& SchemaImplAccess::get(const Schema& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/SchemaCache.cpp b/cpp/src/qmf/SchemaCache.cpp deleted file mode 100644 index 74ca4044fd..0000000000 --- a/cpp/src/qmf/SchemaCache.cpp +++ /dev/null @@ -1,91 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/SchemaCache.h" -#include "qmf/exceptions.h" - -using namespace std; -using namespace qmf; - -bool SchemaCache::declareSchemaId(const SchemaId& id) -{ - qpid::sys::Mutex::ScopedLock l(lock); - SchemaMap::const_iterator iter = schemata.find(id); - if (iter == schemata.end()) { - schemata[id] = Schema(); - return false; - } - return true; -} - - -void SchemaCache::declareSchema(const Schema& schema) -{ - qpid::sys::Mutex::ScopedLock l(lock); - SchemaMap::const_iterator iter = schemata.find(schema.getSchemaId()); - if (iter == schemata.end() || !iter->second.isValid()) { - schemata[schema.getSchemaId()] = schema; - - // - // If there are any threads blocking in SchemaCache::getSchema waiting for - // this schema, unblock them all now. - // - CondMap::iterator cIter = conditions.find(schema.getSchemaId()); - if (cIter != conditions.end()) - cIter->second->notifyAll(); - } -} - - -bool SchemaCache::haveSchema(const SchemaId& id) const -{ - qpid::sys::Mutex::ScopedLock l(lock); - SchemaMap::const_iterator iter = schemata.find(id); - return iter != schemata.end() && iter->second.isValid(); -} - - -const Schema& SchemaCache::getSchema(const SchemaId& id, qpid::messaging::Duration timeout) const -{ - qpid::sys::Mutex::ScopedLock l(lock); - SchemaMap::const_iterator iter = schemata.find(id); - if (iter != schemata.end() && iter->second.isValid()) - return iter->second; - - // - // The desired schema is not in the cache. Assume that the caller knows this and has - // sent a schema request to the remote agent and now wishes to wait until the schema - // information arrives. - // - CondMap::iterator cIter = conditions.find(id); - if (cIter == conditions.end()) - conditions[id] = boost::shared_ptr<qpid::sys::Condition>(new qpid::sys::Condition()); - - uint64_t milliseconds = timeout.getMilliseconds(); - conditions[id]->wait(lock, qpid::sys::AbsTime(qpid::sys::now(), - qpid::sys::Duration(milliseconds * qpid::sys::TIME_MSEC))); - iter = schemata.find(id); - if (iter != schemata.end() && iter->second.isValid()) - return iter->second; - - throw QmfException("Schema lookup timed out"); -} - diff --git a/cpp/src/qmf/SchemaCache.h b/cpp/src/qmf/SchemaCache.h deleted file mode 100644 index a1f104233f..0000000000 --- a/cpp/src/qmf/SchemaCache.h +++ /dev/null @@ -1,56 +0,0 @@ -#ifndef QMF_SCHEMA_CACHE_H -#define QMF_SCHEMA_CACHE_H -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/SchemaIdImpl.h" -#include "qmf/Schema.h" -#include "qpid/sys/Mutex.h" -#include "qpid/sys/Condition.h" -#include "qpid/messaging/Duration.h" -#include <string> -#include <map> -#include <boost/shared_ptr.hpp> - -namespace qmf { - - class SchemaCache { - public: - SchemaCache() {} - ~SchemaCache() {} - - bool declareSchemaId(const SchemaId&); - void declareSchema(const Schema&); - bool haveSchema(const SchemaId&) const; - const Schema& getSchema(const SchemaId&, qpid::messaging::Duration) const; - - private: - mutable qpid::sys::Mutex lock; - typedef std::map<SchemaId, Schema, SchemaIdCompare> SchemaMap; - typedef std::map<SchemaId, boost::shared_ptr<qpid::sys::Condition>, SchemaIdCompare> CondMap; - SchemaMap schemata; - mutable CondMap conditions; - }; - -} - -#endif - diff --git a/cpp/src/qmf/SchemaId.cpp b/cpp/src/qmf/SchemaId.cpp deleted file mode 100644 index 25fa9915ae..0000000000 --- a/cpp/src/qmf/SchemaId.cpp +++ /dev/null @@ -1,96 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/SchemaIdImpl.h" -#include "qmf/PrivateImplRef.h" - -using namespace std; -using namespace qmf; -using qpid::types::Variant; - -typedef PrivateImplRef<SchemaId> PI; - -SchemaId::SchemaId(SchemaIdImpl* impl) { PI::ctor(*this, impl); } -SchemaId::SchemaId(const SchemaId& s) : qmf::Handle<SchemaIdImpl>() { PI::copy(*this, s); } -SchemaId::~SchemaId() { PI::dtor(*this); } -SchemaId& SchemaId::operator=(const SchemaId& s) { return PI::assign(*this, s); } - -SchemaId::SchemaId(int t, const string& p, const string& n) { PI::ctor(*this, new SchemaIdImpl(t, p, n)); } -void SchemaId::setHash(const qpid::types::Uuid& h) { impl->setHash(h); } -int SchemaId::getType() const { return impl->getType(); } -const string& SchemaId::getPackageName() const { return impl->getPackageName(); } -const string& SchemaId::getName() const { return impl->getName(); } -const qpid::types::Uuid& SchemaId::getHash() const { return impl->getHash(); } - - -SchemaIdImpl::SchemaIdImpl(const Variant::Map& map) -{ - Variant::Map::const_iterator iter; - - iter = map.find("_package_name"); - if (iter != map.end()) - package = iter->second.asString(); - - iter = map.find("_class_name"); - if (iter != map.end()) - name = iter->second.asString(); - - iter = map.find("_type"); - if (iter != map.end()) { - const string& stype = iter->second.asString(); - if (stype == "_data") - sType = SCHEMA_TYPE_DATA; - else if (stype == "_event") - sType = SCHEMA_TYPE_EVENT; - } - - iter = map.find("_hash"); - if (iter != map.end()) - hash = iter->second.asUuid(); -} - - -Variant::Map SchemaIdImpl::asMap() const -{ - Variant::Map result; - - result["_package_name"] = package; - result["_class_name"] = name; - if (sType == SCHEMA_TYPE_DATA) - result["_type"] = "_data"; - else - result["_type"] = "_event"; - if (!hash.isNull()) - result["_hash"] = hash; - return result; -} - - -SchemaIdImpl& SchemaIdImplAccess::get(SchemaId& item) -{ - return *item.impl; -} - - -const SchemaIdImpl& SchemaIdImplAccess::get(const SchemaId& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/SchemaIdImpl.h b/cpp/src/qmf/SchemaIdImpl.h deleted file mode 100644 index ae1a3d8d3b..0000000000 --- a/cpp/src/qmf/SchemaIdImpl.h +++ /dev/null @@ -1,83 +0,0 @@ -#ifndef _QMF_SCHEMA_ID_IMPL_H_ -#define _QMF_SCHEMA_ID_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/SchemaId.h" -#include "qpid/types/Variant.h" -#include "qpid/types/Uuid.h" -#include <string> - -namespace qmf { - class SchemaIdImpl : public virtual qpid::RefCounted { - public: - // - // Public impl-only methods - // - SchemaIdImpl(const qpid::types::Variant::Map&); - qpid::types::Variant::Map asMap() const; - - // - // Methods from API handle - // - SchemaIdImpl(int t, const std::string& p, const std::string& n) : sType(t), package(p), name(n) {} - void setHash(const qpid::types::Uuid& h) { hash = h; } - int getType() const { return sType; } - const std::string& getPackageName() const { return package; } - const std::string& getName() const { return name; } - const qpid::types::Uuid& getHash() const { return hash; } - - private: - int sType; - std::string package; - std::string name; - qpid::types::Uuid hash; - }; - - struct SchemaIdImplAccess - { - static SchemaIdImpl& get(SchemaId&); - static const SchemaIdImpl& get(const SchemaId&); - }; - - struct SchemaIdCompare { - bool operator() (const SchemaId& lhs, const SchemaId& rhs) const - { - if (lhs.getName() != rhs.getName()) - return lhs.getName() < rhs.getName(); - if (lhs.getPackageName() != rhs.getPackageName()) - return lhs.getPackageName() < rhs.getPackageName(); - return lhs.getHash() < rhs.getHash(); - } - }; - - struct SchemaIdCompareNoHash { - bool operator() (const SchemaId& lhs, const SchemaId& rhs) const - { - if (lhs.getName() != rhs.getName()) - return lhs.getName() < rhs.getName(); - return lhs.getPackageName() < rhs.getPackageName(); - } - }; -} - -#endif diff --git a/cpp/src/qmf/SchemaImpl.h b/cpp/src/qmf/SchemaImpl.h deleted file mode 100644 index 1c88f87808..0000000000 --- a/cpp/src/qmf/SchemaImpl.h +++ /dev/null @@ -1,95 +0,0 @@ -#ifndef _QMF_SCHEMAIMPL_H_ -#define _QMF_SCHEMAIMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" -#include "qmf/SchemaTypes.h" -#include "qmf/SchemaId.h" -#include "qmf/Schema.h" -#include "qmf/SchemaProperty.h" -#include "qmf/SchemaMethod.h" -#include <list> - -namespace qpid { -namespace management { - class Buffer; -}} - -namespace qmf { - class SchemaImpl : public virtual qpid::RefCounted { - public: - // - // Impl-only public methods - // - SchemaImpl(const qpid::types::Variant::Map& m); - qpid::types::Variant::Map asMap() const; - SchemaImpl(qpid::management::Buffer& v1Buffer); - std::string asV1Content(uint32_t sequence) const; - bool isValidProperty(const std::string& k, const qpid::types::Variant& v) const; - bool isValidMethodInArg(const std::string& m, const std::string& k, const qpid::types::Variant& v) const; - bool isValidMethodOutArg(const std::string& m, const std::string& k, const qpid::types::Variant& v) const; - - // - // Methods from API handle - // - SchemaImpl(int t, const std::string& p, const std::string& c) : schemaId(t, p, c), finalized(false) {} - const SchemaId& getSchemaId() const { checkNotFinal(); return schemaId; } - - void finalize(); - bool isFinalized() const { return finalized; } - void addProperty(const SchemaProperty& p) { checkFinal(); properties.push_back(p); } - void addMethod(const SchemaMethod& m) { checkFinal(); methods.push_back(m); } - - void setDesc(const std::string& d) { description = d; } - const std::string& getDesc() const { return description; } - - void setDefaultSeverity(int s) { checkFinal(); defaultSeverity = s; } - int getDefaultSeverity() const { return defaultSeverity; } - - uint32_t getPropertyCount() const { return properties.size(); } - SchemaProperty getProperty(uint32_t i) const; - - uint32_t getMethodCount() const { return methods.size(); } - SchemaMethod getMethod(uint32_t i) const; - private: - SchemaId schemaId; - int defaultSeverity; - std::string description; - bool finalized; - std::list<SchemaProperty> properties; - std::list<SchemaMethod> methods; - - void checkFinal() const; - void checkNotFinal() const; - bool isCompatibleType(int qmfType, qpid::types::VariantType qpidType) const; - }; - - struct SchemaImplAccess - { - static SchemaImpl& get(Schema&); - static const SchemaImpl& get(const Schema&); - }; -} - -#endif diff --git a/cpp/src/qmf/SchemaMethod.cpp b/cpp/src/qmf/SchemaMethod.cpp deleted file mode 100644 index e267878238..0000000000 --- a/cpp/src/qmf/SchemaMethod.cpp +++ /dev/null @@ -1,186 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/SchemaMethodImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" -#include "qmf/Hash.h" -#include "qpid/messaging/AddressParser.h" -#include "qpid/management/Buffer.h" - -using namespace std; -using qpid::types::Variant; -using namespace qmf; - -typedef PrivateImplRef<SchemaMethod> PI; - -SchemaMethod::SchemaMethod(SchemaMethodImpl* impl) { PI::ctor(*this, impl); } -SchemaMethod::SchemaMethod(const SchemaMethod& s) : qmf::Handle<SchemaMethodImpl>() { PI::copy(*this, s); } -SchemaMethod::~SchemaMethod() { PI::dtor(*this); } -SchemaMethod& SchemaMethod::operator=(const SchemaMethod& s) { return PI::assign(*this, s); } - -SchemaMethod::SchemaMethod(const string& n, const string& o) { PI::ctor(*this, new SchemaMethodImpl(n, o)); } -void SchemaMethod::setDesc(const string& d) { impl->setDesc(d); } -void SchemaMethod::addArgument(const SchemaProperty& p) { impl->addArgument(p); } -const string& SchemaMethod::getName() const { return impl->getName(); } -const string& SchemaMethod::getDesc() const { return impl->getDesc(); } -uint32_t SchemaMethod::getArgumentCount() const { return impl->getArgumentCount(); } -SchemaProperty SchemaMethod::getArgument(uint32_t i) const { return impl->getArgument(i); } - -//======================================================================================== -// Impl Method Bodies -//======================================================================================== - -SchemaMethodImpl::SchemaMethodImpl(const string& n, const string& options) : name(n) -{ - if (!options.empty()) { - qpid::messaging::AddressParser parser = qpid::messaging::AddressParser(options); - Variant::Map optMap; - Variant::Map::iterator iter; - - parser.parseMap(optMap); - iter = optMap.find("desc"); - if (iter != optMap.end()) { - desc = iter->second.asString(); - optMap.erase(iter); - } - - if (!optMap.empty()) - throw QmfException("Unrecognized option: " + optMap.begin()->first); - } -} - - -SchemaMethodImpl::SchemaMethodImpl(const qpid::types::Variant::Map& map) -{ - Variant::Map::const_iterator iter; - Variant::List::const_iterator lIter; - - iter = map.find("_name"); - if (iter == map.end()) - throw QmfException("SchemaMethod without a _name element"); - name = iter->second.asString(); - - iter = map.find("_desc"); - if (iter != map.end()) - desc = iter->second.asString(); - - iter = map.find("_arguments"); - if (iter != map.end()) { - const Variant::List& argList(iter->second.asList()); - for (lIter = argList.begin(); lIter != argList.end(); lIter++) - addArgument(SchemaProperty(new SchemaPropertyImpl(lIter->asMap()))); - } -} - - -Variant::Map SchemaMethodImpl::asMap() const -{ - Variant::Map map; - Variant::List argList; - - map["_name"] = name; - - if (!desc.empty()) - map["_desc"] = desc; - - for (list<SchemaProperty>::const_iterator iter = arguments.begin(); iter != arguments.end(); iter++) - argList.push_back(SchemaPropertyImplAccess::get(*iter).asMap()); - map["_arguments"] = argList; - - return map; -} - - -SchemaMethodImpl::SchemaMethodImpl(qpid::management::Buffer& buffer) -{ - Variant::Map::const_iterator iter; - Variant::Map argMap; - - buffer.getMap(argMap); - - iter = argMap.find("name"); - if (iter == argMap.end()) - throw QmfException("Received V1 Method without a name"); - name = iter->second.asString(); - - iter = argMap.find("desc"); - if (iter != argMap.end()) - desc = iter->second.asString(); - - iter = argMap.find("argCount"); - if (iter == argMap.end()) - throw QmfException("Received V1 Method without argCount"); - - int64_t count = iter->second.asInt64(); - for (int idx = 0; idx < count; idx++) { - SchemaProperty arg(new SchemaPropertyImpl(buffer)); - addArgument(arg); - } -} - - -SchemaProperty SchemaMethodImpl::getArgument(uint32_t i) const -{ - uint32_t count = 0; - for (list<SchemaProperty>::const_iterator iter = arguments.begin(); iter != arguments.end(); iter++) - if (count++ == i) - return *iter; - - throw IndexOutOfRange(); -} - - -void SchemaMethodImpl::updateHash(Hash& hash) const -{ - hash.update(name); - hash.update(desc); - for (list<SchemaProperty>::const_iterator iter = arguments.begin(); iter != arguments.end(); iter++) - SchemaPropertyImplAccess::get(*iter).updateHash(hash); -} - - -void SchemaMethodImpl::encodeV1(qpid::management::Buffer& buffer) const -{ - Variant::Map map; - - map["name"] = name; - map["argCount"] = (uint64_t) arguments.size(); - if (!desc.empty()) - map["desc"] = desc; - - buffer.putMap(map); - - for (list<SchemaProperty>::const_iterator iter = arguments.begin(); iter != arguments.end(); iter++) - SchemaPropertyImplAccess::get(*iter).encodeV1(buffer, true, true); -} - - -SchemaMethodImpl& SchemaMethodImplAccess::get(SchemaMethod& item) -{ - return *item.impl; -} - - -const SchemaMethodImpl& SchemaMethodImplAccess::get(const SchemaMethod& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/SchemaMethodImpl.h b/cpp/src/qmf/SchemaMethodImpl.h deleted file mode 100644 index 930d48509c..0000000000 --- a/cpp/src/qmf/SchemaMethodImpl.h +++ /dev/null @@ -1,75 +0,0 @@ -#ifndef _QMF_SCHEMA_METHOD_IMPL_H_ -#define _QMF_SCHEMA_METHOD_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/SchemaTypes.h" -#include "qmf/SchemaMethod.h" -#include "qmf/SchemaPropertyImpl.h" -#include "qpid/management/Buffer.h" -#include <list> -#include <string> - -namespace qpid { -namespace management { - class Buffer; -}} - -namespace qmf { - class Hash; - class SchemaMethodImpl : public virtual qpid::RefCounted { - public: - // - // Public impl-only methods - // - SchemaMethodImpl(const qpid::types::Variant::Map& m); - SchemaMethodImpl(qpid::management::Buffer& v1Buffer); - qpid::types::Variant::Map asMap() const; - void updateHash(Hash&) const; - void encodeV1(qpid::management::Buffer&) const; - - // - // Methods from API handle - // - SchemaMethodImpl(const std::string& n, const std::string& options); - - void setDesc(const std::string& d) { desc = d; } - void addArgument(const SchemaProperty& p) { arguments.push_back(p); } - const std::string& getName() const { return name; } - const std::string& getDesc() const { return desc; } - uint32_t getArgumentCount() const { return arguments.size(); } - SchemaProperty getArgument(uint32_t i) const; - - private: - std::string name; - std::string desc; - std::list<SchemaProperty> arguments; - }; - - struct SchemaMethodImplAccess - { - static SchemaMethodImpl& get(SchemaMethod&); - static const SchemaMethodImpl& get(const SchemaMethod&); - }; -} - -#endif diff --git a/cpp/src/qmf/SchemaProperty.cpp b/cpp/src/qmf/SchemaProperty.cpp deleted file mode 100644 index 106127261b..0000000000 --- a/cpp/src/qmf/SchemaProperty.cpp +++ /dev/null @@ -1,434 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/SchemaPropertyImpl.h" -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" -#include "qmf/SchemaTypes.h" -#include "qmf/SchemaProperty.h" -#include "qmf/Hash.h" -#include "qpid/messaging/AddressParser.h" -#include <list> -#include <iostream> - -using namespace std; -using qpid::types::Variant; -using namespace qmf; - -typedef PrivateImplRef<SchemaProperty> PI; - -SchemaProperty::SchemaProperty(SchemaPropertyImpl* impl) { PI::ctor(*this, impl); } -SchemaProperty::SchemaProperty(const SchemaProperty& s) : qmf::Handle<SchemaPropertyImpl>() { PI::copy(*this, s); } -SchemaProperty::~SchemaProperty() { PI::dtor(*this); } -SchemaProperty& SchemaProperty::operator=(const SchemaProperty& s) { return PI::assign(*this, s); } - -SchemaProperty::SchemaProperty(const string& n, int t, const string& o) { PI::ctor(*this, new SchemaPropertyImpl(n, t, o)); } - -void SchemaProperty::setAccess(int a) { impl->setAccess(a); } -void SchemaProperty::setIndex(bool i) { impl->setIndex(i); } -void SchemaProperty::setOptional(bool o) { impl->setOptional(o); } -void SchemaProperty::setUnit(const string& u) { impl->setUnit(u); } -void SchemaProperty::setDesc(const string& d) { impl->setDesc(d); } -void SchemaProperty::setSubtype(const string& s) { impl->setSubtype(s); } -void SchemaProperty::setDirection(int d) { impl->setDirection(d); } - -const string& SchemaProperty::getName() const { return impl->getName(); } -int SchemaProperty::getType() const { return impl->getType(); } -int SchemaProperty::getAccess() const { return impl->getAccess(); } -bool SchemaProperty::isIndex() const { return impl->isIndex(); } -bool SchemaProperty::isOptional() const { return impl->isOptional(); } -const string& SchemaProperty::getUnit() const { return impl->getUnit(); } -const string& SchemaProperty::getDesc() const { return impl->getDesc(); } -const string& SchemaProperty::getSubtype() const { return impl->getSubtype(); } -int SchemaProperty::getDirection() const { return impl->getDirection(); } - -//======================================================================================== -// Impl Method Bodies -//======================================================================================== - -SchemaPropertyImpl::SchemaPropertyImpl(const string& n, int t, const string options) : - name(n), dataType(t), access(ACCESS_READ_ONLY), index(false), - optional(false), direction(DIR_IN) -{ - if (!options.empty()) { - qpid::messaging::AddressParser parser = qpid::messaging::AddressParser(options); - Variant::Map optMap; - Variant::Map::iterator iter; - - parser.parseMap(optMap); - - iter = optMap.find("access"); - if (iter != optMap.end()) { - const string& v(iter->second.asString()); - if (v == "RC") access = ACCESS_READ_CREATE; - else if (v == "RO") access = ACCESS_READ_ONLY; - else if (v == "RW") access = ACCESS_READ_WRITE; - else - throw QmfException("Invalid value for 'access' option. Expected RC, RO, or RW"); - optMap.erase(iter); - } - - iter = optMap.find("index"); - if (iter != optMap.end()) { - index = iter->second.asBool(); - optMap.erase(iter); - } - - iter = optMap.find("optional"); - if (iter != optMap.end()) { - optional = iter->second.asBool(); - optMap.erase(iter); - } - - iter = optMap.find("unit"); - if (iter != optMap.end()) { - unit = iter->second.asString(); - optMap.erase(iter); - } - - iter = optMap.find("desc"); - if (iter != optMap.end()) { - desc = iter->second.asString(); - optMap.erase(iter); - } - - iter = optMap.find("subtype"); - if (iter != optMap.end()) { - subtype = iter->second.asString(); - optMap.erase(iter); - } - - iter = optMap.find("dir"); - if (iter != optMap.end()) { - const string& v(iter->second.asString()); - if (v == "IN") direction = DIR_IN; - else if (v == "OUT") direction = DIR_OUT; - else if (v == "INOUT") direction = DIR_IN_OUT; - else - throw QmfException("Invalid value for 'dir' option. Expected IN, OUT, or INOUT"); - optMap.erase(iter); - } - - if (!optMap.empty()) - throw QmfException("Unexpected option: " + optMap.begin()->first); - } -} - - -SchemaPropertyImpl::SchemaPropertyImpl(const Variant::Map& map) : - access(ACCESS_READ_ONLY), index(false), optional(false), direction(DIR_IN) -{ - Variant::Map::const_iterator iter; - - iter = map.find("_name"); - if (iter == map.end()) - throw QmfException("SchemaProperty without a _name element"); - name = iter->second.asString(); - - iter = map.find("_type"); - if (iter == map.end()) - throw QmfException("SchemaProperty without a _type element"); - const string& ts(iter->second.asString()); - if (ts == "TYPE_VOID") dataType = SCHEMA_DATA_VOID; - else if (ts == "TYPE_BOOL") dataType = SCHEMA_DATA_BOOL; - else if (ts == "TYPE_INT") dataType = SCHEMA_DATA_INT; - else if (ts == "TYPE_FLOAT") dataType = SCHEMA_DATA_FLOAT; - else if (ts == "TYPE_STRING") dataType = SCHEMA_DATA_STRING; - else if (ts == "TYPE_MAP") dataType = SCHEMA_DATA_MAP; - else if (ts == "TYPE_LIST") dataType = SCHEMA_DATA_LIST; - else if (ts == "TYPE_UUID") dataType = SCHEMA_DATA_UUID; - else - throw QmfException("SchemaProperty with an invalid type code: " + ts); - - iter = map.find("_access"); - if (iter != map.end()) { - const string& as(iter->second.asString()); - if (as == "RO") access = ACCESS_READ_ONLY; - else if (as == "RC") access = ACCESS_READ_CREATE; - else if (as == "RW") access = ACCESS_READ_WRITE; - else - throw QmfException("SchemaProperty with an invalid access code: " + as); - } - - iter = map.find("_unit"); - if (iter != map.end()) - unit = iter->second.asString(); - - iter = map.find("_dir"); - if (iter != map.end()) { - const string& ds(iter->second.asString()); - if (ds == "I") direction = DIR_IN; - else if (ds == "O") direction = DIR_OUT; - else if (ds == "IO") direction = DIR_IN_OUT; - else - throw QmfException("SchemaProperty with an invalid direction code: " + ds); - } - - iter = map.find("_desc"); - if (iter != map.end()) - desc = iter->second.asString(); - - iter = map.find("_index"); - if (iter != map.end()) - index = iter->second.asBool(); - - iter = map.find("_subtype"); - if (iter != map.end()) - subtype = iter->second.asString(); -} - - -Variant::Map SchemaPropertyImpl::asMap() const -{ - Variant::Map map; - string ts; - - map["_name"] = name; - - switch (dataType) { - case SCHEMA_DATA_VOID: ts = "TYPE_VOID"; break; - case SCHEMA_DATA_BOOL: ts = "TYPE_BOOL"; break; - case SCHEMA_DATA_INT: ts = "TYPE_INT"; break; - case SCHEMA_DATA_FLOAT: ts = "TYPE_FLOAT"; break; - case SCHEMA_DATA_STRING: ts = "TYPE_STRING"; break; - case SCHEMA_DATA_MAP: ts = "TYPE_MAP"; break; - case SCHEMA_DATA_LIST: ts = "TYPE_LIST"; break; - case SCHEMA_DATA_UUID: ts = "TYPE_UUID"; break; - } - map["_type"] = ts; - - switch (access) { - case ACCESS_READ_ONLY: ts = "RO"; break; - case ACCESS_READ_CREATE: ts = "RC"; break; - case ACCESS_READ_WRITE: ts = "RW"; break; - } - map["_access"] = ts; - - if (!unit.empty()) - map["_unit"] = unit; - - switch (direction) { - case DIR_IN: ts = "I"; break; - case DIR_OUT: ts = "O"; break; - case DIR_IN_OUT: ts = "IO"; break; - } - map["_dir"] = ts; - - if (!desc.empty()) - map["_desc"] = desc; - - if (index) - map["_index"] = true; - - if (!subtype.empty()) - map["_subtype"] = subtype; - - return map; -} - - -SchemaPropertyImpl::SchemaPropertyImpl(qpid::management::Buffer& buffer) : - access(ACCESS_READ_ONLY), index(false), optional(false), direction(DIR_IN) -{ - Variant::Map::const_iterator iter; - Variant::Map pmap; - - buffer.getMap(pmap); - iter = pmap.find("name"); - if (iter == pmap.end()) - throw QmfException("Received V1 Schema property without a name"); - name = iter->second.asString(); - - iter = pmap.find("type"); - if (iter == pmap.end()) - throw QmfException("Received V1 Schema property without a type"); - fromV1TypeCode(iter->second.asInt8()); - - iter = pmap.find("unit"); - if (iter != pmap.end()) - unit = iter->second.asString(); - - iter = pmap.find("desc"); - if (iter != pmap.end()) - desc = iter->second.asString(); - - iter = pmap.find("access"); - if (iter != pmap.end()) { - int8_t val = iter->second.asInt8(); - if (val < 1 || val > 3) - throw QmfException("Received V1 Schema property with invalid 'access' code"); - access = val; - } - - iter = pmap.find("index"); - if (iter != pmap.end()) - index = iter->second.asInt64() != 0; - - iter = pmap.find("optional"); - if (iter != pmap.end()) - optional = iter->second.asInt64() != 0; - - iter = pmap.find("dir"); - if (iter != pmap.end()) { - string dirStr(iter->second.asString()); - if (dirStr == "I") direction = DIR_IN; - else if (dirStr == "O") direction = DIR_OUT; - else if (dirStr == "IO") direction = DIR_IN_OUT; - else - throw QmfException("Received V1 Schema property with invalid 'dir' code"); - } -} - - -void SchemaPropertyImpl::updateHash(Hash& hash) const -{ - hash.update(name); - hash.update((uint8_t) dataType); - hash.update(subtype); - hash.update((uint8_t) access); - hash.update(index); - hash.update(optional); - hash.update(unit); - hash.update(desc); - hash.update((uint8_t) direction); -} - - -void SchemaPropertyImpl::encodeV1(qpid::management::Buffer& buffer, bool isArg, bool isMethodArg) const -{ - Variant::Map pmap; - - pmap["name"] = name; - pmap["type"] = v1TypeCode(); - if (!unit.empty()) - pmap["unit"] = unit; - if (!desc.empty()) - pmap["desc"] = desc; - if (!isArg) { - pmap["access"] = access; - pmap["index"] = index ? 1 : 0; - pmap["optional"] = optional ? 1 : 0; - } else { - if (isMethodArg) { - string dirStr; - switch (direction) { - case DIR_IN : dirStr = "I"; break; - case DIR_OUT : dirStr = "O"; break; - case DIR_IN_OUT : dirStr = "IO"; break; - } - pmap["dir"] = dirStr; - } - } - - buffer.putMap(pmap); -} - - -uint8_t SchemaPropertyImpl::v1TypeCode() const -{ - switch (dataType) { - case SCHEMA_DATA_VOID: return 1; - case SCHEMA_DATA_BOOL: return 11; - case SCHEMA_DATA_INT: - if (subtype == "timestamp") return 8; - if (subtype == "duration") return 9; - return 19; - case SCHEMA_DATA_FLOAT: return 13; - case SCHEMA_DATA_STRING: return 7; - case SCHEMA_DATA_LIST: return 21; - case SCHEMA_DATA_UUID: return 14; - case SCHEMA_DATA_MAP: - if (subtype == "reference") return 10; - if (subtype == "data") return 20; - return 15; - } - - return 1; -} - -void SchemaPropertyImpl::fromV1TypeCode(int8_t code) -{ - switch (code) { - case 1: // U8 - case 2: // U16 - case 3: // U32 - case 4: // U64 - dataType = SCHEMA_DATA_INT; - break; - case 6: // SSTR - case 7: // LSTR - dataType = SCHEMA_DATA_STRING; - break; - case 8: // ABSTIME - dataType = SCHEMA_DATA_INT; - subtype = "timestamp"; - break; - case 9: // DELTATIME - dataType = SCHEMA_DATA_INT; - subtype = "duration"; - break; - case 10: // REF - dataType = SCHEMA_DATA_MAP; - subtype = "reference"; - break; - case 11: // BOOL - dataType = SCHEMA_DATA_BOOL; - break; - case 12: // FLOAT - case 13: // DOUBLE - dataType = SCHEMA_DATA_FLOAT; - break; - case 14: // UUID - dataType = SCHEMA_DATA_UUID; - break; - case 15: // FTABLE - dataType = SCHEMA_DATA_MAP; - break; - case 16: // S8 - case 17: // S16 - case 18: // S32 - case 19: // S64 - dataType = SCHEMA_DATA_INT; - break; - case 20: // OBJECT - dataType = SCHEMA_DATA_MAP; - subtype = "data"; - break; - case 21: // LIST - case 22: // ARRAY - dataType = SCHEMA_DATA_LIST; - break; - default: - throw QmfException("Received V1 schema with an unknown data type"); - } -} - - -SchemaPropertyImpl& SchemaPropertyImplAccess::get(SchemaProperty& item) -{ - return *item.impl; -} - - -const SchemaPropertyImpl& SchemaPropertyImplAccess::get(const SchemaProperty& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/SchemaPropertyImpl.h b/cpp/src/qmf/SchemaPropertyImpl.h deleted file mode 100644 index cdfc29066f..0000000000 --- a/cpp/src/qmf/SchemaPropertyImpl.h +++ /dev/null @@ -1,93 +0,0 @@ -#ifndef _QMF_SCHEMA_PROPERTY_IMPL_H_ -#define _QMF_SCHEMA_PROPERTY_IMPL_H_ - -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/SchemaTypes.h" -#include "qmf/SchemaProperty.h" -#include "qpid/types/Variant.h" -#include "qpid/management/Buffer.h" - -namespace qpid { -namespace management { - class Buffer; -}} - -namespace qmf { - class Hash; - class SchemaPropertyImpl : public virtual qpid::RefCounted { - public: - // - // Public impl-only methods - // - SchemaPropertyImpl(const qpid::types::Variant::Map& m); - SchemaPropertyImpl(qpid::management::Buffer& v1Buffer); - qpid::types::Variant::Map asMap() const; - void updateHash(Hash&) const; - void encodeV1(qpid::management::Buffer&, bool isArg, bool isMethodArg) const; - - // - // Methods from API handle - // - SchemaPropertyImpl(const std::string& n, int t, const std::string o); - void setAccess(int a) { access = a; } - void setIndex(bool i) { index = i; } - void setOptional(bool o) { optional = o; } - void setUnit(const std::string& u) { unit = u; } - void setDesc(const std::string& d) { desc = d; } - void setSubtype(const std::string& s) { subtype = s; } - void setDirection(int d) { direction = d; } - - const std::string& getName() const { return name; } - int getType() const { return dataType; } - int getAccess() const { return access; } - bool isIndex() const { return index; } - bool isOptional() const { return optional; } - const std::string& getUnit() const { return unit; } - const std::string& getDesc() const { return desc; } - const std::string& getSubtype() const { return subtype; } - int getDirection() const { return direction; } - - private: - std::string name; - int dataType; - std::string subtype; - int access; - bool index; - bool optional; - std::string unit; - std::string desc; - int direction; - - uint8_t v1TypeCode() const; - void fromV1TypeCode(int8_t); - }; - - struct SchemaPropertyImplAccess - { - static SchemaPropertyImpl& get(SchemaProperty&); - static const SchemaPropertyImpl& get(const SchemaProperty&); - }; -} - -#endif diff --git a/cpp/src/qmf/Subscription.cpp b/cpp/src/qmf/Subscription.cpp deleted file mode 100644 index 73afc8c79d..0000000000 --- a/cpp/src/qmf/Subscription.cpp +++ /dev/null @@ -1,88 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qmf/PrivateImplRef.h" -#include "qmf/exceptions.h" -#include "qmf/SubscriptionImpl.h" -#include "qmf/DataImpl.h" - -using namespace std; -using namespace qmf; -using qpid::types::Variant; - -typedef PrivateImplRef<Subscription> PI; - -Subscription::Subscription(SubscriptionImpl* impl) { PI::ctor(*this, impl); } -Subscription::Subscription(const Subscription& s) : qmf::Handle<SubscriptionImpl>() { PI::copy(*this, s); } -Subscription::~Subscription() { PI::dtor(*this); } -Subscription& Subscription::operator=(const Subscription& s) { return PI::assign(*this, s); } - -void Subscription::cancel() { impl->cancel(); } -bool Subscription::isActive() const { return impl->isActive(); } -void Subscription::lock() { impl->lock(); } -void Subscription::unlock() { impl->unlock(); } -uint32_t Subscription::getDataCount() const { return impl->getDataCount(); } -Data Subscription::getData(uint32_t i) const { return impl->getData(i); } - - -void SubscriptionImpl::cancel() -{ -} - - -bool SubscriptionImpl::isActive() const -{ - return false; -} - - -void SubscriptionImpl::lock() -{ -} - - -void SubscriptionImpl::unlock() -{ -} - - -uint32_t SubscriptionImpl::getDataCount() const -{ - return 0; -} - - -Data SubscriptionImpl::getData(uint32_t) const -{ - return Data(); -} - - -SubscriptionImpl& SubscriptionImplAccess::get(Subscription& item) -{ - return *item.impl; -} - - -const SubscriptionImpl& SubscriptionImplAccess::get(const Subscription& item) -{ - return *item.impl; -} diff --git a/cpp/src/qmf/SubscriptionImpl.h b/cpp/src/qmf/SubscriptionImpl.h deleted file mode 100644 index 053e3cd00e..0000000000 --- a/cpp/src/qmf/SubscriptionImpl.h +++ /dev/null @@ -1,57 +0,0 @@ -#ifndef _QMF_SUBSCRIPTION_IMPL_H_ -#define _QMF_SUBSCRIPTION_IMPL_H_ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "qpid/RefCounted.h" -#include "qmf/Subscription.h" - -namespace qmf { - class SubscriptionImpl : public virtual qpid::RefCounted { - public: - // - // Public impl-only methods - // - SubscriptionImpl(int p) : placeholder(p) {} - ~SubscriptionImpl(); - - // - // Methods from API handle - // - void cancel(); - bool isActive() const; - void lock(); - void unlock(); - uint32_t getDataCount() const; - Data getData(uint32_t) const; - - private: - int placeholder; - }; - - struct SubscriptionImplAccess - { - static SubscriptionImpl& get(Subscription&); - static const SubscriptionImpl& get(const Subscription&); - }; -} - -#endif diff --git a/cpp/src/qmf/agentCapability.h b/cpp/src/qmf/agentCapability.h deleted file mode 100644 index 6a3f6f8534..0000000000 --- a/cpp/src/qmf/agentCapability.h +++ /dev/null @@ -1,39 +0,0 @@ -#ifndef QMF_AGENT_CAPABILITY_H -#define QMF_AGENT_CAPABILITY_H -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -namespace qmf { - - /** - * Legacy (Qpid 0.7 C++ Agent, 0.7 Broker Agent) capabilities - */ - const uint32_t AGENT_CAPABILITY_LEGACY = 0; - - /** - * Qpid 0.8 QMFv2 capabilities - */ - const uint32_t AGENT_CAPABILITY_0_8 = 1; - const uint32_t AGENT_CAPABILITY_V2_SCHEMA = 1; - const uint32_t AGENT_CAPABILITY_AGENT_PREDICATE = 1; -} - -#endif diff --git a/cpp/src/qmf/constants.cpp b/cpp/src/qmf/constants.cpp deleted file mode 100644 index 6e2fd935a9..0000000000 --- a/cpp/src/qmf/constants.cpp +++ /dev/null @@ -1,77 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include "constants.h" - -using namespace std; -using namespace qmf; - -/** - * Header key strings - */ -const string protocol::HEADER_KEY_APP_ID = "x-amqp-0-10.app-id"; -const string protocol::HEADER_KEY_METHOD = "method"; -const string protocol::HEADER_KEY_OPCODE = "qmf.opcode"; -const string protocol::HEADER_KEY_AGENT = "qmf.agent"; -const string protocol::HEADER_KEY_CONTENT = "qmf.content"; -const string protocol::HEADER_KEY_PARTIAL = "partial"; - -/** - * Header values per-key - */ -const string protocol::HEADER_APP_ID_QMF = "qmf2"; - -const string protocol::HEADER_METHOD_REQUEST = "request"; -const string protocol::HEADER_METHOD_RESPONSE = "response"; -const string protocol::HEADER_METHOD_INDICATION = "indication"; - -const string protocol::HEADER_OPCODE_EXCEPTION = "_exception"; -const string protocol::HEADER_OPCODE_AGENT_LOCATE_REQUEST = "_agent_locate_request"; -const string protocol::HEADER_OPCODE_AGENT_LOCATE_RESPONSE = "_agent_locate_response"; -const string protocol::HEADER_OPCODE_AGENT_HEARTBEAT_INDICATION = "_agent_heartbeat_indication"; -const string protocol::HEADER_OPCODE_QUERY_REQUEST = "_query_request"; -const string protocol::HEADER_OPCODE_QUERY_RESPONSE = "_query_response"; -const string protocol::HEADER_OPCODE_SUBSCRIBE_REQUEST = "_subscribe_request"; -const string protocol::HEADER_OPCODE_SUBSCRIBE_RESPONSE = "_subscribe_response"; -const string protocol::HEADER_OPCODE_SUBSCRIBE_CANCEL_INDICATION = "_subscribe_cancel_indication"; -const string protocol::HEADER_OPCODE_SUBSCRIBE_REFRESH_INDICATION = "_subscribe_refresh_indication"; -const string protocol::HEADER_OPCODE_DATA_INDICATION = "_data_indication"; -const string protocol::HEADER_OPCODE_METHOD_REQUEST = "_method_request"; -const string protocol::HEADER_OPCODE_METHOD_RESPONSE = "_method_response"; - -const string protocol::HEADER_CONTENT_SCHEMA_ID = "_schema_id"; -const string protocol::HEADER_CONTENT_SCHEMA_CLASS = "_schema_class"; -const string protocol::HEADER_CONTENT_OBJECT_ID = "_object_id"; -const string protocol::HEADER_CONTENT_DATA = "_data"; -const string protocol::HEADER_CONTENT_EVENT = "_event"; -const string protocol::HEADER_CONTENT_QUERY = "_query"; - -/** - * Keywords for Agent attributes - */ -const string protocol::AGENT_ATTR_VENDOR = "_vendor"; -const string protocol::AGENT_ATTR_PRODUCT = "_product"; -const string protocol::AGENT_ATTR_INSTANCE = "_instance"; -const string protocol::AGENT_ATTR_NAME = "_name"; -const string protocol::AGENT_ATTR_TIMESTAMP = "_timestamp"; -const string protocol::AGENT_ATTR_HEARTBEAT_INTERVAL = "_heartbeat_interval"; -const string protocol::AGENT_ATTR_EPOCH = "_epoch"; -const string protocol::AGENT_ATTR_SCHEMA_UPDATED_TIMESTAMP = "_schema_updated"; diff --git a/cpp/src/qmf/constants.h b/cpp/src/qmf/constants.h deleted file mode 100644 index 79beaaf1ca..0000000000 --- a/cpp/src/qmf/constants.h +++ /dev/null @@ -1,83 +0,0 @@ -#ifndef QMF_CONSTANTS_H -#define QMF_CONSTANTS_H -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ - -#include <string> - -namespace qmf { - - struct protocol { - /** - * Header key strings - */ - static const std::string HEADER_KEY_APP_ID; - static const std::string HEADER_KEY_METHOD; - static const std::string HEADER_KEY_OPCODE; - static const std::string HEADER_KEY_AGENT; - static const std::string HEADER_KEY_CONTENT; - static const std::string HEADER_KEY_PARTIAL; - - /** - * Header values per-key - */ - static const std::string HEADER_APP_ID_QMF; - - static const std::string HEADER_METHOD_REQUEST; - static const std::string HEADER_METHOD_RESPONSE; - static const std::string HEADER_METHOD_INDICATION; - - static const std::string HEADER_OPCODE_EXCEPTION; - static const std::string HEADER_OPCODE_AGENT_LOCATE_REQUEST; - static const std::string HEADER_OPCODE_AGENT_LOCATE_RESPONSE; - static const std::string HEADER_OPCODE_AGENT_HEARTBEAT_INDICATION; - static const std::string HEADER_OPCODE_QUERY_REQUEST; - static const std::string HEADER_OPCODE_QUERY_RESPONSE; - static const std::string HEADER_OPCODE_SUBSCRIBE_REQUEST; - static const std::string HEADER_OPCODE_SUBSCRIBE_RESPONSE; - static const std::string HEADER_OPCODE_SUBSCRIBE_CANCEL_INDICATION; - static const std::string HEADER_OPCODE_SUBSCRIBE_REFRESH_INDICATION; - static const std::string HEADER_OPCODE_DATA_INDICATION; - static const std::string HEADER_OPCODE_METHOD_REQUEST; - static const std::string HEADER_OPCODE_METHOD_RESPONSE; - - static const std::string HEADER_CONTENT_SCHEMA_ID; - static const std::string HEADER_CONTENT_SCHEMA_CLASS; - static const std::string HEADER_CONTENT_OBJECT_ID; - static const std::string HEADER_CONTENT_DATA; - static const std::string HEADER_CONTENT_EVENT; - static const std::string HEADER_CONTENT_QUERY; - - /** - * Keywords for Agent attributes - */ - static const std::string AGENT_ATTR_VENDOR; - static const std::string AGENT_ATTR_PRODUCT; - static const std::string AGENT_ATTR_INSTANCE; - static const std::string AGENT_ATTR_NAME; - static const std::string AGENT_ATTR_TIMESTAMP; - static const std::string AGENT_ATTR_HEARTBEAT_INTERVAL; - static const std::string AGENT_ATTR_EPOCH; - static const std::string AGENT_ATTR_SCHEMA_UPDATED_TIMESTAMP; - }; -} - -#endif diff --git a/cpp/src/qmf/engine/Agent.cpp b/cpp/src/qmf/engine/Agent.cpp deleted file mode 100644 index 1f08dded94..0000000000 --- a/cpp/src/qmf/engine/Agent.cpp +++ /dev/null @@ -1,915 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/Agent.h" -#include "qmf/engine/MessageImpl.h" -#include "qmf/engine/SchemaImpl.h" -#include "qmf/engine/Typecode.h" -#include "qmf/engine/EventImpl.h" -#include "qmf/engine/ObjectImpl.h" -#include "qmf/engine/ObjectIdImpl.h" -#include "qmf/engine/QueryImpl.h" -#include "qmf/engine/ValueImpl.h" -#include "qmf/engine/Protocol.h" -#include <qpid/framing/Buffer.h> -#include <qpid/framing/Uuid.h> -#include <qpid/framing/FieldTable.h> -#include <qpid/framing/FieldValue.h> -#include <qpid/sys/Mutex.h> -#include <qpid/log/Statement.h> -#include <qpid/sys/Time.h> -#include <string.h> -#include <string> -#include <deque> -#include <map> -#include <iostream> -#include <fstream> -#include <boost/shared_ptr.hpp> -#include <boost/noncopyable.hpp> - -using namespace std; -using namespace qmf::engine; -using namespace qpid::framing; -using namespace qpid::sys; - -namespace qmf { -namespace engine { - - struct AgentEventImpl { - typedef boost::shared_ptr<AgentEventImpl> Ptr; - AgentEvent::EventKind kind; - uint32_t sequence; - string authUserId; - string authToken; - string name; - Object* object; - boost::shared_ptr<ObjectId> objectId; - boost::shared_ptr<Query> query; - boost::shared_ptr<Value> arguments; - string exchange; - string bindingKey; - const SchemaObjectClass* objectClass; - - AgentEventImpl(AgentEvent::EventKind k) : - kind(k), sequence(0), object(0), objectClass(0) {} - ~AgentEventImpl() {} - AgentEvent copy(); - }; - - struct AgentQueryContext { - typedef boost::shared_ptr<AgentQueryContext> Ptr; - uint32_t sequence; - string exchange; - string key; - const SchemaMethod* schemaMethod; - AgentQueryContext() : schemaMethod(0) {} - }; - - class AgentImpl : public boost::noncopyable { - public: - AgentImpl(char* label, bool internalStore); - ~AgentImpl(); - - void setStoreDir(const char* path); - void setTransferDir(const char* path); - void handleRcvMessage(Message& message); - bool getXmtMessage(Message& item) const; - void popXmt(); - bool getEvent(AgentEvent& event) const; - void popEvent(); - void newSession(); - void startProtocol(); - void heartbeat(); - void methodResponse(uint32_t sequence, uint32_t status, char* text, const Value& arguments); - void queryResponse(uint32_t sequence, Object& object, bool prop, bool stat); - void queryComplete(uint32_t sequence); - void registerClass(SchemaObjectClass* cls); - void registerClass(SchemaEventClass* cls); - const ObjectId* addObject(Object& obj, uint64_t persistId); - const ObjectId* allocObjectId(uint64_t persistId); - const ObjectId* allocObjectId(uint32_t persistIdLo, uint32_t persistIdHi); - void raiseEvent(Event& event); - - private: - mutable Mutex lock; - Mutex addLock; - string label; - string queueName; - string storeDir; - string transferDir; - bool internalStore; - uint64_t nextTransientId; - Uuid systemId; - uint32_t requestedBrokerBank; - uint32_t requestedAgentBank; - uint32_t assignedBrokerBank; - uint32_t assignedAgentBank; - AgentAttachment attachment; - uint16_t bootSequence; - uint64_t nextObjectId; - uint32_t nextContextNum; - deque<AgentEventImpl::Ptr> eventQueue; - deque<MessageImpl::Ptr> xmtQueue; - map<uint32_t, AgentQueryContext::Ptr> contextMap; - bool attachComplete; - - static const char* QMF_EXCHANGE; - static const char* DIR_EXCHANGE; - static const char* BROKER_KEY; - static const uint32_t MERR_UNKNOWN_METHOD = 2; - static const uint32_t MERR_UNKNOWN_PACKAGE = 8; - static const uint32_t MERR_UNKNOWN_CLASS = 9; - static const uint32_t MERR_INTERNAL_ERROR = 10; -# define MA_BUFFER_SIZE 65536 - char outputBuffer[MA_BUFFER_SIZE]; - - struct AgentClassKey { - string name; - uint8_t hash[16]; - AgentClassKey(const string& n, const uint8_t* h) : name(n) { - memcpy(hash, h, 16); - } - AgentClassKey(Buffer& buffer) { - buffer.getShortString(name); - buffer.getBin128(hash); - } - string repr() { - return name; - } - }; - - struct AgentClassKeyComp { - bool operator() (const AgentClassKey& lhs, const AgentClassKey& rhs) const - { - if (lhs.name != rhs.name) - return lhs.name < rhs.name; - else - for (int i = 0; i < 16; i++) - if (lhs.hash[i] != rhs.hash[i]) - return lhs.hash[i] < rhs.hash[i]; - return false; - } - }; - - typedef map<AgentClassKey, SchemaObjectClass*, AgentClassKeyComp> ObjectClassMap; - typedef map<AgentClassKey, SchemaEventClass*, AgentClassKeyComp> EventClassMap; - - struct ClassMaps { - ObjectClassMap objectClasses; - EventClassMap eventClasses; - }; - - map<string, ClassMaps> packages; - - AgentEventImpl::Ptr eventDeclareQueue(const string& queueName); - AgentEventImpl::Ptr eventBind(const string& exchange, const string& queue, const string& key); - AgentEventImpl::Ptr eventSetupComplete(); - AgentEventImpl::Ptr eventQuery(uint32_t num, const string& userId, const string& package, const string& cls, - boost::shared_ptr<ObjectId> oid); - AgentEventImpl::Ptr eventMethod(uint32_t num, const string& userId, const string& method, - boost::shared_ptr<ObjectId> oid, boost::shared_ptr<Value> argMap, - const SchemaObjectClass* objectClass); - void sendBufferLH(Buffer& buf, const string& destination, const string& routingKey); - - void sendPackageIndicationLH(const string& packageName); - void sendClassIndicationLH(ClassKind kind, const string& packageName, const AgentClassKey& key); - void sendCommandCompleteLH(const string& exchange, const string& key, uint32_t seq, - uint32_t code = 0, const string& text = "OK"); - void sendMethodErrorLH(uint32_t sequence, const string& key, uint32_t code, const string& text=""); - void handleAttachResponse(Buffer& inBuffer); - void handlePackageRequest(Buffer& inBuffer); - void handleClassQuery(Buffer& inBuffer); - void handleSchemaRequest(Buffer& inBuffer, uint32_t sequence, - const string& replyToExchange, const string& replyToKey); - void handleGetQuery(Buffer& inBuffer, uint32_t sequence, const string& replyTo, const string& userId); - void handleMethodRequest(Buffer& inBuffer, uint32_t sequence, const string& replyTo, const string& userId); - void handleConsoleAddedIndication(); - }; -} -} - -const char* AgentImpl::QMF_EXCHANGE = "qpid.management"; -const char* AgentImpl::DIR_EXCHANGE = "amq.direct"; -const char* AgentImpl::BROKER_KEY = "broker"; - -#define STRING_REF(s) {if (!s.empty()) item.s = const_cast<char*>(s.c_str());} - -AgentEvent AgentEventImpl::copy() -{ - AgentEvent item; - - ::memset(&item, 0, sizeof(AgentEvent)); - item.kind = kind; - item.sequence = sequence; - item.object = object; - item.objectId = objectId.get(); - item.query = query.get(); - item.arguments = arguments.get(); - item.objectClass = objectClass; - - STRING_REF(authUserId); - STRING_REF(authToken); - STRING_REF(name); - STRING_REF(exchange); - STRING_REF(bindingKey); - - return item; -} - -AgentImpl::AgentImpl(char* _label, bool i) : - label(_label), queueName("qmfa-"), internalStore(i), nextTransientId(1), - requestedBrokerBank(0), requestedAgentBank(0), - assignedBrokerBank(0), assignedAgentBank(0), - bootSequence(1), nextObjectId(1), nextContextNum(1), attachComplete(false) -{ - queueName += Uuid(true).str(); -} - -AgentImpl::~AgentImpl() -{ -} - -void AgentImpl::setStoreDir(const char* path) -{ - Mutex::ScopedLock _lock(lock); - if (path) - storeDir = path; - else - storeDir.clear(); -} - -void AgentImpl::setTransferDir(const char* path) -{ - Mutex::ScopedLock _lock(lock); - if (path) - transferDir = path; - else - transferDir.clear(); -} - -void AgentImpl::handleRcvMessage(Message& message) -{ - Buffer inBuffer(message.body, message.length); - uint8_t opcode; - uint32_t sequence; - string replyToExchange(message.replyExchange ? message.replyExchange : ""); - string replyToKey(message.replyKey ? message.replyKey : ""); - string userId(message.userId ? message.userId : ""); - - while (Protocol::checkHeader(inBuffer, &opcode, &sequence)) { - if (opcode == Protocol::OP_ATTACH_RESPONSE) handleAttachResponse(inBuffer); - else if (opcode == Protocol::OP_SCHEMA_REQUEST) handleSchemaRequest(inBuffer, sequence, replyToExchange, replyToKey); - else if (opcode == Protocol::OP_CONSOLE_ADDED_INDICATION) handleConsoleAddedIndication(); - else if (opcode == Protocol::OP_GET_QUERY) handleGetQuery(inBuffer, sequence, replyToKey, userId); - else if (opcode == Protocol::OP_METHOD_REQUEST) handleMethodRequest(inBuffer, sequence, replyToKey, userId); - else { - QPID_LOG(error, "AgentImpl::handleRcvMessage invalid opcode=" << opcode); - break; - } - } -} - -bool AgentImpl::getXmtMessage(Message& item) const -{ - Mutex::ScopedLock _lock(lock); - if (xmtQueue.empty()) - return false; - item = xmtQueue.front()->copy(); - return true; -} - -void AgentImpl::popXmt() -{ - Mutex::ScopedLock _lock(lock); - if (!xmtQueue.empty()) - xmtQueue.pop_front(); -} - -bool AgentImpl::getEvent(AgentEvent& event) const -{ - Mutex::ScopedLock _lock(lock); - if (eventQueue.empty()) - return false; - event = eventQueue.front()->copy(); - return true; -} - -void AgentImpl::popEvent() -{ - Mutex::ScopedLock _lock(lock); - if (!eventQueue.empty()) - eventQueue.pop_front(); -} - -void AgentImpl::newSession() -{ - Mutex::ScopedLock _lock(lock); - eventQueue.clear(); - xmtQueue.clear(); - eventQueue.push_back(eventDeclareQueue(queueName)); - eventQueue.push_back(eventBind("amq.direct", queueName, queueName)); - eventQueue.push_back(eventSetupComplete()); -} - -void AgentImpl::startProtocol() -{ - Mutex::ScopedLock _lock(lock); - char rawbuffer[512]; - Buffer buffer(rawbuffer, 512); - - Protocol::encodeHeader(buffer, Protocol::OP_ATTACH_REQUEST); - buffer.putShortString(label); - systemId.encode(buffer); - buffer.putLong(requestedBrokerBank); - buffer.putLong(requestedAgentBank); - sendBufferLH(buffer, QMF_EXCHANGE, BROKER_KEY); - QPID_LOG(trace, "SENT AttachRequest: reqBroker=" << requestedBrokerBank << - " reqAgent=" << requestedAgentBank); -} - -void AgentImpl::heartbeat() -{ - Mutex::ScopedLock _lock(lock); - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - - Protocol::encodeHeader(buffer, Protocol::OP_HEARTBEAT_INDICATION); - buffer.putLongLong(uint64_t(Duration(EPOCH, now()))); - stringstream key; - key << "console.heartbeat." << assignedBrokerBank << "." << assignedAgentBank; - sendBufferLH(buffer, QMF_EXCHANGE, key.str()); - QPID_LOG(trace, "SENT HeartbeatIndication"); -} - -void AgentImpl::methodResponse(uint32_t sequence, uint32_t status, char* text, const Value& argMap) -{ - Mutex::ScopedLock _lock(lock); - map<uint32_t, AgentQueryContext::Ptr>::iterator iter = contextMap.find(sequence); - if (iter == contextMap.end()) - return; - AgentQueryContext::Ptr context = iter->second; - contextMap.erase(iter); - - char* buf(outputBuffer); - uint32_t bufLen(114 + strlen(text)); // header(8) + status(4) + mstring(2 + size) + margin(100) - bool allocated(false); - - if (status == 0) { - for (vector<const SchemaArgument*>::const_iterator aIter = context->schemaMethod->impl->arguments.begin(); - aIter != context->schemaMethod->impl->arguments.end(); aIter++) { - const SchemaArgument* schemaArg = *aIter; - if (schemaArg->getDirection() == DIR_OUT || schemaArg->getDirection() == DIR_IN_OUT) { - if (argMap.keyInMap(schemaArg->getName())) { - const Value* val = argMap.byKey(schemaArg->getName()); - bufLen += val->impl->encodedSize(); - } else { - Value val(schemaArg->getType()); - bufLen += val.impl->encodedSize(); - } - } - } - } - - if (bufLen > MA_BUFFER_SIZE) { - buf = (char*) malloc(bufLen); - allocated = true; - } - - Buffer buffer(buf, bufLen); - Protocol::encodeHeader(buffer, Protocol::OP_METHOD_RESPONSE, context->sequence); - buffer.putLong(status); - buffer.putMediumString(text); - if (status == 0) { - for (vector<const SchemaArgument*>::const_iterator aIter = context->schemaMethod->impl->arguments.begin(); - aIter != context->schemaMethod->impl->arguments.end(); aIter++) { - const SchemaArgument* schemaArg = *aIter; - if (schemaArg->getDirection() == DIR_OUT || schemaArg->getDirection() == DIR_IN_OUT) { - if (argMap.keyInMap(schemaArg->getName())) { - const Value* val = argMap.byKey(schemaArg->getName()); - val->impl->encode(buffer); - } else { - Value val(schemaArg->getType()); - val.impl->encode(buffer); - } - } - } - } - sendBufferLH(buffer, context->exchange, context->key); - if (allocated) - free(buf); - QPID_LOG(trace, "SENT MethodResponse seq=" << context->sequence << " status=" << status << " text=" << text); -} - -void AgentImpl::queryResponse(uint32_t sequence, Object& object, bool prop, bool stat) -{ - Mutex::ScopedLock _lock(lock); - map<uint32_t, AgentQueryContext::Ptr>::iterator iter = contextMap.find(sequence); - if (iter == contextMap.end()) - return; - AgentQueryContext::Ptr context = iter->second; - - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_OBJECT_INDICATION, context->sequence); - - object.impl->encodeSchemaKey(buffer); - object.impl->encodeManagedObjectData(buffer); - if (prop) - object.impl->encodeProperties(buffer); - if (stat) - object.impl->encodeStatistics(buffer); - - sendBufferLH(buffer, context->exchange, context->key); - QPID_LOG(trace, "SENT ContentIndication seq=" << context->sequence); -} - -void AgentImpl::queryComplete(uint32_t sequence) -{ - Mutex::ScopedLock _lock(lock); - map<uint32_t, AgentQueryContext::Ptr>::iterator iter = contextMap.find(sequence); - if (iter == contextMap.end()) - return; - - AgentQueryContext::Ptr context = iter->second; - contextMap.erase(iter); - sendCommandCompleteLH(context->exchange, context->key, context->sequence, 0, "OK"); -} - -void AgentImpl::registerClass(SchemaObjectClass* cls) -{ - Mutex::ScopedLock _lock(lock); - bool newPackage = false; - - map<string, ClassMaps>::iterator iter = packages.find(cls->getClassKey()->getPackageName()); - if (iter == packages.end()) { - packages[cls->getClassKey()->getPackageName()] = ClassMaps(); - iter = packages.find(cls->getClassKey()->getPackageName()); - newPackage = true; - } - - AgentClassKey key(cls->getClassKey()->getClassName(), cls->getClassKey()->getHash()); - iter->second.objectClasses[key] = cls; - - // Indicate this new schema if connected. - - if (attachComplete) { - - if (newPackage) { - sendPackageIndicationLH(iter->first); - } - sendClassIndicationLH(CLASS_OBJECT, iter->first, key); - } -} - -void AgentImpl::registerClass(SchemaEventClass* cls) -{ - Mutex::ScopedLock _lock(lock); - bool newPackage = false; - - map<string, ClassMaps>::iterator iter = packages.find(cls->getClassKey()->getPackageName()); - if (iter == packages.end()) { - packages[cls->getClassKey()->getPackageName()] = ClassMaps(); - iter = packages.find(cls->getClassKey()->getPackageName()); - newPackage = true; - } - - AgentClassKey key(cls->getClassKey()->getClassName(), cls->getClassKey()->getHash()); - iter->second.eventClasses[key] = cls; - - // Indicate this new schema if connected. - - if (attachComplete) { - - if (newPackage) { - sendPackageIndicationLH(iter->first); - } - sendClassIndicationLH(CLASS_EVENT, iter->first, key); - } -} - -const ObjectId* AgentImpl::addObject(Object&, uint64_t) -{ - Mutex::ScopedLock _lock(lock); - return 0; -} - -const ObjectId* AgentImpl::allocObjectId(uint64_t persistId) -{ - Mutex::ScopedLock _lock(lock); - uint16_t sequence = persistId ? 0 : bootSequence; - uint64_t objectNum = persistId ? persistId : nextObjectId++; - - ObjectId* oid = ObjectIdImpl::factory(&attachment, 0, sequence, objectNum); - return oid; -} - -const ObjectId* AgentImpl::allocObjectId(uint32_t persistIdLo, uint32_t persistIdHi) -{ - return allocObjectId(((uint64_t) persistIdHi) << 32 | (uint64_t) persistIdLo); -} - -void AgentImpl::raiseEvent(Event& event) -{ - Mutex::ScopedLock _lock(lock); - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_EVENT_INDICATION); - - event.impl->encodeSchemaKey(buffer); - buffer.putLongLong(uint64_t(Duration(EPOCH, now()))); - event.impl->encode(buffer); - string key(event.impl->getRoutingKey(assignedBrokerBank, assignedAgentBank)); - - sendBufferLH(buffer, QMF_EXCHANGE, key); - QPID_LOG(trace, "SENT EventIndication"); -} - -AgentEventImpl::Ptr AgentImpl::eventDeclareQueue(const string& name) -{ - AgentEventImpl::Ptr event(new AgentEventImpl(AgentEvent::DECLARE_QUEUE)); - event->name = name; - - return event; -} - -AgentEventImpl::Ptr AgentImpl::eventBind(const string& exchange, const string& queue, - const string& key) -{ - AgentEventImpl::Ptr event(new AgentEventImpl(AgentEvent::BIND)); - event->name = queue; - event->exchange = exchange; - event->bindingKey = key; - - return event; -} - -AgentEventImpl::Ptr AgentImpl::eventSetupComplete() -{ - AgentEventImpl::Ptr event(new AgentEventImpl(AgentEvent::SETUP_COMPLETE)); - return event; -} - -AgentEventImpl::Ptr AgentImpl::eventQuery(uint32_t num, const string& userId, const string& package, - const string& cls, boost::shared_ptr<ObjectId> oid) -{ - AgentEventImpl::Ptr event(new AgentEventImpl(AgentEvent::GET_QUERY)); - event->sequence = num; - event->authUserId = userId; - if (oid.get()) - event->query.reset(new Query(oid.get())); - else - event->query.reset(new Query(cls.c_str(), package.c_str())); - return event; -} - -AgentEventImpl::Ptr AgentImpl::eventMethod(uint32_t num, const string& userId, const string& method, - boost::shared_ptr<ObjectId> oid, boost::shared_ptr<Value> argMap, - const SchemaObjectClass* objectClass) -{ - AgentEventImpl::Ptr event(new AgentEventImpl(AgentEvent::METHOD_CALL)); - event->sequence = num; - event->authUserId = userId; - event->name = method; - event->objectId = oid; - event->arguments = argMap; - event->objectClass = objectClass; - return event; -} - -void AgentImpl::sendBufferLH(Buffer& buf, const string& destination, const string& routingKey) -{ - uint32_t length = buf.getPosition(); - MessageImpl::Ptr message(new MessageImpl); - - buf.reset(); - buf.getRawData(message->body, length); - message->destination = destination; - message->routingKey = routingKey; - message->replyExchange = "amq.direct"; - message->replyKey = queueName; - - xmtQueue.push_back(message); -} - -void AgentImpl::sendPackageIndicationLH(const string& packageName) -{ - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_PACKAGE_INDICATION); - buffer.putShortString(packageName); - sendBufferLH(buffer, QMF_EXCHANGE, BROKER_KEY); - QPID_LOG(trace, "SENT PackageIndication: package_name=" << packageName); -} - -void AgentImpl::sendClassIndicationLH(ClassKind kind, const string& packageName, const AgentClassKey& key) -{ - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_CLASS_INDICATION); - buffer.putOctet((int) kind); - buffer.putShortString(packageName); - buffer.putShortString(key.name); - buffer.putBin128(const_cast<uint8_t*>(key.hash)); // const_cast needed for older Qpid libraries - sendBufferLH(buffer, QMF_EXCHANGE, BROKER_KEY); - QPID_LOG(trace, "SENT ClassIndication: package_name=" << packageName << " class_name=" << key.name); -} - -void AgentImpl::sendCommandCompleteLH(const string& exchange, const string& replyToKey, - uint32_t sequence, uint32_t code, const string& text) -{ - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_COMMAND_COMPLETE, sequence); - buffer.putLong(code); - buffer.putShortString(text); - sendBufferLH(buffer, exchange, replyToKey); - QPID_LOG(trace, "SENT CommandComplete: seq=" << sequence << " code=" << code << " text=" << text); -} - -void AgentImpl::sendMethodErrorLH(uint32_t sequence, const string& key, uint32_t code, const string& text) -{ - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_METHOD_RESPONSE, sequence); - buffer.putLong(code); - - string fulltext; - switch (code) { - case MERR_UNKNOWN_PACKAGE: fulltext = "Unknown Package"; break; - case MERR_UNKNOWN_CLASS: fulltext = "Unknown Class"; break; - case MERR_UNKNOWN_METHOD: fulltext = "Unknown Method"; break; - case MERR_INTERNAL_ERROR: fulltext = "Internal Error"; break; - default: fulltext = "Unspecified Error"; break; - } - - if (!text.empty()) { - fulltext += " ("; - fulltext += text; - fulltext += ")"; - } - - buffer.putMediumString(fulltext); - sendBufferLH(buffer, DIR_EXCHANGE, key); - QPID_LOG(trace, "SENT MethodResponse: errorCode=" << code << " text=" << fulltext); -} - -void AgentImpl::handleAttachResponse(Buffer& inBuffer) -{ - Mutex::ScopedLock _lock(lock); - - assignedBrokerBank = inBuffer.getLong(); - assignedAgentBank = inBuffer.getLong(); - - QPID_LOG(trace, "RCVD AttachResponse: broker=" << assignedBrokerBank << " agent=" << assignedAgentBank); - - if ((assignedBrokerBank != requestedBrokerBank) || - (assignedAgentBank != requestedAgentBank)) { - if (requestedAgentBank == 0) { - QPID_LOG(notice, "Initial object-id bank assigned: " << assignedBrokerBank << "." << - assignedAgentBank); - } else { - QPID_LOG(warning, "Collision in object-id! New bank assigned: " << assignedBrokerBank << - "." << assignedAgentBank); - } - //storeData(); // TODO - requestedBrokerBank = assignedBrokerBank; - requestedAgentBank = assignedAgentBank; - } - - attachment.setBanks(assignedBrokerBank, assignedAgentBank); - - // Bind to qpid.management to receive commands - stringstream key; - key << "agent." << assignedBrokerBank << "." << assignedAgentBank; - eventQueue.push_back(eventBind(QMF_EXCHANGE, queueName, key.str())); - - // Send package indications for all local packages - for (map<string, ClassMaps>::iterator pIter = packages.begin(); - pIter != packages.end(); - pIter++) { - sendPackageIndicationLH(pIter->first); - - // Send class indications for all local classes - ClassMaps cMap = pIter->second; - for (ObjectClassMap::iterator cIter = cMap.objectClasses.begin(); - cIter != cMap.objectClasses.end(); cIter++) - sendClassIndicationLH(CLASS_OBJECT, pIter->first, cIter->first); - for (EventClassMap::iterator cIter = cMap.eventClasses.begin(); - cIter != cMap.eventClasses.end(); cIter++) - sendClassIndicationLH(CLASS_EVENT, pIter->first, cIter->first); - } - - attachComplete = true; -} - -void AgentImpl::handlePackageRequest(Buffer&) -{ - Mutex::ScopedLock _lock(lock); -} - -void AgentImpl::handleClassQuery(Buffer&) -{ - Mutex::ScopedLock _lock(lock); -} - -void AgentImpl::handleSchemaRequest(Buffer& inBuffer, uint32_t sequence, - const string& replyExchange, const string& replyKey) -{ - Mutex::ScopedLock _lock(lock); - string rExchange(replyExchange); - string rKey(replyKey); - string packageName; - inBuffer.getShortString(packageName); - AgentClassKey key(inBuffer); - - if (rExchange.empty()) - rExchange = QMF_EXCHANGE; - if (rKey.empty()) - rKey = BROKER_KEY; - - QPID_LOG(trace, "RCVD SchemaRequest: package=" << packageName << " class=" << key.name); - - map<string, ClassMaps>::iterator pIter = packages.find(packageName); - if (pIter == packages.end()) { - sendCommandCompleteLH(rExchange, rKey, sequence, 1, "package not found"); - return; - } - - ClassMaps cMap = pIter->second; - ObjectClassMap::iterator ocIter = cMap.objectClasses.find(key); - if (ocIter != cMap.objectClasses.end()) { - SchemaObjectClass* oImpl = ocIter->second; - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_SCHEMA_RESPONSE, sequence); - oImpl->impl->encode(buffer); - sendBufferLH(buffer, rExchange, rKey); - QPID_LOG(trace, "SENT SchemaResponse: (object) package=" << packageName << " class=" << key.name); - return; - } - - EventClassMap::iterator ecIter = cMap.eventClasses.find(key); - if (ecIter != cMap.eventClasses.end()) { - SchemaEventClass* eImpl = ecIter->second; - Buffer buffer(outputBuffer, MA_BUFFER_SIZE); - Protocol::encodeHeader(buffer, Protocol::OP_SCHEMA_RESPONSE, sequence); - eImpl->impl->encode(buffer); - sendBufferLH(buffer, rExchange, rKey); - QPID_LOG(trace, "SENT SchemaResponse: (event) package=" << packageName << " class=" << key.name); - return; - } - - sendCommandCompleteLH(rExchange, rKey, sequence, 1, "class not found"); -} - -void AgentImpl::handleGetQuery(Buffer& inBuffer, uint32_t sequence, const string& replyTo, const string& userId) -{ - Mutex::ScopedLock _lock(lock); - FieldTable ft; - FieldTable::ValuePtr value; - map<string, ClassMaps>::const_iterator pIter = packages.end(); - string pname; - string cname; - string oidRepr; - boost::shared_ptr<ObjectId> oid; - - ft.decode(inBuffer); - - QPID_LOG(trace, "RCVD GetQuery: seq=" << sequence << " map=" << ft); - - value = ft.get("_package"); - if (value.get() && value->convertsTo<string>()) { - pname = value->get<string>(); - pIter = packages.find(pname); - if (pIter == packages.end()) { - sendCommandCompleteLH(DIR_EXCHANGE, replyTo, sequence); - return; - } - } - - value = ft.get("_class"); - if (value.get() && value->convertsTo<string>()) { - cname = value->get<string>(); - // TODO - check for validity of class (in package or any package) - if (pIter == packages.end()) { - } else { - - } - } - - value = ft.get("_objectid"); - if (value.get() && value->convertsTo<string>()) { - oidRepr = value->get<string>(); - oid.reset(new ObjectId()); - oid->impl->fromString(oidRepr); - } - - AgentQueryContext::Ptr context(new AgentQueryContext); - uint32_t contextNum = nextContextNum++; - context->sequence = sequence; - context->exchange = DIR_EXCHANGE; - context->key = replyTo; - contextMap[contextNum] = context; - - eventQueue.push_back(eventQuery(contextNum, userId, pname, cname, oid)); -} - -void AgentImpl::handleMethodRequest(Buffer& buffer, uint32_t sequence, const string& replyTo, const string& userId) -{ - Mutex::ScopedLock _lock(lock); - string pname; - string method; - boost::shared_ptr<ObjectId> oid(ObjectIdImpl::factory(buffer)); - buffer.getShortString(pname); - AgentClassKey classKey(buffer); - buffer.getShortString(method); - - QPID_LOG(trace, "RCVD MethodRequest seq=" << sequence << " method=" << method); - - map<string, ClassMaps>::const_iterator pIter = packages.find(pname); - if (pIter == packages.end()) { - sendMethodErrorLH(sequence, replyTo, MERR_UNKNOWN_PACKAGE, pname); - return; - } - - ObjectClassMap::const_iterator cIter = pIter->second.objectClasses.find(classKey); - if (cIter == pIter->second.objectClasses.end()) { - sendMethodErrorLH(sequence, replyTo, MERR_UNKNOWN_CLASS, classKey.repr()); - return; - } - - const SchemaObjectClass* schema = cIter->second; - vector<const SchemaMethod*>::const_iterator mIter = schema->impl->methods.begin(); - for (; mIter != schema->impl->methods.end(); mIter++) { - if ((*mIter)->getName() == method) - break; - } - - if (mIter == schema->impl->methods.end()) { - sendMethodErrorLH(sequence, replyTo, MERR_UNKNOWN_METHOD, method); - return; - } - - const SchemaMethod* schemaMethod = *mIter; - boost::shared_ptr<Value> argMap(new Value(TYPE_MAP)); - Value* value; - for (vector<const SchemaArgument*>::const_iterator aIter = schemaMethod->impl->arguments.begin(); - aIter != schemaMethod->impl->arguments.end(); aIter++) { - const SchemaArgument* schemaArg = *aIter; - if (schemaArg->getDirection() == DIR_IN || schemaArg->getDirection() == DIR_IN_OUT) - value = ValueImpl::factory(schemaArg->getType(), buffer); - else - value = ValueImpl::factory(schemaArg->getType()); - argMap->insert(schemaArg->getName(), value); - } - - AgentQueryContext::Ptr context(new AgentQueryContext); - uint32_t contextNum = nextContextNum++; - context->sequence = sequence; - context->exchange = DIR_EXCHANGE; - context->key = replyTo; - context->schemaMethod = schemaMethod; - contextMap[contextNum] = context; - - eventQueue.push_back(eventMethod(contextNum, userId, method, oid, argMap, schema)); -} - -void AgentImpl::handleConsoleAddedIndication() -{ - Mutex::ScopedLock _lock(lock); -} - -//================================================================== -// Wrappers -//================================================================== - -Agent::Agent(char* label, bool internalStore) { impl = new AgentImpl(label, internalStore); } -Agent::~Agent() { delete impl; } -void Agent::setStoreDir(const char* path) { impl->setStoreDir(path); } -void Agent::setTransferDir(const char* path) { impl->setTransferDir(path); } -void Agent::handleRcvMessage(Message& message) { impl->handleRcvMessage(message); } -bool Agent::getXmtMessage(Message& item) const { return impl->getXmtMessage(item); } -void Agent::popXmt() { impl->popXmt(); } -bool Agent::getEvent(AgentEvent& event) const { return impl->getEvent(event); } -void Agent::popEvent() { impl->popEvent(); } -void Agent::newSession() { impl->newSession(); } -void Agent::startProtocol() { impl->startProtocol(); } -void Agent::heartbeat() { impl->heartbeat(); } -void Agent::methodResponse(uint32_t sequence, uint32_t status, char* text, const Value& arguments) { impl->methodResponse(sequence, status, text, arguments); } -void Agent::queryResponse(uint32_t sequence, Object& object, bool prop, bool stat) { impl->queryResponse(sequence, object, prop, stat); } -void Agent::queryComplete(uint32_t sequence) { impl->queryComplete(sequence); } -void Agent::registerClass(SchemaObjectClass* cls) { impl->registerClass(cls); } -void Agent::registerClass(SchemaEventClass* cls) { impl->registerClass(cls); } -const ObjectId* Agent::addObject(Object& obj, uint64_t persistId) { return impl->addObject(obj, persistId); } -const ObjectId* Agent::allocObjectId(uint64_t persistId) { return impl->allocObjectId(persistId); } -const ObjectId* Agent::allocObjectId(uint32_t persistIdLo, uint32_t persistIdHi) { return impl->allocObjectId(persistIdLo, persistIdHi); } -void Agent::raiseEvent(Event& event) { impl->raiseEvent(event); } - diff --git a/cpp/src/qmf/engine/BrokerProxyImpl.cpp b/cpp/src/qmf/engine/BrokerProxyImpl.cpp deleted file mode 100644 index 5fc71979fd..0000000000 --- a/cpp/src/qmf/engine/BrokerProxyImpl.cpp +++ /dev/null @@ -1,827 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/BrokerProxyImpl.h" -#include "qmf/engine/ConsoleImpl.h" -#include "qmf/engine/Protocol.h" -#include "qpid/Address.h" -#include "qpid/sys/SystemInfo.h" -#include <qpid/log/Statement.h> -#include <qpid/StringUtils.h> -#include <string.h> -#include <iostream> -#include <fstream> - -using namespace std; -using namespace qmf::engine; -using namespace qpid::framing; -using namespace qpid::sys; - -namespace { - const char* QMF_EXCHANGE = "qpid.management"; - const char* DIR_EXCHANGE = "amq.direct"; - const char* BROKER_KEY = "broker"; - const char* BROKER_PACKAGE = "org.apache.qpid.broker"; - const char* AGENT_CLASS = "agent"; - const char* BROKER_AGENT_KEY = "agent.1.0"; -} - -const Object* QueryResponseImpl::getObject(uint32_t idx) const -{ - vector<ObjectPtr>::const_iterator iter = results.begin(); - - while (idx > 0) { - if (iter == results.end()) - return 0; - iter++; - idx--; - } - - return iter->get(); -} - -#define STRING_REF(s) {if (!s.empty()) item.s = const_cast<char*>(s.c_str());} - -BrokerEvent BrokerEventImpl::copy() -{ - BrokerEvent item; - - ::memset(&item, 0, sizeof(BrokerEvent)); - item.kind = kind; - - STRING_REF(name); - STRING_REF(exchange); - STRING_REF(bindingKey); - item.context = context; - item.queryResponse = queryResponse.get(); - item.methodResponse = methodResponse.get(); - - return item; -} - -BrokerProxyImpl::BrokerProxyImpl(BrokerProxy& pub, Console& _console) : publicObject(pub), console(_console) -{ - stringstream qn; - qpid::Address addr; - - SystemInfo::getLocalHostname(addr); - qn << "qmfc-" << SystemInfo::getProcessName() << "-" << addr << "-" << SystemInfo::getProcessId(); - queueName = qn.str(); - - seqMgr.setUnsolicitedContext(SequenceContext::Ptr(new StaticContext(*this))); -} - -void BrokerProxyImpl::sessionOpened(SessionHandle& /*sh*/) -{ - Mutex::ScopedLock _lock(lock); - agentList.clear(); - eventQueue.clear(); - xmtQueue.clear(); - eventQueue.push_back(eventDeclareQueue(queueName)); - eventQueue.push_back(eventBind(DIR_EXCHANGE, queueName, queueName)); - eventQueue.push_back(eventSetupComplete()); - - // TODO: Store session handle -} - -void BrokerProxyImpl::sessionClosed() -{ - Mutex::ScopedLock _lock(lock); - agentList.clear(); - eventQueue.clear(); - xmtQueue.clear(); -} - -void BrokerProxyImpl::startProtocol() -{ - AgentProxyPtr agent(AgentProxyImpl::factory(console, publicObject, 0, "Agent embedded in broker")); - { - Mutex::ScopedLock _lock(lock); - char rawbuffer[512]; - Buffer buffer(rawbuffer, 512); - - agentList[0] = agent; - - requestsOutstanding = 1; - topicBound = false; - uint32_t sequence(seqMgr.reserve()); - Protocol::encodeHeader(buffer, Protocol::OP_BROKER_REQUEST, sequence); - sendBufferLH(buffer, QMF_EXCHANGE, BROKER_KEY); - QPID_LOG(trace, "SENT BrokerRequest seq=" << sequence); - } - - console.impl->eventAgentAdded(agent); -} - -void BrokerProxyImpl::sendBufferLH(Buffer& buf, const string& destination, const string& routingKey) -{ - uint32_t length = buf.getPosition(); - MessageImpl::Ptr message(new MessageImpl); - - buf.reset(); - buf.getRawData(message->body, length); - message->destination = destination; - message->routingKey = routingKey; - message->replyExchange = DIR_EXCHANGE; - message->replyKey = queueName; - - xmtQueue.push_back(message); -} - -void BrokerProxyImpl::handleRcvMessage(Message& message) -{ - Buffer inBuffer(message.body, message.length); - uint8_t opcode; - uint32_t sequence; - - while (Protocol::checkHeader(inBuffer, &opcode, &sequence)) - seqMgr.dispatch(opcode, sequence, message.routingKey ? string(message.routingKey) : string(), inBuffer); -} - -bool BrokerProxyImpl::getXmtMessage(Message& item) const -{ - Mutex::ScopedLock _lock(lock); - if (xmtQueue.empty()) - return false; - item = xmtQueue.front()->copy(); - return true; -} - -void BrokerProxyImpl::popXmt() -{ - Mutex::ScopedLock _lock(lock); - if (!xmtQueue.empty()) - xmtQueue.pop_front(); -} - -bool BrokerProxyImpl::getEvent(BrokerEvent& event) const -{ - Mutex::ScopedLock _lock(lock); - if (eventQueue.empty()) - return false; - event = eventQueue.front()->copy(); - return true; -} - -void BrokerProxyImpl::popEvent() -{ - Mutex::ScopedLock _lock(lock); - if (!eventQueue.empty()) - eventQueue.pop_front(); -} - -uint32_t BrokerProxyImpl::agentCount() const -{ - Mutex::ScopedLock _lock(lock); - return agentList.size(); -} - -const AgentProxy* BrokerProxyImpl::getAgent(uint32_t idx) const -{ - Mutex::ScopedLock _lock(lock); - for (map<uint32_t, AgentProxyPtr>::const_iterator iter = agentList.begin(); - iter != agentList.end(); iter++) - if (idx-- == 0) - return iter->second.get(); - return 0; -} - -void BrokerProxyImpl::sendQuery(const Query& query, void* context, const AgentProxy* agent) -{ - SequenceContext::Ptr queryContext(new QueryContext(*this, context)); - Mutex::ScopedLock _lock(lock); - bool sent = false; - if (agent != 0) { - if (sendGetRequestLH(queryContext, query, agent)) - sent = true; - } else { - // TODO (optimization) only send queries to agents that have the requested class+package - for (map<uint32_t, AgentProxyPtr>::const_iterator iter = agentList.begin(); - iter != agentList.end(); iter++) { - if (sendGetRequestLH(queryContext, query, iter->second.get())) - sent = true; - } - } - - if (!sent) { - queryContext->reserve(); - queryContext->release(); - } -} - -bool BrokerProxyImpl::sendGetRequestLH(SequenceContext::Ptr queryContext, const Query& query, const AgentProxy* agent) -{ - if (query.impl->singleAgent()) { - if (query.impl->agentBank() != agent->getAgentBank()) - return false; - } - stringstream key; - Buffer outBuffer(outputBuffer, MA_BUFFER_SIZE); - uint32_t sequence(seqMgr.reserve(queryContext)); - agent->impl->addSequence(sequence); - - Protocol::encodeHeader(outBuffer, Protocol::OP_GET_QUERY, sequence); - query.impl->encode(outBuffer); - key << "agent.1." << agent->impl->agentBank; - sendBufferLH(outBuffer, QMF_EXCHANGE, key.str()); - QPID_LOG(trace, "SENT GetQuery seq=" << sequence << " key=" << key.str()); - return true; -} - -string BrokerProxyImpl::encodeMethodArguments(const SchemaMethod* schema, const Value* argmap, Buffer& buffer) -{ - int argCount = schema->getArgumentCount(); - - if (argmap == 0 || !argmap->isMap()) - return string("Arguments must be in a map value"); - - for (int aIdx = 0; aIdx < argCount; aIdx++) { - const SchemaArgument* arg(schema->getArgument(aIdx)); - if (arg->getDirection() == DIR_IN || arg->getDirection() == DIR_IN_OUT) { - if (argmap->keyInMap(arg->getName())) { - const Value* argVal(argmap->byKey(arg->getName())); - if (argVal->getType() != arg->getType()) - return string("Argument is the wrong type: ") + arg->getName(); - argVal->impl->encode(buffer); - } else { - Value defaultValue(arg->getType()); - defaultValue.impl->encode(buffer); - } - } - } - - return string(); -} - -string BrokerProxyImpl::encodedSizeMethodArguments(const SchemaMethod* schema, const Value* argmap, uint32_t& size) -{ - int argCount = schema->getArgumentCount(); - - if (argmap == 0 || !argmap->isMap()) - return string("Arguments must be in a map value"); - - for (int aIdx = 0; aIdx < argCount; aIdx++) { - const SchemaArgument* arg(schema->getArgument(aIdx)); - if (arg->getDirection() == DIR_IN || arg->getDirection() == DIR_IN_OUT) { - if (argmap->keyInMap(arg->getName())) { - const Value* argVal(argmap->byKey(arg->getName())); - if (argVal->getType() != arg->getType()) - return string("Argument is the wrong type: ") + arg->getName(); - size += argVal->impl->encodedSize(); - } else { - Value defaultValue(arg->getType()); - size += defaultValue.impl->encodedSize(); - } - } - } - - return string(); -} - -void BrokerProxyImpl::sendMethodRequest(ObjectId* oid, const SchemaObjectClass* cls, - const string& methodName, const Value* args, void* userContext) -{ - int methodCount = cls->getMethodCount(); - int idx; - for (idx = 0; idx < methodCount; idx++) { - const SchemaMethod* method = cls->getMethod(idx); - if (string(method->getName()) == methodName) { - Mutex::ScopedLock _lock(lock); - SequenceContext::Ptr methodContext(new MethodContext(*this, userContext, method)); - stringstream key; - char* buf(outputBuffer); - uint32_t bufLen(1024); - bool allocated(false); - - string argErrorString = encodedSizeMethodArguments(method, args, bufLen); - if (!argErrorString.empty()) { - MethodResponsePtr argError(MethodResponseImpl::factory(1, argErrorString)); - eventQueue.push_back(eventMethodResponse(userContext, argError)); - return; - } - - if (bufLen > MA_BUFFER_SIZE) { - buf = (char*) malloc(bufLen); - allocated = true; - } - - Buffer outBuffer(buf, bufLen); - uint32_t sequence(seqMgr.reserve(methodContext)); - - Protocol::encodeHeader(outBuffer, Protocol::OP_METHOD_REQUEST, sequence); - oid->impl->encode(outBuffer); - cls->getClassKey()->impl->encode(outBuffer); - outBuffer.putShortString(methodName); - - encodeMethodArguments(method, args, outBuffer); - key << "agent.1." << oid->impl->getAgentBank(); - sendBufferLH(outBuffer, QMF_EXCHANGE, key.str()); - QPID_LOG(trace, "SENT MethodRequest seq=" << sequence << " method=" << methodName << " key=" << key.str()); - - if (allocated) - free(buf); - - return; - } - } - - MethodResponsePtr error(MethodResponseImpl::factory(1, string("Unknown method: ") + methodName)); - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(eventMethodResponse(userContext, error)); -} - -void BrokerProxyImpl::addBinding(const string& exchange, const string& key) -{ - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(eventBind(exchange, queueName, key)); -} - -BrokerEventImpl::Ptr BrokerProxyImpl::eventDeclareQueue(const string& queueName) -{ - BrokerEventImpl::Ptr event(new BrokerEventImpl(BrokerEvent::DECLARE_QUEUE)); - event->name = queueName; - return event; -} - -BrokerEventImpl::Ptr BrokerProxyImpl::eventBind(const string& exchange, const string& queue, const string& key) -{ - BrokerEventImpl::Ptr event(new BrokerEventImpl(BrokerEvent::BIND)); - event->name = queue; - event->exchange = exchange; - event->bindingKey = key; - - return event; -} - -BrokerEventImpl::Ptr BrokerProxyImpl::eventSetupComplete() -{ - BrokerEventImpl::Ptr event(new BrokerEventImpl(BrokerEvent::SETUP_COMPLETE)); - return event; -} - -BrokerEventImpl::Ptr BrokerProxyImpl::eventStable() -{ - QPID_LOG(trace, "Console Link to Broker Stable"); - BrokerEventImpl::Ptr event(new BrokerEventImpl(BrokerEvent::STABLE)); - return event; -} - -BrokerEventImpl::Ptr BrokerProxyImpl::eventQueryComplete(void* context, QueryResponsePtr response) -{ - BrokerEventImpl::Ptr event(new BrokerEventImpl(BrokerEvent::QUERY_COMPLETE)); - event->context = context; - event->queryResponse = response; - return event; -} - -BrokerEventImpl::Ptr BrokerProxyImpl::eventMethodResponse(void* context, MethodResponsePtr response) -{ - BrokerEventImpl::Ptr event(new BrokerEventImpl(BrokerEvent::METHOD_RESPONSE)); - event->context = context; - event->methodResponse = response; - return event; -} - -void BrokerProxyImpl::handleBrokerResponse(Buffer& inBuffer, uint32_t seq) -{ - brokerId.decode(inBuffer); - QPID_LOG(trace, "RCVD BrokerResponse seq=" << seq << " brokerId=" << brokerId); - Mutex::ScopedLock _lock(lock); - Buffer outBuffer(outputBuffer, MA_BUFFER_SIZE); - uint32_t sequence(seqMgr.reserve()); - incOutstandingLH(); - Protocol::encodeHeader(outBuffer, Protocol::OP_PACKAGE_REQUEST, sequence); - sendBufferLH(outBuffer, QMF_EXCHANGE, BROKER_KEY); - QPID_LOG(trace, "SENT PackageRequest seq=" << sequence); -} - -void BrokerProxyImpl::handlePackageIndication(Buffer& inBuffer, uint32_t seq) -{ - string package; - - inBuffer.getShortString(package); - QPID_LOG(trace, "RCVD PackageIndication seq=" << seq << " package=" << package); - console.impl->learnPackage(package); - - Mutex::ScopedLock _lock(lock); - Buffer outBuffer(outputBuffer, MA_BUFFER_SIZE); - uint32_t sequence(seqMgr.reserve()); - incOutstandingLH(); - Protocol::encodeHeader(outBuffer, Protocol::OP_CLASS_QUERY, sequence); - outBuffer.putShortString(package); - sendBufferLH(outBuffer, QMF_EXCHANGE, BROKER_KEY); - QPID_LOG(trace, "SENT ClassQuery seq=" << sequence << " package=" << package); -} - -void BrokerProxyImpl::handleCommandComplete(Buffer& inBuffer, uint32_t seq) -{ - string text; - uint32_t code = inBuffer.getLong(); - inBuffer.getShortString(text); - QPID_LOG(trace, "RCVD CommandComplete seq=" << seq << " code=" << code << " text=" << text); -} - -void BrokerProxyImpl::handleClassIndication(Buffer& inBuffer, uint32_t seq) -{ - uint8_t kind = inBuffer.getOctet(); - auto_ptr<SchemaClassKey> classKey(SchemaClassKeyImpl::factory(inBuffer)); - - QPID_LOG(trace, "RCVD ClassIndication seq=" << seq << " kind=" << (int) kind << " key=" << classKey->impl->str()); - - if (!console.impl->haveClass(classKey.get())) { - Mutex::ScopedLock _lock(lock); - incOutstandingLH(); - Buffer outBuffer(outputBuffer, MA_BUFFER_SIZE); - uint32_t sequence(seqMgr.reserve()); - Protocol::encodeHeader(outBuffer, Protocol::OP_SCHEMA_REQUEST, sequence); - classKey->impl->encode(outBuffer); - sendBufferLH(outBuffer, QMF_EXCHANGE, BROKER_KEY); - QPID_LOG(trace, "SENT SchemaRequest seq=" << sequence <<" key=" << classKey->impl->str()); - } -} - -MethodResponsePtr BrokerProxyImpl::handleMethodResponse(Buffer& inBuffer, uint32_t seq, const SchemaMethod* schema) -{ - MethodResponsePtr response(MethodResponseImpl::factory(inBuffer, schema)); - - QPID_LOG(trace, "RCVD MethodResponse seq=" << seq << " status=" << response->getStatus() << " text=" << - response->getException()->asString()); - - return response; -} - -void BrokerProxyImpl::handleHeartbeatIndication(Buffer& inBuffer, uint32_t seq, const string& routingKey) -{ - vector<string> tokens = qpid::split(routingKey, "."); - uint32_t agentBank; - uint64_t timestamp; - - if (routingKey.empty() || tokens.size() != 4) - agentBank = 0; - else - agentBank = ::atoi(tokens[3].c_str()); - - timestamp = inBuffer.getLongLong(); - map<uint32_t, AgentProxyPtr>::const_iterator iter = agentList.find(agentBank); - if (iter != agentList.end()) { - console.impl->eventAgentHeartbeat(iter->second, timestamp); - } - QPID_LOG(trace, "RCVD HeartbeatIndication seq=" << seq << " agentBank=" << agentBank); -} - -void BrokerProxyImpl::handleEventIndication(Buffer& inBuffer, uint32_t seq) -{ - auto_ptr<SchemaClassKey> classKey(SchemaClassKeyImpl::factory(inBuffer)); - const SchemaEventClass *schema = console.impl->getEventClass(classKey.get()); - if (schema == 0) { - QPID_LOG(trace, "No Schema Found for EventIndication. seq=" << seq << " key=" << classKey->impl->str()); - return; - } - - EventPtr eptr(EventImpl::factory(schema, inBuffer)); - - console.impl->eventEventReceived(eptr); - QPID_LOG(trace, "RCVD EventIndication seq=" << seq << " key=" << classKey->impl->str()); -} - -void BrokerProxyImpl::handleSchemaResponse(Buffer& inBuffer, uint32_t seq) -{ - SchemaObjectClass* oClassPtr; - SchemaEventClass* eClassPtr; - uint8_t kind = inBuffer.getOctet(); - const SchemaClassKey* key; - if (kind == CLASS_OBJECT) { - oClassPtr = SchemaObjectClassImpl::factory(inBuffer); - console.impl->learnClass(oClassPtr); - key = oClassPtr->getClassKey(); - QPID_LOG(trace, "RCVD SchemaResponse seq=" << seq << " kind=object key=" << key->impl->str()); - - // - // If we have just learned about the org.apache.qpid.broker:agent class, send a get - // request for the current list of agents so we can have it on-hand before we declare - // this session "stable". - // - if (key->impl->getClassName() == AGENT_CLASS && key->impl->getPackageName() == BROKER_PACKAGE) { - Mutex::ScopedLock _lock(lock); - incOutstandingLH(); - Buffer outBuffer(outputBuffer, MA_BUFFER_SIZE); - uint32_t sequence(seqMgr.reserve()); - Protocol::encodeHeader(outBuffer, Protocol::OP_GET_QUERY, sequence); - FieldTable ft; - ft.setString("_class", AGENT_CLASS); - ft.setString("_package", BROKER_PACKAGE); - ft.encode(outBuffer); - sendBufferLH(outBuffer, QMF_EXCHANGE, BROKER_AGENT_KEY); - QPID_LOG(trace, "SENT GetQuery seq=" << sequence << " key=" << BROKER_AGENT_KEY); - } - } else if (kind == CLASS_EVENT) { - eClassPtr = SchemaEventClassImpl::factory(inBuffer); - console.impl->learnClass(eClassPtr); - key = eClassPtr->getClassKey(); - QPID_LOG(trace, "RCVD SchemaResponse seq=" << seq << " kind=event key=" << key->impl->str()); - } - else { - QPID_LOG(error, "BrokerProxyImpl::handleSchemaResponse received unknown class kind: " << (int) kind); - } -} - -ObjectPtr BrokerProxyImpl::handleObjectIndication(Buffer& inBuffer, uint32_t seq, bool prop, bool stat) -{ - auto_ptr<SchemaClassKey> classKey(SchemaClassKeyImpl::factory(inBuffer)); - QPID_LOG(trace, "RCVD ObjectIndication seq=" << seq << " key=" << classKey->impl->str()); - - SchemaObjectClass* schema = console.impl->getSchema(classKey.get()); - if (schema == 0) { - QPID_LOG(trace, "No Schema Found for ObjectIndication. seq=" << seq << " key=" << classKey->impl->str()); - return ObjectPtr(); - } - - ObjectPtr optr(ObjectImpl::factory(schema, this, inBuffer, prop, stat, true)); - if (prop && classKey->impl->getPackageName() == BROKER_PACKAGE && classKey->impl->getClassName() == AGENT_CLASS) { - // - // We've intercepted information about a remote agent... update the agent list accordingly - // - updateAgentList(optr); - } - return optr; -} - -void BrokerProxyImpl::updateAgentList(ObjectPtr obj) -{ - Value* value = obj->getValue("agentBank"); - Mutex::ScopedLock _lock(lock); - if (value != 0 && value->isUint()) { - uint32_t agentBank = value->asUint(); - if (obj->isDeleted()) { - map<uint32_t, AgentProxyPtr>::iterator iter = agentList.find(agentBank); - if (iter != agentList.end()) { - AgentProxyPtr agent(iter->second); - console.impl->eventAgentDeleted(agent); - agentList.erase(agentBank); - QPID_LOG(trace, "Agent at bank " << agentBank << " removed from agent list"); - - // - // Release all sequence numbers for requests in-flight to this agent. - // Since the agent is no longer connected, these requests would not - // otherwise complete. - // - agent->impl->releaseInFlight(seqMgr); - } - } else { - Value* str = obj->getValue("label"); - string label; - if (str != 0 && str->isString()) - label = str->asString(); - map<uint32_t, AgentProxyPtr>::const_iterator iter = agentList.find(agentBank); - if (iter == agentList.end()) { - AgentProxyPtr agent(AgentProxyImpl::factory(console, publicObject, agentBank, label)); - agentList[agentBank] = agent; - console.impl->eventAgentAdded(agent); - QPID_LOG(trace, "Agent '" << label << "' found at bank " << agentBank); - } - } - } -} - -void BrokerProxyImpl::incOutstandingLH() -{ - requestsOutstanding++; -} - -void BrokerProxyImpl::decOutstanding() -{ - Mutex::ScopedLock _lock(lock); - requestsOutstanding--; - if (requestsOutstanding == 0 && !topicBound) { - topicBound = true; - for (vector<pair<string, string> >::const_iterator iter = console.impl->bindingList.begin(); - iter != console.impl->bindingList.end(); iter++) { - string exchange(iter->first.empty() ? QMF_EXCHANGE : iter->first); - string key(iter->second); - eventQueue.push_back(eventBind(exchange, queueName, key)); - } - eventQueue.push_back(eventStable()); - } -} - -MethodResponseImpl::MethodResponseImpl(const MethodResponseImpl& from) : - status(from.status), schema(from.schema) -{ - if (from.exception.get()) - exception.reset(new Value(*(from.exception))); - if (from.arguments.get()) - arguments.reset(new Value(*(from.arguments))); -} - -MethodResponseImpl::MethodResponseImpl(Buffer& buf, const SchemaMethod* s) : schema(s) -{ - string text; - - status = buf.getLong(); - buf.getMediumString(text); - exception.reset(new Value(TYPE_LSTR)); - exception->setString(text.c_str()); - - if (status != 0) - return; - - arguments.reset(new Value(TYPE_MAP)); - int argCount(schema->getArgumentCount()); - for (int idx = 0; idx < argCount; idx++) { - const SchemaArgument* arg = schema->getArgument(idx); - if (arg->getDirection() == DIR_OUT || arg->getDirection() == DIR_IN_OUT) { - Value* value(ValueImpl::factory(arg->getType(), buf)); - arguments->insert(arg->getName(), value); - } - } -} - -MethodResponseImpl::MethodResponseImpl(uint32_t s, const string& text) : schema(0) -{ - status = s; - exception.reset(new Value(TYPE_LSTR)); - exception->setString(text.c_str()); -} - -MethodResponse* MethodResponseImpl::factory(Buffer& buf, const SchemaMethod* schema) -{ - MethodResponseImpl* impl(new MethodResponseImpl(buf, schema)); - return new MethodResponse(impl); -} - -MethodResponse* MethodResponseImpl::factory(uint32_t status, const std::string& text) -{ - MethodResponseImpl* impl(new MethodResponseImpl(status, text)); - return new MethodResponse(impl); -} - -bool StaticContext::handleMessage(uint8_t opcode, uint32_t sequence, const string& routingKey, Buffer& buffer) -{ - ObjectPtr object; - bool completeContext = false; - - if (opcode == Protocol::OP_BROKER_RESPONSE) { - broker.handleBrokerResponse(buffer, sequence); - completeContext = true; - } - else if (opcode == Protocol::OP_COMMAND_COMPLETE) { - broker.handleCommandComplete(buffer, sequence); - completeContext = true; - } - else if (opcode == Protocol::OP_SCHEMA_RESPONSE) { - broker.handleSchemaResponse(buffer, sequence); - completeContext = true; - } - else if (opcode == Protocol::OP_PACKAGE_INDICATION) - broker.handlePackageIndication(buffer, sequence); - else if (opcode == Protocol::OP_CLASS_INDICATION) - broker.handleClassIndication(buffer, sequence); - else if (opcode == Protocol::OP_HEARTBEAT_INDICATION) - broker.handleHeartbeatIndication(buffer, sequence, routingKey); - else if (opcode == Protocol::OP_EVENT_INDICATION) - broker.handleEventIndication(buffer, sequence); - else if (opcode == Protocol::OP_PROPERTY_INDICATION) { - object = broker.handleObjectIndication(buffer, sequence, true, false); - broker.console.impl->eventObjectUpdate(object, true, false); - } - else if (opcode == Protocol::OP_STATISTIC_INDICATION) { - object = broker.handleObjectIndication(buffer, sequence, false, true); - broker.console.impl->eventObjectUpdate(object, false, true); - } - else if (opcode == Protocol::OP_OBJECT_INDICATION) { - object = broker.handleObjectIndication(buffer, sequence, true, true); - broker.console.impl->eventObjectUpdate(object, true, true); - } - else { - QPID_LOG(trace, "StaticContext::handleMessage invalid opcode: " << opcode); - completeContext = true; - } - - return completeContext; -} - -void QueryContext::reserve() -{ - Mutex::ScopedLock _lock(lock); - requestsOutstanding++; -} - -void QueryContext::release() -{ - { - Mutex::ScopedLock _lock(lock); - if (--requestsOutstanding > 0) - return; - } - - Mutex::ScopedLock _block(broker.lock); - broker.eventQueue.push_back(broker.eventQueryComplete(userContext, queryResponse)); -} - -bool QueryContext::handleMessage(uint8_t opcode, uint32_t sequence, const string& /*routingKey*/, Buffer& buffer) -{ - bool completeContext = false; - ObjectPtr object; - - if (opcode == Protocol::OP_COMMAND_COMPLETE) { - broker.handleCommandComplete(buffer, sequence); - completeContext = true; - - // - // Visit each agent and remove the sequence from that agent's in-flight list. - // This could be made more efficient because only one agent will have this sequence - // in its list. - // - map<uint32_t, AgentProxyPtr> copy; - { - Mutex::ScopedLock _block(broker.lock); - copy = broker.agentList; - } - for (map<uint32_t, AgentProxyPtr>::iterator iter = copy.begin(); iter != copy.end(); iter++) - iter->second->impl->delSequence(sequence); - } - else if (opcode == Protocol::OP_OBJECT_INDICATION) { - object = broker.handleObjectIndication(buffer, sequence, true, true); - if (object.get() != 0) - queryResponse->impl->results.push_back(object); - } - else { - QPID_LOG(trace, "QueryContext::handleMessage invalid opcode: " << opcode); - completeContext = true; - } - - return completeContext; -} - -void MethodContext::release() -{ - Mutex::ScopedLock _block(broker.lock); - broker.eventQueue.push_back(broker.eventMethodResponse(userContext, methodResponse)); -} - -bool MethodContext::handleMessage(uint8_t opcode, uint32_t sequence, const string& /*routingKey*/, Buffer& buffer) -{ - if (opcode == Protocol::OP_METHOD_RESPONSE) - methodResponse = broker.handleMethodResponse(buffer, sequence, schema); - else - QPID_LOG(trace, "QueryContext::handleMessage invalid opcode: " << opcode); - - return true; -} - - -//================================================================== -// Wrappers -//================================================================== - -AgentProxy::AgentProxy(AgentProxyImpl* i) : impl(i) {} -AgentProxy::AgentProxy(const AgentProxy& from) : impl(new AgentProxyImpl(*(from.impl))) {} -AgentProxy::~AgentProxy() { delete impl; } -const char* AgentProxy::getLabel() const { return impl->getLabel().c_str(); } -uint32_t AgentProxy::getBrokerBank() const { return impl->getBrokerBank(); } -uint32_t AgentProxy::getAgentBank() const { return impl->getAgentBank(); } - -BrokerProxy::BrokerProxy(Console& console) : impl(new BrokerProxyImpl(*this, console)) {} -BrokerProxy::~BrokerProxy() { delete impl; } -void BrokerProxy::sessionOpened(SessionHandle& sh) { impl->sessionOpened(sh); } -void BrokerProxy::sessionClosed() { impl->sessionClosed(); } -void BrokerProxy::startProtocol() { impl->startProtocol(); } -void BrokerProxy::handleRcvMessage(Message& message) { impl->handleRcvMessage(message); } -bool BrokerProxy::getXmtMessage(Message& item) const { return impl->getXmtMessage(item); } -void BrokerProxy::popXmt() { impl->popXmt(); } -bool BrokerProxy::getEvent(BrokerEvent& event) const { return impl->getEvent(event); } -void BrokerProxy::popEvent() { impl->popEvent(); } -uint32_t BrokerProxy::agentCount() const { return impl->agentCount(); } -const AgentProxy* BrokerProxy::getAgent(uint32_t idx) const { return impl->getAgent(idx); } -void BrokerProxy::sendQuery(const Query& query, void* context, const AgentProxy* agent) { impl->sendQuery(query, context, agent); } - -MethodResponse::MethodResponse(const MethodResponse& from) : impl(new MethodResponseImpl(*(from.impl))) {} -MethodResponse::MethodResponse(MethodResponseImpl* i) : impl(i) {} -MethodResponse::~MethodResponse() {} -uint32_t MethodResponse::getStatus() const { return impl->getStatus(); } -const Value* MethodResponse::getException() const { return impl->getException(); } -const Value* MethodResponse::getArgs() const { return impl->getArgs(); } - -QueryResponse::QueryResponse(QueryResponseImpl* i) : impl(i) {} -QueryResponse::~QueryResponse() {} -uint32_t QueryResponse::getStatus() const { return impl->getStatus(); } -const Value* QueryResponse::getException() const { return impl->getException(); } -uint32_t QueryResponse::getObjectCount() const { return impl->getObjectCount(); } -const Object* QueryResponse::getObject(uint32_t idx) const { return impl->getObject(idx); } - diff --git a/cpp/src/qmf/engine/BrokerProxyImpl.h b/cpp/src/qmf/engine/BrokerProxyImpl.h deleted file mode 100644 index 0542b67dbb..0000000000 --- a/cpp/src/qmf/engine/BrokerProxyImpl.h +++ /dev/null @@ -1,241 +0,0 @@ -#ifndef _QmfEngineBrokerProxyImpl_ -#define _QmfEngineBrokerProxyImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/Console.h" -#include "qmf/engine/ObjectImpl.h" -#include "qmf/engine/EventImpl.h" -#include "qmf/engine/SchemaImpl.h" -#include "qmf/engine/ValueImpl.h" -#include "qmf/engine/QueryImpl.h" -#include "qmf/engine/SequenceManager.h" -#include "qmf/engine/MessageImpl.h" -#include "qpid/framing/Buffer.h" -#include "qpid/framing/Uuid.h" -#include "qpid/sys/Mutex.h" -#include "boost/shared_ptr.hpp" -#include "boost/noncopyable.hpp" -#include <memory> -#include <string> -#include <deque> -#include <map> -#include <set> -#include <vector> - -namespace qmf { -namespace engine { - - typedef boost::shared_ptr<MethodResponse> MethodResponsePtr; - struct MethodResponseImpl { - uint32_t status; - const SchemaMethod* schema; - std::auto_ptr<Value> exception; - std::auto_ptr<Value> arguments; - - MethodResponseImpl(const MethodResponseImpl& from); - MethodResponseImpl(qpid::framing::Buffer& buf, const SchemaMethod* schema); - MethodResponseImpl(uint32_t status, const std::string& text); - static MethodResponse* factory(qpid::framing::Buffer& buf, const SchemaMethod* schema); - static MethodResponse* factory(uint32_t status, const std::string& text); - ~MethodResponseImpl() {} - uint32_t getStatus() const { return status; } - const Value* getException() const { return exception.get(); } - const Value* getArgs() const { return arguments.get(); } - }; - - typedef boost::shared_ptr<QueryResponse> QueryResponsePtr; - struct QueryResponseImpl { - uint32_t status; - std::auto_ptr<Value> exception; - std::vector<ObjectPtr> results; - - QueryResponseImpl() : status(0) {} - static QueryResponse* factory() { - QueryResponseImpl* impl(new QueryResponseImpl()); - return new QueryResponse(impl); - } - ~QueryResponseImpl() {} - uint32_t getStatus() const { return status; } - const Value* getException() const { return exception.get(); } - uint32_t getObjectCount() const { return results.size(); } - const Object* getObject(uint32_t idx) const; - }; - - struct BrokerEventImpl { - typedef boost::shared_ptr<BrokerEventImpl> Ptr; - BrokerEvent::EventKind kind; - std::string name; - std::string exchange; - std::string bindingKey; - void* context; - QueryResponsePtr queryResponse; - MethodResponsePtr methodResponse; - - BrokerEventImpl(BrokerEvent::EventKind k) : kind(k), context(0) {} - ~BrokerEventImpl() {} - BrokerEvent copy(); - }; - - typedef boost::shared_ptr<AgentProxy> AgentProxyPtr; - struct AgentProxyImpl { - Console& console; - BrokerProxy& broker; - uint32_t agentBank; - std::string label; - std::set<uint32_t> inFlightSequences; - - AgentProxyImpl(Console& c, BrokerProxy& b, uint32_t ab, const std::string& l) : console(c), broker(b), agentBank(ab), label(l) {} - static AgentProxy* factory(Console& c, BrokerProxy& b, uint32_t ab, const std::string& l) { - AgentProxyImpl* impl(new AgentProxyImpl(c, b, ab, l)); - return new AgentProxy(impl); - } - ~AgentProxyImpl() {} - const std::string& getLabel() const { return label; } - uint32_t getBrokerBank() const { return 1; } - uint32_t getAgentBank() const { return agentBank; } - void addSequence(uint32_t seq) { inFlightSequences.insert(seq); } - void delSequence(uint32_t seq) { inFlightSequences.erase(seq); } - void releaseInFlight(SequenceManager& seqMgr) { - for (std::set<uint32_t>::iterator iter = inFlightSequences.begin(); iter != inFlightSequences.end(); iter++) - seqMgr.release(*iter); - inFlightSequences.clear(); - } - }; - - class BrokerProxyImpl : public boost::noncopyable { - public: - BrokerProxyImpl(BrokerProxy& pub, Console& _console); - ~BrokerProxyImpl() {} - - void sessionOpened(SessionHandle& sh); - void sessionClosed(); - void startProtocol(); - - void sendBufferLH(qpid::framing::Buffer& buf, const std::string& destination, const std::string& routingKey); - void handleRcvMessage(Message& message); - bool getXmtMessage(Message& item) const; - void popXmt(); - - bool getEvent(BrokerEvent& event) const; - void popEvent(); - - uint32_t agentCount() const; - const AgentProxy* getAgent(uint32_t idx) const; - void sendQuery(const Query& query, void* context, const AgentProxy* agent); - bool sendGetRequestLH(SequenceContext::Ptr queryContext, const Query& query, const AgentProxy* agent); - std::string encodeMethodArguments(const SchemaMethod* schema, const Value* args, qpid::framing::Buffer& buffer); - std::string encodedSizeMethodArguments(const SchemaMethod* schema, const Value* args, uint32_t& size); - void sendMethodRequest(ObjectId* oid, const SchemaObjectClass* cls, const std::string& method, const Value* args, void* context); - - void addBinding(const std::string& exchange, const std::string& key); - void staticRelease() { decOutstanding(); } - - private: - friend struct StaticContext; - friend struct QueryContext; - friend struct MethodContext; - BrokerProxy& publicObject; - mutable qpid::sys::Mutex lock; - Console& console; - std::string queueName; - qpid::framing::Uuid brokerId; - SequenceManager seqMgr; - uint32_t requestsOutstanding; - bool topicBound; - std::map<uint32_t, AgentProxyPtr> agentList; - std::deque<MessageImpl::Ptr> xmtQueue; - std::deque<BrokerEventImpl::Ptr> eventQueue; - -# define MA_BUFFER_SIZE 65536 - char outputBuffer[MA_BUFFER_SIZE]; - - BrokerEventImpl::Ptr eventDeclareQueue(const std::string& queueName); - BrokerEventImpl::Ptr eventBind(const std::string& exchange, const std::string& queue, const std::string& key); - BrokerEventImpl::Ptr eventSetupComplete(); - BrokerEventImpl::Ptr eventStable(); - BrokerEventImpl::Ptr eventQueryComplete(void* context, QueryResponsePtr response); - BrokerEventImpl::Ptr eventMethodResponse(void* context, MethodResponsePtr response); - - void handleBrokerResponse(qpid::framing::Buffer& inBuffer, uint32_t seq); - void handlePackageIndication(qpid::framing::Buffer& inBuffer, uint32_t seq); - void handleCommandComplete(qpid::framing::Buffer& inBuffer, uint32_t seq); - void handleClassIndication(qpid::framing::Buffer& inBuffer, uint32_t seq); - MethodResponsePtr handleMethodResponse(qpid::framing::Buffer& inBuffer, uint32_t seq, const SchemaMethod* schema); - void handleHeartbeatIndication(qpid::framing::Buffer& inBuffer, uint32_t seq, const std::string& routingKey); - void handleEventIndication(qpid::framing::Buffer& inBuffer, uint32_t seq); - void handleSchemaResponse(qpid::framing::Buffer& inBuffer, uint32_t seq); - ObjectPtr handleObjectIndication(qpid::framing::Buffer& inBuffer, uint32_t seq, bool prop, bool stat); - void updateAgentList(ObjectPtr obj); - void incOutstandingLH(); - void decOutstanding(); - }; - - // - // StaticContext is used to handle: - // - // 1) Responses to console-level requests (for schema info, etc.) - // 2) Unsolicited messages from agents (events, published updates, etc.) - // - struct StaticContext : public SequenceContext { - StaticContext(BrokerProxyImpl& b) : broker(b) {} - virtual ~StaticContext() {} - void reserve() {} - void release() { broker.staticRelease(); } - bool handleMessage(uint8_t opcode, uint32_t sequence, const std::string& routingKey, qpid::framing::Buffer& buffer); - BrokerProxyImpl& broker; - }; - - // - // QueryContext is used to track and handle responses associated with a single Get Query - // - struct QueryContext : public SequenceContext { - QueryContext(BrokerProxyImpl& b, void* u) : - broker(b), userContext(u), requestsOutstanding(0), queryResponse(QueryResponseImpl::factory()) {} - virtual ~QueryContext() {} - void reserve(); - void release(); - bool handleMessage(uint8_t opcode, uint32_t sequence, const std::string& routingKey, qpid::framing::Buffer& buffer); - - mutable qpid::sys::Mutex lock; - BrokerProxyImpl& broker; - void* userContext; - uint32_t requestsOutstanding; - QueryResponsePtr queryResponse; - }; - - struct MethodContext : public SequenceContext { - MethodContext(BrokerProxyImpl& b, void* u, const SchemaMethod* s) : broker(b), userContext(u), schema(s) {} - virtual ~MethodContext() {} - void reserve() {} - void release(); - bool handleMessage(uint8_t opcode, uint32_t sequence, const std::string& routingKey, qpid::framing::Buffer& buffer); - - BrokerProxyImpl& broker; - void* userContext; - const SchemaMethod* schema; - MethodResponsePtr methodResponse; - }; - -} -} - -#endif - diff --git a/cpp/src/qmf/engine/ConnectionSettingsImpl.cpp b/cpp/src/qmf/engine/ConnectionSettingsImpl.cpp deleted file mode 100644 index 22a65f28ca..0000000000 --- a/cpp/src/qmf/engine/ConnectionSettingsImpl.cpp +++ /dev/null @@ -1,278 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/ConnectionSettingsImpl.h" -#include "qmf/engine/Typecode.h" - -using namespace std; -using namespace qmf::engine; -using namespace qpid; - -const string attrProtocol("protocol"); -const string attrHost("host"); -const string attrPort("port"); -const string attrVirtualhost("virtualhost"); -const string attrUsername("username"); -const string attrPassword("password"); -const string attrMechanism("mechanism"); -const string attrLocale("locale"); -const string attrHeartbeat("heartbeat"); -const string attrMaxChannels("maxChannels"); -const string attrMaxFrameSize("maxFrameSize"); -const string attrBounds("bounds"); -const string attrTcpNoDelay("tcpNoDelay"); -const string attrService("service"); -const string attrMinSsf("minSsf"); -const string attrMaxSsf("maxSsf"); -const string attrRetryDelayMin("retryDelayMin"); -const string attrRetryDelayMax("retryDelayMax"); -const string attrRetryDelayFactor("retryDelayFactor"); -const string attrSendUserId("sendUserId"); - -ConnectionSettingsImpl::ConnectionSettingsImpl() : - retryDelayMin(1), retryDelayMax(64), retryDelayFactor(2), sendUserId(true) -{ -} - -ConnectionSettingsImpl::ConnectionSettingsImpl(const string& /*url*/) : - retryDelayMin(1), retryDelayMax(64), retryDelayFactor(2), sendUserId(true) -{ - // TODO: Parse the URL -} - -bool ConnectionSettingsImpl::setAttr(const string& key, const Value& value) -{ - if (key == attrProtocol) clientSettings.protocol = value.asString(); - else if (key == attrHost) clientSettings.host = value.asString(); - else if (key == attrPort) clientSettings.port = value.asUint(); - else if (key == attrVirtualhost) clientSettings.virtualhost = value.asString(); - else if (key == attrUsername) clientSettings.username = value.asString(); - else if (key == attrPassword) clientSettings.password = value.asString(); - else if (key == attrMechanism) clientSettings.mechanism = value.asString(); - else if (key == attrLocale) clientSettings.locale = value.asString(); - else if (key == attrHeartbeat) clientSettings.heartbeat = value.asUint(); - else if (key == attrMaxChannels) clientSettings.maxChannels = value.asUint(); - else if (key == attrMaxFrameSize) clientSettings.maxFrameSize = value.asUint(); - else if (key == attrBounds) clientSettings.bounds = value.asUint(); - else if (key == attrTcpNoDelay) clientSettings.tcpNoDelay = value.asBool(); - else if (key == attrService) clientSettings.service = value.asString(); - else if (key == attrMinSsf) clientSettings.minSsf = value.asUint(); - else if (key == attrMaxSsf) clientSettings.maxSsf = value.asUint(); - - else if (key == attrRetryDelayMin) retryDelayMin = value.asUint(); - else if (key == attrRetryDelayMax) retryDelayMax = value.asUint(); - else if (key == attrRetryDelayFactor) retryDelayFactor = value.asUint(); - else if (key == attrSendUserId) sendUserId = value.asBool(); - else - return false; - return true; -} - -Value ConnectionSettingsImpl::getAttr(const string& key) const -{ - Value strval(TYPE_LSTR); - Value intval(TYPE_UINT32); - Value boolval(TYPE_BOOL); - - if (key == attrProtocol) { - strval.setString(clientSettings.protocol.c_str()); - return strval; - } - - if (key == attrHost) { - strval.setString(clientSettings.host.c_str()); - return strval; - } - - if (key == attrPort) { - intval.setUint(clientSettings.port); - return intval; - } - - if (key == attrVirtualhost) { - strval.setString(clientSettings.virtualhost.c_str()); - return strval; - } - - if (key == attrUsername) { - strval.setString(clientSettings.username.c_str()); - return strval; - } - - if (key == attrPassword) { - strval.setString(clientSettings.password.c_str()); - return strval; - } - - if (key == attrMechanism) { - strval.setString(clientSettings.mechanism.c_str()); - return strval; - } - - if (key == attrLocale) { - strval.setString(clientSettings.locale.c_str()); - return strval; - } - - if (key == attrHeartbeat) { - intval.setUint(clientSettings.heartbeat); - return intval; - } - - if (key == attrMaxChannels) { - intval.setUint(clientSettings.maxChannels); - return intval; - } - - if (key == attrMaxFrameSize) { - intval.setUint(clientSettings.maxFrameSize); - return intval; - } - - if (key == attrBounds) { - intval.setUint(clientSettings.bounds); - return intval; - } - - if (key == attrTcpNoDelay) { - boolval.setBool(clientSettings.tcpNoDelay); - return boolval; - } - - if (key == attrService) { - strval.setString(clientSettings.service.c_str()); - return strval; - } - - if (key == attrMinSsf) { - intval.setUint(clientSettings.minSsf); - return intval; - } - - if (key == attrMaxSsf) { - intval.setUint(clientSettings.maxSsf); - return intval; - } - - if (key == attrRetryDelayMin) { - intval.setUint(retryDelayMin); - return intval; - } - - if (key == attrRetryDelayMax) { - intval.setUint(retryDelayMax); - return intval; - } - - if (key == attrRetryDelayFactor) { - intval.setUint(retryDelayFactor); - return intval; - } - - if (key == attrSendUserId) { - boolval.setBool(sendUserId); - return boolval; - } - - return strval; -} - -const string& ConnectionSettingsImpl::getAttrString() const -{ - // TODO: build and return attribute string - return attrString; -} - -void ConnectionSettingsImpl::transportTcp(uint16_t port) -{ - clientSettings.protocol = "tcp"; - clientSettings.port = port; -} - -void ConnectionSettingsImpl::transportSsl(uint16_t port) -{ - clientSettings.protocol = "ssl"; - clientSettings.port = port; -} - -void ConnectionSettingsImpl::transportRdma(uint16_t port) -{ - clientSettings.protocol = "rdma"; - clientSettings.port = port; -} - -void ConnectionSettingsImpl::authAnonymous(const string& username) -{ - clientSettings.mechanism = "ANONYMOUS"; - clientSettings.username = username; -} - -void ConnectionSettingsImpl::authPlain(const string& username, const string& password) -{ - clientSettings.mechanism = "PLAIN"; - clientSettings.username = username; - clientSettings.password = password; -} - -void ConnectionSettingsImpl::authGssapi(const string& serviceName, uint32_t minSsf, uint32_t maxSsf) -{ - clientSettings.mechanism = "GSSAPI"; - clientSettings.service = serviceName; - clientSettings.minSsf = minSsf; - clientSettings.maxSsf = maxSsf; -} - -void ConnectionSettingsImpl::setRetry(int delayMin, int delayMax, int delayFactor) -{ - retryDelayMin = delayMin; - retryDelayMax = delayMax; - retryDelayFactor = delayFactor; -} - -const client::ConnectionSettings& ConnectionSettingsImpl::getClientSettings() const -{ - return clientSettings; -} - -void ConnectionSettingsImpl::getRetrySettings(int* min, int* max, int* factor) const -{ - *min = retryDelayMin; - *max = retryDelayMax; - *factor = retryDelayFactor; -} - -//================================================================== -// Wrappers -//================================================================== - -ConnectionSettings::ConnectionSettings(const ConnectionSettings& from) { impl = new ConnectionSettingsImpl(*from.impl); } -ConnectionSettings::ConnectionSettings() { impl = new ConnectionSettingsImpl(); } -ConnectionSettings::ConnectionSettings(const char* url) { impl = new ConnectionSettingsImpl(url); } -ConnectionSettings::~ConnectionSettings() { delete impl; } -bool ConnectionSettings::setAttr(const char* key, const Value& value) { return impl->setAttr(key, value); } -Value ConnectionSettings::getAttr(const char* key) const { return impl->getAttr(key); } -const char* ConnectionSettings::getAttrString() const { return impl->getAttrString().c_str(); } -void ConnectionSettings::transportTcp(uint16_t port) { impl->transportTcp(port); } -void ConnectionSettings::transportSsl(uint16_t port) { impl->transportSsl(port); } -void ConnectionSettings::transportRdma(uint16_t port) { impl->transportRdma(port); } -void ConnectionSettings::authAnonymous(const char* username) { impl->authAnonymous(username); } -void ConnectionSettings::authPlain(const char* username, const char* password) { impl->authPlain(username, password); } -void ConnectionSettings::authGssapi(const char* serviceName, uint32_t minSsf, uint32_t maxSsf) { impl->authGssapi(serviceName, minSsf, maxSsf); } -void ConnectionSettings::setRetry(int delayMin, int delayMax, int delayFactor) { impl->setRetry(delayMin, delayMax, delayFactor); } - diff --git a/cpp/src/qmf/engine/ConnectionSettingsImpl.h b/cpp/src/qmf/engine/ConnectionSettingsImpl.h deleted file mode 100644 index 98bf87868b..0000000000 --- a/cpp/src/qmf/engine/ConnectionSettingsImpl.h +++ /dev/null @@ -1,63 +0,0 @@ -#ifndef _QmfEngineConnectionSettingsImpl_ -#define _QmfEngineConnectionSettingsImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/ConnectionSettings.h" -#include "qmf/engine/Value.h" -#include "qpid/client/ConnectionSettings.h" -#include <string> -#include <map> - -namespace qmf { -namespace engine { - - class ConnectionSettingsImpl { - qpid::client::ConnectionSettings clientSettings; - mutable std::string attrString; - int retryDelayMin; - int retryDelayMax; - int retryDelayFactor; - bool sendUserId; - - public: - ConnectionSettingsImpl(); - ConnectionSettingsImpl(const std::string& url); - ~ConnectionSettingsImpl() {} - bool setAttr(const std::string& key, const Value& value); - Value getAttr(const std::string& key) const; - const std::string& getAttrString() const; - void transportTcp(uint16_t port); - void transportSsl(uint16_t port); - void transportRdma(uint16_t port); - void authAnonymous(const std::string& username); - void authPlain(const std::string& username, const std::string& password); - void authGssapi(const std::string& serviceName, uint32_t minSsf, uint32_t maxSsf); - void setRetry(int delayMin, int delayMax, int delayFactor); - - const qpid::client::ConnectionSettings& getClientSettings() const; - void getRetrySettings(int* delayMin, int* delayMax, int* delayFactor) const; - bool getSendUserId() const { return sendUserId; } - }; - -} -} - -#endif diff --git a/cpp/src/qmf/engine/ConsoleImpl.cpp b/cpp/src/qmf/engine/ConsoleImpl.cpp deleted file mode 100644 index 4a5da31bdc..0000000000 --- a/cpp/src/qmf/engine/ConsoleImpl.cpp +++ /dev/null @@ -1,458 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/ConsoleImpl.h" -#include "qmf/engine/MessageImpl.h" -#include "qmf/engine/SchemaImpl.h" -#include "qmf/engine/Typecode.h" -#include "qmf/engine/ObjectImpl.h" -#include "qmf/engine/ObjectIdImpl.h" -#include "qmf/engine/QueryImpl.h" -#include "qmf/engine/ValueImpl.h" -#include "qmf/engine/Protocol.h" -#include "qmf/engine/SequenceManager.h" -#include "qmf/engine/BrokerProxyImpl.h" -#include <qpid/framing/Buffer.h> -#include <qpid/framing/Uuid.h> -#include <qpid/framing/FieldTable.h> -#include <qpid/framing/FieldValue.h> -#include <qpid/log/Statement.h> -#include <qpid/sys/Time.h> -#include <qpid/sys/SystemInfo.h> -#include <string.h> -#include <iostream> -#include <fstream> - -using namespace std; -using namespace qmf::engine; -using namespace qpid::framing; -using namespace qpid::sys; - -namespace { - const char* QMF_EXCHANGE = "qpid.management"; -} - -#define STRING_REF(s) {if (!s.empty()) item.s = const_cast<char*>(s.c_str());} - -ConsoleEvent ConsoleEventImpl::copy() -{ - ConsoleEvent item; - - ::memset(&item, 0, sizeof(ConsoleEvent)); - item.kind = kind; - item.agent = agent.get(); - item.classKey = classKey; - item.object = object.get(); - item.context = context; - item.event = event.get(); - item.timestamp = timestamp; - item.hasProps = hasProps; - item.hasStats = hasStats; - - STRING_REF(name); - - return item; -} - -ConsoleImpl::ConsoleImpl(const ConsoleSettings& s) : settings(s) -{ - bindingList.push_back(pair<string, string>(string(), "schema.#")); - if (settings.rcvObjects && settings.rcvEvents && settings.rcvHeartbeats && !settings.userBindings) { - bindingList.push_back(pair<string, string>(string(), "console.#")); - } else { - if (settings.rcvObjects && !settings.userBindings) - bindingList.push_back(pair<string, string>(string(), "console.obj.#")); - else - bindingList.push_back(pair<string, string>(string(), "console.obj.*.*.org.apache.qpid.broker.agent")); - if (settings.rcvEvents) - bindingList.push_back(pair<string, string>(string(), "console.event.#")); - if (settings.rcvHeartbeats) - bindingList.push_back(pair<string, string>(string(), "console.heartbeat.#")); - } -} - -ConsoleImpl::~ConsoleImpl() -{ - // This function intentionally left blank. -} - -bool ConsoleImpl::getEvent(ConsoleEvent& event) const -{ - Mutex::ScopedLock _lock(lock); - if (eventQueue.empty()) - return false; - event = eventQueue.front()->copy(); - return true; -} - -void ConsoleImpl::popEvent() -{ - Mutex::ScopedLock _lock(lock); - if (!eventQueue.empty()) - eventQueue.pop_front(); -} - -void ConsoleImpl::addConnection(BrokerProxy& broker, void* /*context*/) -{ - Mutex::ScopedLock _lock(lock); - brokerList.push_back(broker.impl); -} - -void ConsoleImpl::delConnection(BrokerProxy& broker) -{ - Mutex::ScopedLock _lock(lock); - for (vector<BrokerProxyImpl*>::iterator iter = brokerList.begin(); - iter != brokerList.end(); iter++) - if (*iter == broker.impl) { - brokerList.erase(iter); - break; - } -} - -uint32_t ConsoleImpl::packageCount() const -{ - Mutex::ScopedLock _lock(lock); - return packages.size(); -} - -const string& ConsoleImpl::getPackageName(uint32_t idx) const -{ - const static string empty; - - Mutex::ScopedLock _lock(lock); - if (idx >= packages.size()) - return empty; - - PackageList::const_iterator iter = packages.begin(); - for (uint32_t i = 0; i < idx; i++) iter++; - return iter->first; -} - -uint32_t ConsoleImpl::classCount(const char* packageName) const -{ - Mutex::ScopedLock _lock(lock); - PackageList::const_iterator pIter = packages.find(packageName); - if (pIter == packages.end()) - return 0; - - const ObjectClassList& oList = pIter->second.first; - const EventClassList& eList = pIter->second.second; - - return oList.size() + eList.size(); -} - -const SchemaClassKey* ConsoleImpl::getClass(const char* packageName, uint32_t idx) const -{ - Mutex::ScopedLock _lock(lock); - PackageList::const_iterator pIter = packages.find(packageName); - if (pIter == packages.end()) - return 0; - - const ObjectClassList& oList = pIter->second.first; - const EventClassList& eList = pIter->second.second; - uint32_t count = 0; - - for (ObjectClassList::const_iterator oIter = oList.begin(); - oIter != oList.end(); oIter++) { - if (count == idx) - return oIter->second->getClassKey(); - count++; - } - - for (EventClassList::const_iterator eIter = eList.begin(); - eIter != eList.end(); eIter++) { - if (count == idx) - return eIter->second->getClassKey(); - count++; - } - - return 0; -} - -ClassKind ConsoleImpl::getClassKind(const SchemaClassKey* key) const -{ - Mutex::ScopedLock _lock(lock); - PackageList::const_iterator pIter = packages.find(key->getPackageName()); - if (pIter == packages.end()) - return CLASS_OBJECT; - - const EventClassList& eList = pIter->second.second; - if (eList.find(key) != eList.end()) - return CLASS_EVENT; - return CLASS_OBJECT; -} - -const SchemaObjectClass* ConsoleImpl::getObjectClass(const SchemaClassKey* key) const -{ - Mutex::ScopedLock _lock(lock); - PackageList::const_iterator pIter = packages.find(key->getPackageName()); - if (pIter == packages.end()) - return 0; - - const ObjectClassList& oList = pIter->second.first; - ObjectClassList::const_iterator iter = oList.find(key); - if (iter == oList.end()) - return 0; - return iter->second; -} - -const SchemaEventClass* ConsoleImpl::getEventClass(const SchemaClassKey* key) const -{ - Mutex::ScopedLock _lock(lock); - PackageList::const_iterator pIter = packages.find(key->getPackageName()); - if (pIter == packages.end()) - return 0; - - const EventClassList& eList = pIter->second.second; - EventClassList::const_iterator iter = eList.find(key); - if (iter == eList.end()) - return 0; - return iter->second; -} - -void ConsoleImpl::bindPackage(const char* packageName) -{ - stringstream key; - key << "console.obj.*.*." << packageName << ".#"; - Mutex::ScopedLock _lock(lock); - bindingList.push_back(pair<string, string>(string(), key.str())); - for (vector<BrokerProxyImpl*>::iterator iter = brokerList.begin(); - iter != brokerList.end(); iter++) - (*iter)->addBinding(QMF_EXCHANGE, key.str()); -} - -void ConsoleImpl::bindClass(const SchemaClassKey* classKey) -{ - stringstream key; - key << "console.obj.*.*." << classKey->getPackageName() << "." << classKey->getClassName() << ".#"; - Mutex::ScopedLock _lock(lock); - bindingList.push_back(pair<string, string>(string(), key.str())); - for (vector<BrokerProxyImpl*>::iterator iter = brokerList.begin(); - iter != brokerList.end(); iter++) - (*iter)->addBinding(QMF_EXCHANGE, key.str()); -} - -void ConsoleImpl::bindClass(const char* packageName, const char* className) -{ - stringstream key; - key << "console.obj.*.*." << packageName << "." << className << ".#"; - Mutex::ScopedLock _lock(lock); - bindingList.push_back(pair<string, string>(string(), key.str())); - for (vector<BrokerProxyImpl*>::iterator iter = brokerList.begin(); - iter != brokerList.end(); iter++) - (*iter)->addBinding(QMF_EXCHANGE, key.str()); -} - - -void ConsoleImpl::bindEvent(const SchemaClassKey* classKey) -{ - bindEvent(classKey->getPackageName(), classKey->getClassName()); -} - -void ConsoleImpl::bindEvent(const char* packageName, const char* eventName) -{ - if (!settings.userBindings) throw qpid::Exception("Console not configured for userBindings."); - if (settings.rcvEvents) throw qpid::Exception("Console already configured to receive all events."); - - stringstream key; - key << "console.event.*.*." << packageName; - if (eventName && *eventName) { - key << "." << eventName << ".#"; - } else { - key << ".#"; - } - - Mutex::ScopedLock _lock(lock); - bindingList.push_back(pair<string, string>(string(), key.str())); - for (vector<BrokerProxyImpl*>::iterator iter = brokerList.begin(); - iter != brokerList.end(); iter++) - (*iter)->addBinding(QMF_EXCHANGE, key.str()); -} - -/* -void ConsoleImpl::startSync(const Query& query, void* context, SyncQuery& sync) -{ -} - -void ConsoleImpl::touchSync(SyncQuery& sync) -{ -} - -void ConsoleImpl::endSync(SyncQuery& sync) -{ -} -*/ - -void ConsoleImpl::learnPackage(const string& packageName) -{ - Mutex::ScopedLock _lock(lock); - if (packages.find(packageName) == packages.end()) { - packages.insert(pair<string, pair<ObjectClassList, EventClassList> > - (packageName, pair<ObjectClassList, EventClassList>(ObjectClassList(), EventClassList()))); - eventNewPackage(packageName); - } -} - -void ConsoleImpl::learnClass(SchemaObjectClass* cls) -{ - Mutex::ScopedLock _lock(lock); - const SchemaClassKey* key = cls->getClassKey(); - PackageList::iterator pIter = packages.find(key->getPackageName()); - if (pIter == packages.end()) - return; - - ObjectClassList& list = pIter->second.first; - if (list.find(key) == list.end()) { - list[key] = cls; - eventNewClass(key); - } -} - -void ConsoleImpl::learnClass(SchemaEventClass* cls) -{ - Mutex::ScopedLock _lock(lock); - const SchemaClassKey* key = cls->getClassKey(); - PackageList::iterator pIter = packages.find(key->getPackageName()); - if (pIter == packages.end()) - return; - - EventClassList& list = pIter->second.second; - if (list.find(key) == list.end()) { - list[key] = cls; - eventNewClass(key); - } -} - -bool ConsoleImpl::haveClass(const SchemaClassKey* key) const -{ - Mutex::ScopedLock _lock(lock); - PackageList::const_iterator pIter = packages.find(key->getPackageName()); - if (pIter == packages.end()) - return false; - - const ObjectClassList& oList = pIter->second.first; - const EventClassList& eList = pIter->second.second; - - return oList.find(key) != oList.end() || eList.find(key) != eList.end(); -} - -SchemaObjectClass* ConsoleImpl::getSchema(const SchemaClassKey* key) const -{ - Mutex::ScopedLock _lock(lock); - PackageList::const_iterator pIter = packages.find(key->getPackageName()); - if (pIter == packages.end()) - return 0; - - const ObjectClassList& oList = pIter->second.first; - ObjectClassList::const_iterator iter = oList.find(key); - if (iter == oList.end()) - return 0; - - return iter->second; -} - -void ConsoleImpl::eventAgentAdded(boost::shared_ptr<AgentProxy> agent) -{ - ConsoleEventImpl::Ptr event(new ConsoleEventImpl(ConsoleEvent::AGENT_ADDED)); - event->agent = agent; - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(event); -} - -void ConsoleImpl::eventAgentDeleted(boost::shared_ptr<AgentProxy> agent) -{ - ConsoleEventImpl::Ptr event(new ConsoleEventImpl(ConsoleEvent::AGENT_DELETED)); - event->agent = agent; - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(event); -} - -void ConsoleImpl::eventNewPackage(const string& packageName) -{ - ConsoleEventImpl::Ptr event(new ConsoleEventImpl(ConsoleEvent::NEW_PACKAGE)); - event->name = packageName; - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(event); -} - -void ConsoleImpl::eventNewClass(const SchemaClassKey* key) -{ - ConsoleEventImpl::Ptr event(new ConsoleEventImpl(ConsoleEvent::NEW_CLASS)); - event->classKey = key; - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(event); -} - -void ConsoleImpl::eventObjectUpdate(ObjectPtr object, bool prop, bool stat) -{ - ConsoleEventImpl::Ptr event(new ConsoleEventImpl(ConsoleEvent::OBJECT_UPDATE)); - event->object = object; - event->hasProps = prop; - event->hasStats = stat; - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(event); -} - -void ConsoleImpl::eventAgentHeartbeat(boost::shared_ptr<AgentProxy> agent, uint64_t timestamp) -{ - ConsoleEventImpl::Ptr event(new ConsoleEventImpl(ConsoleEvent::AGENT_HEARTBEAT)); - event->agent = agent; - event->timestamp = timestamp; - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(event); -} - - -void ConsoleImpl::eventEventReceived(EventPtr event) -{ - ConsoleEventImpl::Ptr console_event(new ConsoleEventImpl(ConsoleEvent::EVENT_RECEIVED)); - console_event->event = event; - Mutex::ScopedLock _lock(lock); - eventQueue.push_back(console_event); -} - -//================================================================== -// Wrappers -//================================================================== - -Console::Console(const ConsoleSettings& settings) : impl(new ConsoleImpl(settings)) {} -Console::~Console() { delete impl; } -bool Console::getEvent(ConsoleEvent& event) const { return impl->getEvent(event); } -void Console::popEvent() { impl->popEvent(); } -void Console::addConnection(BrokerProxy& broker, void* context) { impl->addConnection(broker, context); } -void Console::delConnection(BrokerProxy& broker) { impl->delConnection(broker); } -uint32_t Console::packageCount() const { return impl->packageCount(); } -const char* Console::getPackageName(uint32_t idx) const { return impl->getPackageName(idx).c_str(); } -uint32_t Console::classCount(const char* packageName) const { return impl->classCount(packageName); } -const SchemaClassKey* Console::getClass(const char* packageName, uint32_t idx) const { return impl->getClass(packageName, idx); } -ClassKind Console::getClassKind(const SchemaClassKey* key) const { return impl->getClassKind(key); } -const SchemaObjectClass* Console::getObjectClass(const SchemaClassKey* key) const { return impl->getObjectClass(key); } -const SchemaEventClass* Console::getEventClass(const SchemaClassKey* key) const { return impl->getEventClass(key); } -void Console::bindPackage(const char* packageName) { impl->bindPackage(packageName); } -void Console::bindClass(const SchemaClassKey* key) { impl->bindClass(key); } -void Console::bindClass(const char* packageName, const char* className) { impl->bindClass(packageName, className); } - -void Console::bindEvent(const SchemaClassKey *key) { impl->bindEvent(key); } -void Console::bindEvent(const char* packageName, const char* eventName) { impl->bindEvent(packageName, eventName); } - -//void Console::startSync(const Query& query, void* context, SyncQuery& sync) { impl->startSync(query, context, sync); } -//void Console::touchSync(SyncQuery& sync) { impl->touchSync(sync); } -//void Console::endSync(SyncQuery& sync) { impl->endSync(sync); } - - diff --git a/cpp/src/qmf/engine/ConsoleImpl.h b/cpp/src/qmf/engine/ConsoleImpl.h deleted file mode 100644 index 0c27fdabcd..0000000000 --- a/cpp/src/qmf/engine/ConsoleImpl.h +++ /dev/null @@ -1,148 +0,0 @@ -#ifndef _QmfEngineConsoleEngineImpl_ -#define _QmfEngineConsoleEngineImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/Console.h" -#include "qmf/engine/MessageImpl.h" -#include "qmf/engine/SchemaImpl.h" -#include "qmf/engine/Typecode.h" -#include "qmf/engine/ObjectImpl.h" -#include "qmf/engine/ObjectIdImpl.h" -#include "qmf/engine/QueryImpl.h" -#include "qmf/engine/ValueImpl.h" -#include "qmf/engine/Protocol.h" -#include "qmf/engine/SequenceManager.h" -#include "qmf/engine/BrokerProxyImpl.h" -#include <qpid/framing/Buffer.h> -#include <qpid/framing/Uuid.h> -#include <qpid/framing/FieldTable.h> -#include <qpid/framing/FieldValue.h> -#include <qpid/sys/Mutex.h> -#include <qpid/sys/Time.h> -#include <qpid/sys/SystemInfo.h> -#include <string.h> -#include <string> -#include <deque> -#include <map> -#include <vector> -#include <iostream> -#include <fstream> -#include <boost/shared_ptr.hpp> -#include <boost/noncopyable.hpp> - -namespace qmf { -namespace engine { - - struct ConsoleEventImpl { - typedef boost::shared_ptr<ConsoleEventImpl> Ptr; - ConsoleEvent::EventKind kind; - boost::shared_ptr<AgentProxy> agent; - std::string name; - const SchemaClassKey* classKey; - boost::shared_ptr<Object> object; - void* context; - boost::shared_ptr<Event> event; - uint64_t timestamp; - bool hasProps; - bool hasStats; - - ConsoleEventImpl(ConsoleEvent::EventKind k) : - kind(k), classKey(0), context(0), timestamp(0) {} - ~ConsoleEventImpl() {} - ConsoleEvent copy(); - }; - - class ConsoleImpl : public boost::noncopyable { - public: - ConsoleImpl(const ConsoleSettings& settings = ConsoleSettings()); - ~ConsoleImpl(); - - bool getEvent(ConsoleEvent& event) const; - void popEvent(); - - void addConnection(BrokerProxy& broker, void* context); - void delConnection(BrokerProxy& broker); - - uint32_t packageCount() const; - const std::string& getPackageName(uint32_t idx) const; - - uint32_t classCount(const char* packageName) const; - const SchemaClassKey* getClass(const char* packageName, uint32_t idx) const; - - ClassKind getClassKind(const SchemaClassKey* key) const; - const SchemaObjectClass* getObjectClass(const SchemaClassKey* key) const; - const SchemaEventClass* getEventClass(const SchemaClassKey* key) const; - - void bindPackage(const char* packageName); - void bindClass(const SchemaClassKey* key); - void bindClass(const char* packageName, const char* className); - void bindEvent(const SchemaClassKey* key); - void bindEvent(const char* packageName, const char* eventName); - - /* - void startSync(const Query& query, void* context, SyncQuery& sync); - void touchSync(SyncQuery& sync); - void endSync(SyncQuery& sync); - */ - - private: - friend class BrokerProxyImpl; - friend struct StaticContext; - const ConsoleSettings& settings; - mutable qpid::sys::Mutex lock; - std::deque<ConsoleEventImpl::Ptr> eventQueue; - std::vector<BrokerProxyImpl*> brokerList; - std::vector<std::pair<std::string, std::string> > bindingList; // exchange/key (empty exchange => QMF_EXCHANGE) - - // Declare a compare class for the class maps that compares the dereferenced - // class key pointers. The default behavior would be to compare the pointer - // addresses themselves. - struct KeyCompare { - bool operator()(const SchemaClassKey* left, const SchemaClassKey* right) const { - return *left < *right; - } - }; - - typedef std::map<const SchemaClassKey*, SchemaObjectClass*, KeyCompare> ObjectClassList; - typedef std::map<const SchemaClassKey*, SchemaEventClass*, KeyCompare> EventClassList; - typedef std::map<std::string, std::pair<ObjectClassList, EventClassList> > PackageList; - - PackageList packages; - - void learnPackage(const std::string& packageName); - void learnClass(SchemaObjectClass* cls); - void learnClass(SchemaEventClass* cls); - bool haveClass(const SchemaClassKey* key) const; - SchemaObjectClass* getSchema(const SchemaClassKey* key) const; - - void eventAgentAdded(boost::shared_ptr<AgentProxy> agent); - void eventAgentDeleted(boost::shared_ptr<AgentProxy> agent); - void eventNewPackage(const std::string& packageName); - void eventNewClass(const SchemaClassKey* key); - void eventObjectUpdate(ObjectPtr object, bool prop, bool stat); - void eventAgentHeartbeat(boost::shared_ptr<AgentProxy> agent, uint64_t timestamp); - void eventEventReceived(boost::shared_ptr<Event> event); - }; -} -} - -#endif - diff --git a/cpp/src/qmf/engine/EventImpl.cpp b/cpp/src/qmf/engine/EventImpl.cpp deleted file mode 100644 index 4b034e8e83..0000000000 --- a/cpp/src/qmf/engine/EventImpl.cpp +++ /dev/null @@ -1,120 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include <qmf/engine/EventImpl.h> -#include <qmf/engine/ValueImpl.h> - -#include <sstream> - -using namespace std; -using namespace qmf::engine; -using qpid::framing::Buffer; - -EventImpl::EventImpl(const SchemaEventClass* type) : eventClass(type), timestamp(0), severity(0) -{ - int argCount = eventClass->getArgumentCount(); - int idx; - - for (idx = 0; idx < argCount; idx++) { - const SchemaArgument* arg = eventClass->getArgument(idx); - arguments[arg->getName()] = ValuePtr(new Value(arg->getType())); - } -} - - -EventImpl::EventImpl(const SchemaEventClass* type, Buffer& buffer) : - eventClass(type), timestamp(0), severity(0) -{ - int argCount = eventClass->getArgumentCount(); - int idx; - - timestamp = buffer.getLongLong(); - severity = buffer.getOctet(); - - for (idx = 0; idx < argCount; idx++) - { - const SchemaArgument *arg = eventClass->getArgument(idx); - Value* pval = ValueImpl::factory(arg->getType(), buffer); - arguments[arg->getName()] = ValuePtr(pval); - } -} - - -Event* EventImpl::factory(const SchemaEventClass* type, Buffer& buffer) -{ - EventImpl* impl(new EventImpl(type, buffer)); - return new Event(impl); -} - - -Value* EventImpl::getValue(const char* key) const -{ - map<string, ValuePtr>::const_iterator iter; - - iter = arguments.find(key); - if (iter != arguments.end()) - return iter->second.get(); - - return 0; -} - - -void EventImpl::encodeSchemaKey(Buffer& buffer) const -{ - buffer.putShortString(eventClass->getClassKey()->getPackageName()); - buffer.putShortString(eventClass->getClassKey()->getClassName()); - buffer.putBin128(const_cast<uint8_t*>(eventClass->getClassKey()->getHash())); -} - - -void EventImpl::encode(Buffer& buffer) const -{ - buffer.putOctet((uint8_t) eventClass->getSeverity()); - - int argCount = eventClass->getArgumentCount(); - for (int idx = 0; idx < argCount; idx++) { - const SchemaArgument* arg = eventClass->getArgument(idx); - ValuePtr value = arguments[arg->getName()]; - value->impl->encode(buffer); - } -} - - -string EventImpl::getRoutingKey(uint32_t brokerBank, uint32_t agentBank) const -{ - stringstream key; - - key << "console.event." << brokerBank << "." << agentBank << "." << - eventClass->getClassKey()->getPackageName() << "." << - eventClass->getClassKey()->getClassName(); - return key.str(); -} - - -//================================================================== -// Wrappers -//================================================================== - -Event::Event(const SchemaEventClass* type) : impl(new EventImpl(type)) {} -Event::Event(EventImpl* i) : impl(i) {} -Event::Event(const Event& from) : impl(new EventImpl(*(from.impl))) {} -Event::~Event() { delete impl; } -const SchemaEventClass* Event::getClass() const { return impl->getClass(); } -Value* Event::getValue(const char* key) const { return impl->getValue(key); } - diff --git a/cpp/src/qmf/engine/EventImpl.h b/cpp/src/qmf/engine/EventImpl.h deleted file mode 100644 index 4046e71ef9..0000000000 --- a/cpp/src/qmf/engine/EventImpl.h +++ /dev/null @@ -1,57 +0,0 @@ -#ifndef _QmfEngineEventImpl_ -#define _QmfEngineEventImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include <qmf/engine/Event.h> -#include <qmf/engine/Schema.h> -#include <qpid/framing/Buffer.h> -#include <boost/shared_ptr.hpp> -#include <map> - -namespace qmf { -namespace engine { - - typedef boost::shared_ptr<Event> EventPtr; - - struct EventImpl { - typedef boost::shared_ptr<Value> ValuePtr; - const SchemaEventClass* eventClass; - uint64_t timestamp; - uint8_t severity; - mutable std::map<std::string, ValuePtr> arguments; - - EventImpl(const SchemaEventClass* type); - EventImpl(const SchemaEventClass* type, qpid::framing::Buffer& buffer); - static Event* factory(const SchemaEventClass* type, qpid::framing::Buffer& buffer); - - const SchemaEventClass* getClass() const { return eventClass; } - Value* getValue(const char* key) const; - - void encodeSchemaKey(qpid::framing::Buffer& buffer) const; - void encode(qpid::framing::Buffer& buffer) const; - std::string getRoutingKey(uint32_t brokerBank, uint32_t agentBank) const; - }; - -} -} - -#endif - diff --git a/cpp/src/qmf/engine/MessageImpl.cpp b/cpp/src/qmf/engine/MessageImpl.cpp deleted file mode 100644 index 0047d3eb9d..0000000000 --- a/cpp/src/qmf/engine/MessageImpl.cpp +++ /dev/null @@ -1,43 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/MessageImpl.h" -#include <string.h> - -using namespace std; -using namespace qmf::engine; - -#define STRING_REF(s) {if (!s.empty()) item.s = const_cast<char*>(s.c_str());} - -Message MessageImpl::copy() -{ - Message item; - - ::memset(&item, 0, sizeof(Message)); - item.body = const_cast<char*>(body.c_str()); - item.length = body.length(); - STRING_REF(destination); - STRING_REF(routingKey); - STRING_REF(replyExchange); - STRING_REF(replyKey); - STRING_REF(userId); - - return item; -} - diff --git a/cpp/src/qmf/engine/MessageImpl.h b/cpp/src/qmf/engine/MessageImpl.h deleted file mode 100644 index b91291d2e4..0000000000 --- a/cpp/src/qmf/engine/MessageImpl.h +++ /dev/null @@ -1,44 +0,0 @@ -#ifndef _QmfEngineMessageImpl_ -#define _QmfEngineMessageImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/Message.h" -#include <string> -#include <boost/shared_ptr.hpp> - -namespace qmf { -namespace engine { - - struct MessageImpl { - typedef boost::shared_ptr<MessageImpl> Ptr; - std::string body; - std::string destination; - std::string routingKey; - std::string replyExchange; - std::string replyKey; - std::string userId; - - Message copy(); - }; -} -} - -#endif diff --git a/cpp/src/qmf/engine/ObjectIdImpl.cpp b/cpp/src/qmf/engine/ObjectIdImpl.cpp deleted file mode 100644 index 9216f7bac0..0000000000 --- a/cpp/src/qmf/engine/ObjectIdImpl.cpp +++ /dev/null @@ -1,210 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/ObjectIdImpl.h" -#include <stdlib.h> -#include <sstream> - -using namespace std; -using namespace qmf::engine; -using qpid::framing::Buffer; - -void AgentAttachment::setBanks(uint32_t broker, uint32_t agent) -{ - first = - ((uint64_t) (broker & 0x000fffff)) << 28 | - ((uint64_t) (agent & 0x0fffffff)); -} - -ObjectIdImpl::ObjectIdImpl(Buffer& buffer) : agent(0) -{ - decode(buffer); -} - -ObjectIdImpl::ObjectIdImpl(AgentAttachment* a, uint8_t flags, uint16_t seq, uint64_t object) : agent(a) -{ - first = - ((uint64_t) (flags & 0x0f)) << 60 | - ((uint64_t) (seq & 0x0fff)) << 48; - second = object; -} - -ObjectId* ObjectIdImpl::factory(Buffer& buffer) -{ - ObjectIdImpl* impl(new ObjectIdImpl(buffer)); - return new ObjectId(impl); -} - -ObjectId* ObjectIdImpl::factory(AgentAttachment* agent, uint8_t flags, uint16_t seq, uint64_t object) -{ - ObjectIdImpl* impl(new ObjectIdImpl(agent, flags, seq, object)); - return new ObjectId(impl); -} - -void ObjectIdImpl::decode(Buffer& buffer) -{ - first = buffer.getLongLong(); - second = buffer.getLongLong(); -} - -void ObjectIdImpl::encode(Buffer& buffer) const -{ - if (agent == 0) - buffer.putLongLong(first); - else - buffer.putLongLong(first | agent->first); - buffer.putLongLong(second); -} - -void ObjectIdImpl::fromString(const std::string& repr) -{ -#define FIELDS 5 -#if defined (_WIN32) && !defined (atoll) -# define atoll(X) _atoi64(X) -#endif - - std::string copy(repr.c_str()); - char* cText; - char* field[FIELDS]; - bool atFieldStart = true; - int idx = 0; - - cText = const_cast<char*>(copy.c_str()); - for (char* cursor = cText; *cursor; cursor++) { - if (atFieldStart) { - if (idx >= FIELDS) - return; // TODO error - field[idx++] = cursor; - atFieldStart = false; - } else { - if (*cursor == '-') { - *cursor = '\0'; - atFieldStart = true; - } - } - } - - if (idx != FIELDS) - return; // TODO error - - first = (atoll(field[0]) << 60) + - (atoll(field[1]) << 48) + - (atoll(field[2]) << 28) + - atoll(field[3]); - second = atoll(field[4]); - agent = 0; -} - -const string& ObjectIdImpl::asString() const -{ - stringstream val; - - val << (int) getFlags() << "-" << getSequence() << "-" << getBrokerBank() << "-" << - getAgentBank() << "-" << getObjectNum(); - repr = val.str(); - return repr; -} - -#define ACTUAL_FIRST (agent == 0 ? first : first | agent->first) -#define ACTUAL_OTHER (other.agent == 0 ? other.first : other.first | other.agent->first) - -uint8_t ObjectIdImpl::getFlags() const -{ - return (ACTUAL_FIRST & 0xF000000000000000LL) >> 60; -} - -uint16_t ObjectIdImpl::getSequence() const -{ - return (ACTUAL_FIRST & 0x0FFF000000000000LL) >> 48; -} - -uint32_t ObjectIdImpl::getBrokerBank() const -{ - return (ACTUAL_FIRST & 0x0000FFFFF0000000LL) >> 28; -} - -uint32_t ObjectIdImpl::getAgentBank() const -{ - return ACTUAL_FIRST & 0x000000000FFFFFFFLL; -} - -uint64_t ObjectIdImpl::getObjectNum() const -{ - return second; -} - -uint32_t ObjectIdImpl::getObjectNumHi() const -{ - return (uint32_t) (second >> 32); -} - -uint32_t ObjectIdImpl::getObjectNumLo() const -{ - return (uint32_t) (second & 0x00000000FFFFFFFFLL); -} - -bool ObjectIdImpl::operator==(const ObjectIdImpl& other) const -{ - return ACTUAL_FIRST == ACTUAL_OTHER && second == other.second; -} - -bool ObjectIdImpl::operator<(const ObjectIdImpl& other) const -{ - return (ACTUAL_FIRST < ACTUAL_OTHER) || ((ACTUAL_FIRST == ACTUAL_OTHER) && (second < other.second)); -} - -bool ObjectIdImpl::operator>(const ObjectIdImpl& other) const -{ - return (ACTUAL_FIRST > ACTUAL_OTHER) || ((ACTUAL_FIRST == ACTUAL_OTHER) && (second > other.second)); -} - - -//================================================================== -// Wrappers -//================================================================== - -ObjectId::ObjectId() : impl(new ObjectIdImpl()) {} -ObjectId::ObjectId(const ObjectId& from) : impl(new ObjectIdImpl(*(from.impl))) {} -ObjectId::ObjectId(ObjectIdImpl* i) : impl(i) {} -ObjectId::~ObjectId() { delete impl; } -uint64_t ObjectId::getObjectNum() const { return impl->getObjectNum(); } -uint32_t ObjectId::getObjectNumHi() const { return impl->getObjectNumHi(); } -uint32_t ObjectId::getObjectNumLo() const { return impl->getObjectNumLo(); } -bool ObjectId::isDurable() const { return impl->isDurable(); } -const char* ObjectId::str() const { return impl->asString().c_str(); } -uint8_t ObjectId::getFlags() const { return impl->getFlags(); } -uint16_t ObjectId::getSequence() const { return impl->getSequence(); } -uint32_t ObjectId::getBrokerBank() const { return impl->getBrokerBank(); } -uint32_t ObjectId::getAgentBank() const { return impl->getAgentBank(); } -bool ObjectId::operator==(const ObjectId& other) const { return *impl == *other.impl; } -bool ObjectId::operator<(const ObjectId& other) const { return *impl < *other.impl; } -bool ObjectId::operator>(const ObjectId& other) const { return *impl > *other.impl; } -bool ObjectId::operator<=(const ObjectId& other) const { return !(*impl > *other.impl); } -bool ObjectId::operator>=(const ObjectId& other) const { return !(*impl < *other.impl); } -ObjectId& ObjectId::operator=(const ObjectId& other) { - ObjectIdImpl *old; - if (this != &other) { - old = impl; - impl = new ObjectIdImpl(*(other.impl)); - if (old) - delete old; - } - return *this; -} - diff --git a/cpp/src/qmf/engine/ObjectIdImpl.h b/cpp/src/qmf/engine/ObjectIdImpl.h deleted file mode 100644 index d70c8efff4..0000000000 --- a/cpp/src/qmf/engine/ObjectIdImpl.h +++ /dev/null @@ -1,72 +0,0 @@ -#ifndef _QmfEngineObjectIdImpl_ -#define _QmfEngineObjectIdImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include <qmf/engine/ObjectId.h> -#include <qpid/framing/Buffer.h> - -namespace qmf { -namespace engine { - - struct AgentAttachment { - uint64_t first; - - AgentAttachment() : first(0) {} - void setBanks(uint32_t broker, uint32_t bank); - uint64_t getFirst() const { return first; } - }; - - struct ObjectIdImpl { - AgentAttachment* agent; - uint64_t first; - uint64_t second; - mutable std::string repr; - - ObjectIdImpl() : agent(0), first(0), second(0) {} - ObjectIdImpl(qpid::framing::Buffer& buffer); - ObjectIdImpl(AgentAttachment* agent, uint8_t flags, uint16_t seq, uint64_t object); - - static ObjectId* factory(qpid::framing::Buffer& buffer); - static ObjectId* factory(AgentAttachment* agent, uint8_t flags, uint16_t seq, uint64_t object); - - void decode(qpid::framing::Buffer& buffer); - void encode(qpid::framing::Buffer& buffer) const; - void fromString(const std::string& repr); - const std::string& asString() const; - uint8_t getFlags() const; - uint16_t getSequence() const; - uint32_t getBrokerBank() const; - uint32_t getAgentBank() const; - uint64_t getObjectNum() const; - uint32_t getObjectNumHi() const; - uint32_t getObjectNumLo() const; - bool isDurable() const { return getSequence() == 0; } - void setValue(uint64_t f, uint64_t s) { first = f; second = s; agent = 0; } - - bool operator==(const ObjectIdImpl& other) const; - bool operator<(const ObjectIdImpl& other) const; - bool operator>(const ObjectIdImpl& other) const; - }; -} -} - -#endif - diff --git a/cpp/src/qmf/engine/ObjectImpl.cpp b/cpp/src/qmf/engine/ObjectImpl.cpp deleted file mode 100644 index 45925cb804..0000000000 --- a/cpp/src/qmf/engine/ObjectImpl.cpp +++ /dev/null @@ -1,232 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/ObjectImpl.h" -#include "qmf/engine/ValueImpl.h" -#include "qmf/engine/BrokerProxyImpl.h" -#include <qpid/sys/Time.h> - -using namespace std; -using namespace qmf::engine; -using namespace qpid::sys; -using qpid::framing::Buffer; - -ObjectImpl::ObjectImpl(const SchemaObjectClass* type) : objectClass(type), broker(0), createTime(uint64_t(Duration(EPOCH, now()))), destroyTime(0), lastUpdatedTime(createTime) -{ - int propCount = objectClass->getPropertyCount(); - int statCount = objectClass->getStatisticCount(); - int idx; - - for (idx = 0; idx < propCount; idx++) { - const SchemaProperty* prop = objectClass->getProperty(idx); - properties[prop->getName()] = ValuePtr(new Value(prop->getType())); - } - - for (idx = 0; idx < statCount; idx++) { - const SchemaStatistic* stat = objectClass->getStatistic(idx); - statistics[stat->getName()] = ValuePtr(new Value(stat->getType())); - } -} - -ObjectImpl::ObjectImpl(const SchemaObjectClass* type, BrokerProxyImpl* b, Buffer& buffer, bool prop, bool stat, bool managed) : - objectClass(type), broker(b), createTime(0), destroyTime(0), lastUpdatedTime(0) -{ - int idx; - - if (managed) { - lastUpdatedTime = buffer.getLongLong(); - createTime = buffer.getLongLong(); - destroyTime = buffer.getLongLong(); - objectId.reset(ObjectIdImpl::factory(buffer)); - } - - if (prop) { - int propCount = objectClass->getPropertyCount(); - set<string> excludes; - parsePresenceMasks(buffer, excludes); - for (idx = 0; idx < propCount; idx++) { - const SchemaProperty* prop = objectClass->getProperty(idx); - if (excludes.count(prop->getName()) != 0) { - properties[prop->getName()] = ValuePtr(new Value(prop->getType())); - } else { - Value* pval = ValueImpl::factory(prop->getType(), buffer); - properties[prop->getName()] = ValuePtr(pval); - } - } - } - - if (stat) { - int statCount = objectClass->getStatisticCount(); - for (idx = 0; idx < statCount; idx++) { - const SchemaStatistic* stat = objectClass->getStatistic(idx); - Value* sval = ValueImpl::factory(stat->getType(), buffer); - statistics[stat->getName()] = ValuePtr(sval); - } - } -} - -Object* ObjectImpl::factory(const SchemaObjectClass* type, BrokerProxyImpl* b, Buffer& buffer, bool prop, bool stat, bool managed) -{ - ObjectImpl* impl(new ObjectImpl(type, b, buffer, prop, stat, managed)); - return new Object(impl); -} - -ObjectImpl::~ObjectImpl() -{ -} - -void ObjectImpl::destroy() -{ - destroyTime = uint64_t(Duration(EPOCH, now())); - // TODO - flag deletion -} - -Value* ObjectImpl::getValue(const string& key) const -{ - map<string, ValuePtr>::const_iterator iter; - - iter = properties.find(key); - if (iter != properties.end()) - return iter->second.get(); - - iter = statistics.find(key); - if (iter != statistics.end()) - return iter->second.get(); - - return 0; -} - -void ObjectImpl::invokeMethod(const string& methodName, const Value* inArgs, void* context) const -{ - if (broker != 0 && objectId.get() != 0) - broker->sendMethodRequest(objectId.get(), objectClass, methodName, inArgs, context); -} - -void ObjectImpl::merge(const Object& from) -{ - for (map<string, ValuePtr>::const_iterator piter = from.impl->properties.begin(); - piter != from.impl->properties.end(); piter++) - properties[piter->first] = piter->second; - for (map<string, ValuePtr>::const_iterator siter = from.impl->statistics.begin(); - siter != from.impl->statistics.end(); siter++) - statistics[siter->first] = siter->second; -} - -void ObjectImpl::parsePresenceMasks(Buffer& buffer, set<string>& excludeList) -{ - int propCount = objectClass->getPropertyCount(); - excludeList.clear(); - uint8_t bit = 0; - uint8_t mask = 0; - - for (int idx = 0; idx < propCount; idx++) { - const SchemaProperty* prop = objectClass->getProperty(idx); - if (prop->isOptional()) { - if (bit == 0) { - mask = buffer.getOctet(); - bit = 1; - } - if ((mask & bit) == 0) - excludeList.insert(string(prop->getName())); - if (bit == 0x80) - bit = 0; - else - bit = bit << 1; - } - } -} - -void ObjectImpl::encodeSchemaKey(qpid::framing::Buffer& buffer) const -{ - buffer.putShortString(objectClass->getClassKey()->getPackageName()); - buffer.putShortString(objectClass->getClassKey()->getClassName()); - buffer.putBin128(const_cast<uint8_t*>(objectClass->getClassKey()->getHash())); -} - -void ObjectImpl::encodeManagedObjectData(qpid::framing::Buffer& buffer) const -{ - buffer.putLongLong(lastUpdatedTime); - buffer.putLongLong(createTime); - buffer.putLongLong(destroyTime); - objectId->impl->encode(buffer); -} - -void ObjectImpl::encodeProperties(qpid::framing::Buffer& buffer) const -{ - int propCount = objectClass->getPropertyCount(); - uint8_t bit = 0; - uint8_t mask = 0; - ValuePtr value; - - for (int idx = 0; idx < propCount; idx++) { - const SchemaProperty* prop = objectClass->getProperty(idx); - if (prop->isOptional()) { - value = properties[prop->getName()]; - if (bit == 0) - bit = 1; - if (!value->isNull()) - mask |= bit; - if (bit == 0x80) { - buffer.putOctet(mask); - bit = 0; - mask = 0; - } else - bit = bit << 1; - } - } - if (bit != 0) { - buffer.putOctet(mask); - } - - for (int idx = 0; idx < propCount; idx++) { - const SchemaProperty* prop = objectClass->getProperty(idx); - value = properties[prop->getName()]; - if (!prop->isOptional() || !value->isNull()) { - value->impl->encode(buffer); - } - } -} - -void ObjectImpl::encodeStatistics(qpid::framing::Buffer& buffer) const -{ - int statCount = objectClass->getStatisticCount(); - for (int idx = 0; idx < statCount; idx++) { - const SchemaStatistic* stat = objectClass->getStatistic(idx); - ValuePtr value = statistics[stat->getName()]; - value->impl->encode(buffer); - } -} - -//================================================================== -// Wrappers -//================================================================== - -Object::Object(const SchemaObjectClass* type) : impl(new ObjectImpl(type)) {} -Object::Object(ObjectImpl* i) : impl(i) {} -Object::Object(const Object& from) : impl(new ObjectImpl(*(from.impl))) {} -Object::~Object() { delete impl; } -void Object::destroy() { impl->destroy(); } -const ObjectId* Object::getObjectId() const { return impl->getObjectId(); } -void Object::setObjectId(ObjectId* oid) { impl->setObjectId(oid); } -const SchemaObjectClass* Object::getClass() const { return impl->getClass(); } -Value* Object::getValue(const char* key) const { return impl->getValue(key); } -void Object::invokeMethod(const char* m, const Value* a, void* c) const { impl->invokeMethod(m, a, c); } -bool Object::isDeleted() const { return impl->isDeleted(); } -void Object::merge(const Object& from) { impl->merge(from); } - diff --git a/cpp/src/qmf/engine/ObjectImpl.h b/cpp/src/qmf/engine/ObjectImpl.h deleted file mode 100644 index 6f25867004..0000000000 --- a/cpp/src/qmf/engine/ObjectImpl.h +++ /dev/null @@ -1,76 +0,0 @@ -#ifndef _QmfEngineObjectImpl_ -#define _QmfEngineObjectImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include <qmf/engine/Object.h> -#include <qmf/engine/ObjectIdImpl.h> -#include <map> -#include <set> -#include <string> -#include <qpid/framing/Buffer.h> -#include <boost/shared_ptr.hpp> -#include <qpid/sys/Mutex.h> - -namespace qmf { -namespace engine { - - class BrokerProxyImpl; - - typedef boost::shared_ptr<Object> ObjectPtr; - - struct ObjectImpl { - typedef boost::shared_ptr<Value> ValuePtr; - const SchemaObjectClass* objectClass; - BrokerProxyImpl* broker; - boost::shared_ptr<ObjectId> objectId; - uint64_t createTime; - uint64_t destroyTime; - uint64_t lastUpdatedTime; - mutable std::map<std::string, ValuePtr> properties; - mutable std::map<std::string, ValuePtr> statistics; - - ObjectImpl(const SchemaObjectClass* type); - ObjectImpl(const SchemaObjectClass* type, BrokerProxyImpl* b, qpid::framing::Buffer& buffer, - bool prop, bool stat, bool managed); - static Object* factory(const SchemaObjectClass* type, BrokerProxyImpl* b, qpid::framing::Buffer& buffer, - bool prop, bool stat, bool managed); - ~ObjectImpl(); - - void destroy(); - const ObjectId* getObjectId() const { return objectId.get(); } - void setObjectId(ObjectId* oid) { objectId.reset(new ObjectId(*oid)); } - const SchemaObjectClass* getClass() const { return objectClass; } - Value* getValue(const std::string& key) const; - void invokeMethod(const std::string& methodName, const Value* inArgs, void* context) const; - bool isDeleted() const { return destroyTime != 0; } - void merge(const Object& from); - - void parsePresenceMasks(qpid::framing::Buffer& buffer, std::set<std::string>& excludeList); - void encodeSchemaKey(qpid::framing::Buffer& buffer) const; - void encodeManagedObjectData(qpid::framing::Buffer& buffer) const; - void encodeProperties(qpid::framing::Buffer& buffer) const; - void encodeStatistics(qpid::framing::Buffer& buffer) const; - }; -} -} - -#endif - diff --git a/cpp/src/qmf/engine/Protocol.cpp b/cpp/src/qmf/engine/Protocol.cpp deleted file mode 100644 index 9e5f490604..0000000000 --- a/cpp/src/qmf/engine/Protocol.cpp +++ /dev/null @@ -1,52 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/Protocol.h" -#include "qpid/framing/Buffer.h" - -using namespace std; -using namespace qmf::engine; -using namespace qpid::framing; - - -bool Protocol::checkHeader(Buffer& buf, uint8_t *opcode, uint32_t *seq) -{ - if (buf.available() < 8) - return false; - - uint8_t h1 = buf.getOctet(); - uint8_t h2 = buf.getOctet(); - uint8_t h3 = buf.getOctet(); - - *opcode = buf.getOctet(); - *seq = buf.getLong(); - - return h1 == 'A' && h2 == 'M' && h3 == '2'; -} - -void Protocol::encodeHeader(qpid::framing::Buffer& buf, uint8_t opcode, uint32_t seq) -{ - buf.putOctet('A'); - buf.putOctet('M'); - buf.putOctet('2'); - buf.putOctet(opcode); - buf.putLong (seq); -} - - diff --git a/cpp/src/qmf/engine/Protocol.h b/cpp/src/qmf/engine/Protocol.h deleted file mode 100644 index 1cdfa60c84..0000000000 --- a/cpp/src/qmf/engine/Protocol.h +++ /dev/null @@ -1,69 +0,0 @@ -#ifndef _QmfEngineProtocol_ -#define _QmfEngineProtocol_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include <qpid/sys/IntegerTypes.h> - -namespace qpid { - namespace framing { - class Buffer; - } -} - -namespace qmf { -namespace engine { - - class Protocol { - public: - static bool checkHeader(qpid::framing::Buffer& buf, uint8_t *opcode, uint32_t *seq); - static void encodeHeader(qpid::framing::Buffer& buf, uint8_t opcode, uint32_t seq = 0); - - const static uint8_t OP_ATTACH_REQUEST = 'A'; - const static uint8_t OP_ATTACH_RESPONSE = 'a'; - - const static uint8_t OP_BROKER_REQUEST = 'B'; - const static uint8_t OP_BROKER_RESPONSE = 'b'; - - const static uint8_t OP_CONSOLE_ADDED_INDICATION = 'x'; - const static uint8_t OP_COMMAND_COMPLETE = 'z'; - const static uint8_t OP_HEARTBEAT_INDICATION = 'h'; - - const static uint8_t OP_PACKAGE_REQUEST = 'P'; - const static uint8_t OP_PACKAGE_INDICATION = 'p'; - const static uint8_t OP_CLASS_QUERY = 'Q'; - const static uint8_t OP_CLASS_INDICATION = 'q'; - const static uint8_t OP_SCHEMA_REQUEST = 'S'; - const static uint8_t OP_SCHEMA_RESPONSE = 's'; - - const static uint8_t OP_METHOD_REQUEST = 'M'; - const static uint8_t OP_METHOD_RESPONSE = 'm'; - const static uint8_t OP_GET_QUERY = 'G'; - const static uint8_t OP_OBJECT_INDICATION = 'g'; - const static uint8_t OP_PROPERTY_INDICATION = 'c'; - const static uint8_t OP_STATISTIC_INDICATION = 'i'; - const static uint8_t OP_EVENT_INDICATION = 'e'; - }; - -} -} - -#endif - diff --git a/cpp/src/qmf/engine/QueryImpl.cpp b/cpp/src/qmf/engine/QueryImpl.cpp deleted file mode 100644 index 6f2beeee87..0000000000 --- a/cpp/src/qmf/engine/QueryImpl.cpp +++ /dev/null @@ -1,103 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/QueryImpl.h" -#include "qmf/engine/ObjectIdImpl.h" -#include "qpid/framing/Buffer.h" -#include "qpid/framing/FieldTable.h" - -using namespace std; -using namespace qmf::engine; -using namespace qpid::framing; - -bool QueryElementImpl::evaluate(const Object* /*object*/) const -{ - // TODO: Implement this - return false; -} - -bool QueryExpressionImpl::evaluate(const Object* /*object*/) const -{ - // TODO: Implement this - return false; -} - -QueryImpl::QueryImpl(Buffer& buffer) -{ - FieldTable ft; - ft.decode(buffer); - // TODO -} - -Query* QueryImpl::factory(Buffer& buffer) -{ - QueryImpl* impl(new QueryImpl(buffer)); - return new Query(impl); -} - -void QueryImpl::encode(Buffer& buffer) const -{ - FieldTable ft; - - if (oid.get() != 0) { - ft.setString("_objectid", oid->impl->asString()); - } else { - if (!packageName.empty()) - ft.setString("_package", packageName); - ft.setString("_class", className); - } - - ft.encode(buffer); -} - - -//================================================================== -// Wrappers -//================================================================== - -QueryElement::QueryElement(const char* attrName, const Value* value, ValueOper oper) : impl(new QueryElementImpl(attrName, value, oper)) {} -QueryElement::QueryElement(QueryElementImpl* i) : impl(i) {} -QueryElement::~QueryElement() { delete impl; } -bool QueryElement::evaluate(const Object* object) const { return impl->evaluate(object); } - -QueryExpression::QueryExpression(ExprOper oper, const QueryOperand* operand1, const QueryOperand* operand2) : impl(new QueryExpressionImpl(oper, operand1, operand2)) {} -QueryExpression::QueryExpression(QueryExpressionImpl* i) : impl(i) {} -QueryExpression::~QueryExpression() { delete impl; } -bool QueryExpression::evaluate(const Object* object) const { return impl->evaluate(object); } - -Query::Query(const char* className, const char* packageName) : impl(new QueryImpl(className, packageName)) {} -Query::Query(const SchemaClassKey* key) : impl(new QueryImpl(key)) {} -Query::Query(const ObjectId* oid) : impl(new QueryImpl(oid)) {} -Query::Query(QueryImpl* i) : impl(i) {} -Query::Query(const Query& from) : impl(new QueryImpl(*(from.impl))) {} -Query::~Query() { delete impl; } -void Query::setSelect(const QueryOperand* criterion) { impl->setSelect(criterion); } -void Query::setLimit(uint32_t maxResults) { impl->setLimit(maxResults); } -void Query::setOrderBy(const char* attrName, bool decreasing) { impl->setOrderBy(attrName, decreasing); } -const char* Query::getPackage() const { return impl->getPackage().c_str(); } -const char* Query::getClass() const { return impl->getClass().c_str(); } -const ObjectId* Query::getObjectId() const { return impl->getObjectId(); } -bool Query::haveSelect() const { return impl->haveSelect(); } -bool Query::haveLimit() const { return impl->haveLimit(); } -bool Query::haveOrderBy() const { return impl->haveOrderBy(); } -const QueryOperand* Query::getSelect() const { return impl->getSelect(); } -uint32_t Query::getLimit() const { return impl->getLimit(); } -const char* Query::getOrderBy() const { return impl->getOrderBy().c_str(); } -bool Query::getDecreasing() const { return impl->getDecreasing(); } - diff --git a/cpp/src/qmf/engine/QueryImpl.h b/cpp/src/qmf/engine/QueryImpl.h deleted file mode 100644 index 8ebe0d932f..0000000000 --- a/cpp/src/qmf/engine/QueryImpl.h +++ /dev/null @@ -1,102 +0,0 @@ -#ifndef _QmfEngineQueryImpl_ -#define _QmfEngineQueryImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/Query.h" -#include "qmf/engine/Schema.h" -#include <string> -#include <boost/shared_ptr.hpp> - -namespace qpid { - namespace framing { - class Buffer; - } -} - -namespace qmf { -namespace engine { - - struct QueryElementImpl { - QueryElementImpl(const std::string& a, const Value* v, ValueOper o) : attrName(a), value(v), oper(o) {} - ~QueryElementImpl() {} - bool evaluate(const Object* object) const; - - std::string attrName; - const Value* value; - ValueOper oper; - }; - - struct QueryExpressionImpl { - QueryExpressionImpl(ExprOper o, const QueryOperand* operand1, const QueryOperand* operand2) : oper(o), left(operand1), right(operand2) {} - ~QueryExpressionImpl() {} - bool evaluate(const Object* object) const; - - ExprOper oper; - const QueryOperand* left; - const QueryOperand* right; - }; - - struct QueryImpl { - // Constructors mapped to public - QueryImpl(const std::string& c, const std::string& p) : packageName(p), className(c), select(0), resultLimit(0) {} - QueryImpl(const SchemaClassKey* key) : packageName(key->getPackageName()), className(key->getClassName()), select(0), resultLimit(0) {} - QueryImpl(const ObjectId* oid) : oid(new ObjectId(*oid)), select(0), resultLimit(0) {} - - // Factory constructors - QueryImpl(qpid::framing::Buffer& buffer); - - ~QueryImpl() {}; - static Query* factory(qpid::framing::Buffer& buffer); - - void setSelect(const QueryOperand* criterion) { select = criterion; } - void setLimit(uint32_t maxResults) { resultLimit = maxResults; } - void setOrderBy(const std::string& attrName, bool decreasing) { - orderBy = attrName; orderDecreasing = decreasing; - } - - const std::string& getPackage() const { return packageName; } - const std::string& getClass() const { return className; } - const ObjectId* getObjectId() const { return oid.get(); } - - bool haveSelect() const { return select != 0; } - bool haveLimit() const { return resultLimit > 0; } - bool haveOrderBy() const { return !orderBy.empty(); } - const QueryOperand* getSelect() const { return select; } - uint32_t getLimit() const { return resultLimit; } - const std::string& getOrderBy() const { return orderBy; } - bool getDecreasing() const { return orderDecreasing; } - - void encode(qpid::framing::Buffer& buffer) const; - bool singleAgent() const { return oid.get() != 0; } - uint32_t agentBank() const { return singleAgent() ? oid->getAgentBank() : 0; } - - std::string packageName; - std::string className; - boost::shared_ptr<ObjectId> oid; - const QueryOperand* select; - uint32_t resultLimit; - std::string orderBy; - bool orderDecreasing; - }; -} -} - -#endif diff --git a/cpp/src/qmf/engine/ResilientConnection.cpp b/cpp/src/qmf/engine/ResilientConnection.cpp deleted file mode 100644 index ab65b8d768..0000000000 --- a/cpp/src/qmf/engine/ResilientConnection.cpp +++ /dev/null @@ -1,514 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/ResilientConnection.h" -#include "qmf/engine/MessageImpl.h" -#include "qmf/engine/ConnectionSettingsImpl.h" -#include <qpid/client/Connection.h> -#include <qpid/client/Session.h> -#include <qpid/client/MessageListener.h> -#include <qpid/client/SubscriptionManager.h> -#include <qpid/client/Message.h> -#include <qpid/sys/Thread.h> -#include <qpid/sys/Runnable.h> -#include <qpid/sys/Mutex.h> -#include <qpid/sys/Condition.h> -#include <qpid/sys/Time.h> -#include <qpid/log/Statement.h> -#include <qpid/RefCounted.h> -#include <boost/bind.hpp> -#include <string> -#include <deque> -#include <vector> -#include <set> -#include <boost/intrusive_ptr.hpp> -#include <boost/noncopyable.hpp> -#include <unistd.h> -#include <fcntl.h> - -using namespace std; -using namespace qmf::engine; -using namespace qpid; -using qpid::sys::Mutex; - -namespace qmf { -namespace engine { - struct ResilientConnectionEventImpl { - ResilientConnectionEvent::EventKind kind; - void* sessionContext; - string errorText; - MessageImpl message; - - ResilientConnectionEventImpl(ResilientConnectionEvent::EventKind k, - const MessageImpl& m = MessageImpl()) : - kind(k), sessionContext(0), message(m) {} - ResilientConnectionEvent copy(); - }; - - struct RCSession : public client::MessageListener, public qpid::sys::Runnable, public qpid::RefCounted { - typedef boost::intrusive_ptr<RCSession> Ptr; - ResilientConnectionImpl& connImpl; - string name; - client::Connection& connection; - client::Session session; - client::SubscriptionManager* subscriptions; - string userId; - void* userContext; - vector<string> dests; - qpid::sys::Thread thread; - - RCSession(ResilientConnectionImpl& ci, const string& n, client::Connection& c, void* uc); - ~RCSession(); - void received(client::Message& msg); - void run(); - void stop(); - }; - - class ResilientConnectionImpl : public qpid::sys::Runnable, public boost::noncopyable { - public: - ResilientConnectionImpl(const ConnectionSettings& settings); - ~ResilientConnectionImpl(); - - bool isConnected() const; - bool getEvent(ResilientConnectionEvent& event); - void popEvent(); - bool createSession(const char* name, void* sessionContext, SessionHandle& handle); - void destroySession(SessionHandle handle); - void sendMessage(SessionHandle handle, qmf::engine::Message& message); - void declareQueue(SessionHandle handle, char* queue); - void deleteQueue(SessionHandle handle, char* queue); - void bind(SessionHandle handle, char* exchange, char* queue, char* key); - void unbind(SessionHandle handle, char* exchange, char* queue, char* key); - void setNotifyFd(int fd); - void notify(); - - void run(); - void failure(); - void sessionClosed(RCSession* sess); - - void EnqueueEvent(ResilientConnectionEvent::EventKind kind, - void* sessionContext = 0, - const MessageImpl& message = MessageImpl(), - const string& errorText = ""); - - private: - int notifyFd; - bool connected; - bool shutdown; - string lastError; - const ConnectionSettings settings; - client::Connection connection; - mutable qpid::sys::Mutex lock; - int delayMin; - int delayMax; - int delayFactor; - qpid::sys::Condition cond; - deque<ResilientConnectionEventImpl> eventQueue; - set<RCSession::Ptr> sessions; - qpid::sys::Thread connThread; - }; -} -} - -ResilientConnectionEvent ResilientConnectionEventImpl::copy() -{ - ResilientConnectionEvent item; - - ::memset(&item, 0, sizeof(ResilientConnectionEvent)); - item.kind = kind; - item.sessionContext = sessionContext; - item.message = message.copy(); - item.errorText = const_cast<char*>(errorText.c_str()); - - return item; -} - -RCSession::RCSession(ResilientConnectionImpl& ci, const string& n, client::Connection& c, void* uc) : - connImpl(ci), name(n), connection(c), session(connection.newSession(name)), - subscriptions(new client::SubscriptionManager(session)), userContext(uc), thread(*this) -{ - const qpid::client::ConnectionSettings& operSettings = connection.getNegotiatedSettings(); - userId = operSettings.username; -} - -RCSession::~RCSession() -{ - subscriptions->stop(); - thread.join(); - session.close(); - delete subscriptions; -} - -void RCSession::run() -{ - try { - subscriptions->run(); - } catch (exception& /*e*/) { - connImpl.sessionClosed(this); - } -} - -void RCSession::stop() -{ - subscriptions->stop(); -} - -void RCSession::received(client::Message& msg) -{ - MessageImpl qmsg; - qmsg.body = msg.getData(); - - qpid::framing::DeliveryProperties dp = msg.getDeliveryProperties(); - if (dp.hasRoutingKey()) { - qmsg.routingKey = dp.getRoutingKey(); - } - - qpid::framing::MessageProperties mp = msg.getMessageProperties(); - if (mp.hasReplyTo()) { - const qpid::framing::ReplyTo& rt = mp.getReplyTo(); - qmsg.replyExchange = rt.getExchange(); - qmsg.replyKey = rt.getRoutingKey(); - } - - if (mp.hasUserId()) { - qmsg.userId = mp.getUserId(); - } - - connImpl.EnqueueEvent(ResilientConnectionEvent::RECV, userContext, qmsg); -} - -ResilientConnectionImpl::ResilientConnectionImpl(const ConnectionSettings& _settings) : - notifyFd(-1), connected(false), shutdown(false), settings(_settings), delayMin(1), connThread(*this) -{ - connection.registerFailureCallback(boost::bind(&ResilientConnectionImpl::failure, this)); - settings.impl->getRetrySettings(&delayMin, &delayMax, &delayFactor); -} - -ResilientConnectionImpl::~ResilientConnectionImpl() -{ - shutdown = true; - connected = false; - cond.notify(); - connThread.join(); - connection.close(); -} - -bool ResilientConnectionImpl::isConnected() const -{ - Mutex::ScopedLock _lock(lock); - return connected; -} - -bool ResilientConnectionImpl::getEvent(ResilientConnectionEvent& event) -{ - Mutex::ScopedLock _lock(lock); - if (eventQueue.empty()) - return false; - event = eventQueue.front().copy(); - return true; -} - -void ResilientConnectionImpl::popEvent() -{ - Mutex::ScopedLock _lock(lock); - if (!eventQueue.empty()) - eventQueue.pop_front(); -} - -bool ResilientConnectionImpl::createSession(const char* name, void* sessionContext, - SessionHandle& handle) -{ - Mutex::ScopedLock _lock(lock); - if (!connected) - return false; - - RCSession::Ptr sess = RCSession::Ptr(new RCSession(*this, name, connection, sessionContext)); - - handle.impl = (void*) sess.get(); - sessions.insert(sess); - - return true; -} - -void ResilientConnectionImpl::destroySession(SessionHandle handle) -{ - Mutex::ScopedLock _lock(lock); - RCSession::Ptr sess = RCSession::Ptr((RCSession*) handle.impl); - set<RCSession::Ptr>::iterator iter = sessions.find(sess); - if (iter != sessions.end()) { - for (vector<string>::iterator dIter = sess->dests.begin(); dIter != sess->dests.end(); dIter++) - sess->subscriptions->cancel(dIter->c_str()); - sess->subscriptions->stop(); - sess->subscriptions->wait(); - - sessions.erase(iter); - return; - } -} - -void ResilientConnectionImpl::sendMessage(SessionHandle handle, qmf::engine::Message& message) -{ - Mutex::ScopedLock _lock(lock); - RCSession::Ptr sess = RCSession::Ptr((RCSession*) handle.impl); - set<RCSession::Ptr>::iterator iter = sessions.find(sess); - qpid::client::Message msg; - string data(message.body, message.length); - msg.getDeliveryProperties().setRoutingKey(message.routingKey); - msg.getMessageProperties().setReplyTo(qpid::framing::ReplyTo(message.replyExchange, message.replyKey)); - if (settings.impl->getSendUserId()) - msg.getMessageProperties().setUserId(sess->userId); - msg.setData(data); - - try { - sess->session.messageTransfer(client::arg::content=msg, client::arg::destination=message.destination); - } catch(exception& e) { - QPID_LOG(error, "Session Exception during message-transfer: " << e.what()); - sessions.erase(iter); - EnqueueEvent(ResilientConnectionEvent::SESSION_CLOSED, (*iter)->userContext); - } -} - -void ResilientConnectionImpl::declareQueue(SessionHandle handle, char* queue) -{ - Mutex::ScopedLock _lock(lock); - RCSession* sess = (RCSession*) handle.impl; - - sess->session.queueDeclare(client::arg::queue=queue, client::arg::autoDelete=true, client::arg::exclusive=true); - sess->subscriptions->setAcceptMode(client::ACCEPT_MODE_NONE); - sess->subscriptions->setAcquireMode(client::ACQUIRE_MODE_PRE_ACQUIRED); - sess->subscriptions->subscribe(*sess, queue, queue); - sess->subscriptions->setFlowControl(queue, client::FlowControl::unlimited()); - sess->dests.push_back(string(queue)); -} - -void ResilientConnectionImpl::deleteQueue(SessionHandle handle, char* queue) -{ - Mutex::ScopedLock _lock(lock); - RCSession* sess = (RCSession*) handle.impl; - - sess->session.queueDelete(client::arg::queue=queue); - for (vector<string>::iterator iter = sess->dests.begin(); - iter != sess->dests.end(); iter++) - if (*iter == queue) { - sess->subscriptions->cancel(queue); - sess->dests.erase(iter); - break; - } -} - -void ResilientConnectionImpl::bind(SessionHandle handle, - char* exchange, char* queue, char* key) -{ - Mutex::ScopedLock _lock(lock); - RCSession* sess = (RCSession*) handle.impl; - - sess->session.exchangeBind(client::arg::exchange=exchange, client::arg::queue=queue, client::arg::bindingKey=key); -} - -void ResilientConnectionImpl::unbind(SessionHandle handle, - char* exchange, char* queue, char* key) -{ - Mutex::ScopedLock _lock(lock); - RCSession* sess = (RCSession*) handle.impl; - - sess->session.exchangeUnbind(client::arg::exchange=exchange, client::arg::queue=queue, client::arg::bindingKey=key); -} - -void ResilientConnectionImpl::notify() -{ - if (notifyFd != -1) - { - int unused_ret; //Suppress warnings about ignoring return value. - unused_ret = ::write(notifyFd, ".", 1); - } -} - - -void ResilientConnectionImpl::setNotifyFd(int fd) -{ - notifyFd = fd; - if (notifyFd > 0) { - int original = fcntl(notifyFd, F_GETFL); - fcntl(notifyFd, F_SETFL, O_NONBLOCK | original); - } -} - -void ResilientConnectionImpl::run() -{ - int delay(delayMin); - - while (true) { - try { - QPID_LOG(trace, "Trying to open connection..."); - connection.open(settings.impl->getClientSettings()); - { - Mutex::ScopedLock _lock(lock); - connected = true; - EnqueueEvent(ResilientConnectionEvent::CONNECTED); - - while (connected) - cond.wait(lock); - delay = delayMin; - - while (!sessions.empty()) { - set<RCSession::Ptr>::iterator iter = sessions.begin(); - RCSession::Ptr sess = *iter; - sessions.erase(iter); - EnqueueEvent(ResilientConnectionEvent::SESSION_CLOSED, sess->userContext); - Mutex::ScopedUnlock _u(lock); - sess->stop(); - - // Nullify the intrusive pointer within the scoped unlock, otherwise, - // the reference is held until overwritted above (under lock) which causes - // the session destructor to be called with the lock held. - sess = 0; - } - - EnqueueEvent(ResilientConnectionEvent::DISCONNECTED); - - if (shutdown) - return; - } - connection.close(); - } catch (exception &e) { - QPID_LOG(debug, "connection.open exception: " << e.what()); - Mutex::ScopedLock _lock(lock); - lastError = e.what(); - if (delay < delayMax) - delay *= delayFactor; - } - - ::qpid::sys::sleep(delay); - } -} - -void ResilientConnectionImpl::failure() -{ - Mutex::ScopedLock _lock(lock); - - connected = false; - lastError = "Closed by Peer"; - cond.notify(); -} - -void ResilientConnectionImpl::sessionClosed(RCSession*) -{ - Mutex::ScopedLock _lock(lock); - connected = false; - lastError = "Closed due to Session failure"; - cond.notify(); -} - -void ResilientConnectionImpl::EnqueueEvent(ResilientConnectionEvent::EventKind kind, - void* sessionContext, - const MessageImpl& message, - const string& errorText) -{ - { - Mutex::ScopedLock _lock(lock); - ResilientConnectionEventImpl event(kind, message); - - event.sessionContext = sessionContext; - event.errorText = errorText; - - eventQueue.push_back(event); - } - - if (notifyFd != -1) - { - int unused_ret; //Suppress warnings about ignoring return value. - unused_ret = ::write(notifyFd, ".", 1); - } -} - - -//================================================================== -// Wrappers -//================================================================== - -ResilientConnection::ResilientConnection(const ConnectionSettings& settings) -{ - impl = new ResilientConnectionImpl(settings); -} - -ResilientConnection::~ResilientConnection() -{ - delete impl; -} - -bool ResilientConnection::isConnected() const -{ - return impl->isConnected(); -} - -bool ResilientConnection::getEvent(ResilientConnectionEvent& event) -{ - return impl->getEvent(event); -} - -void ResilientConnection::popEvent() -{ - impl->popEvent(); -} - -bool ResilientConnection::createSession(const char* name, void* sessionContext, SessionHandle& handle) -{ - return impl->createSession(name, sessionContext, handle); -} - -void ResilientConnection::destroySession(SessionHandle handle) -{ - impl->destroySession(handle); -} - -void ResilientConnection::sendMessage(SessionHandle handle, qmf::engine::Message& message) -{ - impl->sendMessage(handle, message); -} - -void ResilientConnection::declareQueue(SessionHandle handle, char* queue) -{ - impl->declareQueue(handle, queue); -} - -void ResilientConnection::deleteQueue(SessionHandle handle, char* queue) -{ - impl->deleteQueue(handle, queue); -} - -void ResilientConnection::bind(SessionHandle handle, char* exchange, char* queue, char* key) -{ - impl->bind(handle, exchange, queue, key); -} - -void ResilientConnection::unbind(SessionHandle handle, char* exchange, char* queue, char* key) -{ - impl->unbind(handle, exchange, queue, key); -} - -void ResilientConnection::setNotifyFd(int fd) -{ - impl->setNotifyFd(fd); -} - -void ResilientConnection::notify() -{ - impl->notify(); -} - diff --git a/cpp/src/qmf/engine/SchemaImpl.cpp b/cpp/src/qmf/engine/SchemaImpl.cpp deleted file mode 100644 index f75663e131..0000000000 --- a/cpp/src/qmf/engine/SchemaImpl.cpp +++ /dev/null @@ -1,614 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/SchemaImpl.h" -#include <qpid/framing/Buffer.h> -#include <qpid/framing/FieldTable.h> -#include <qpid/framing/Uuid.h> -#include <string.h> -#include <string> -#include <vector> -#include <sstream> - -using namespace std; -using namespace qmf::engine; -using qpid::framing::Buffer; -using qpid::framing::FieldTable; -using qpid::framing::Uuid; - -SchemaHash::SchemaHash() -{ - for (int idx = 0; idx < 16; idx++) - hash[idx] = 0x5A; -} - -void SchemaHash::encode(Buffer& buffer) const -{ - buffer.putBin128(hash); -} - -void SchemaHash::decode(Buffer& buffer) -{ - buffer.getBin128(hash); -} - -void SchemaHash::update(uint8_t data) -{ - update((char*) &data, 1); -} - -void SchemaHash::update(const char* data, uint32_t len) -{ - union h { - uint8_t b[16]; - uint64_t q[2]; - }* h = reinterpret_cast<union h*>(&hash[0]); - uint64_t* first = &h->q[0]; - uint64_t* second = &h->q[1]; - for (uint32_t idx = 0; idx < len; idx++) { - *first = *first ^ (uint64_t) data[idx]; - *second = *second << 1; - *second |= ((*first & 0x8000000000000000LL) >> 63); - *first = *first << 1; - *first = *first ^ *second; - } -} - -bool SchemaHash::operator==(const SchemaHash& other) const -{ - return ::memcmp(&hash, &other.hash, 16) == 0; -} - -bool SchemaHash::operator<(const SchemaHash& other) const -{ - return ::memcmp(&hash, &other.hash, 16) < 0; -} - -bool SchemaHash::operator>(const SchemaHash& other) const -{ - return ::memcmp(&hash, &other.hash, 16) > 0; -} - -SchemaArgumentImpl::SchemaArgumentImpl(Buffer& buffer) -{ - FieldTable map; - map.decode(buffer); - - name = map.getAsString("name"); - typecode = (Typecode) map.getAsInt("type"); - unit = map.getAsString("unit"); - description = map.getAsString("desc"); - - dir = DIR_IN; - string dstr(map.getAsString("dir")); - if (dstr == "O") - dir = DIR_OUT; - else if (dstr == "IO") - dir = DIR_IN_OUT; -} - -SchemaArgument* SchemaArgumentImpl::factory(Buffer& buffer) -{ - SchemaArgumentImpl* impl(new SchemaArgumentImpl(buffer)); - return new SchemaArgument(impl); -} - -void SchemaArgumentImpl::encode(Buffer& buffer) const -{ - FieldTable map; - - map.setString("name", name); - map.setInt("type", (int) typecode); - if (dir == DIR_IN) - map.setString("dir", "I"); - else if (dir == DIR_OUT) - map.setString("dir", "O"); - else - map.setString("dir", "IO"); - if (!unit.empty()) - map.setString("unit", unit); - if (!description.empty()) - map.setString("desc", description); - - map.encode(buffer); -} - -void SchemaArgumentImpl::updateHash(SchemaHash& hash) const -{ - hash.update(name); - hash.update(typecode); - hash.update(dir); - hash.update(unit); - hash.update(description); -} - -SchemaMethodImpl::SchemaMethodImpl(Buffer& buffer) -{ - FieldTable map; - int argCount; - - map.decode(buffer); - name = map.getAsString("name"); - argCount = map.getAsInt("argCount"); - description = map.getAsString("desc"); - - for (int idx = 0; idx < argCount; idx++) { - SchemaArgument* arg = SchemaArgumentImpl::factory(buffer); - addArgument(arg); - } -} - -SchemaMethod* SchemaMethodImpl::factory(Buffer& buffer) -{ - SchemaMethodImpl* impl(new SchemaMethodImpl(buffer)); - return new SchemaMethod(impl); -} - -void SchemaMethodImpl::encode(Buffer& buffer) const -{ - FieldTable map; - - map.setString("name", name); - map.setInt("argCount", arguments.size()); - if (!description.empty()) - map.setString("desc", description); - map.encode(buffer); - - for (vector<const SchemaArgument*>::const_iterator iter = arguments.begin(); - iter != arguments.end(); iter++) - (*iter)->impl->encode(buffer); -} - -void SchemaMethodImpl::addArgument(const SchemaArgument* argument) -{ - arguments.push_back(argument); -} - -const SchemaArgument* SchemaMethodImpl::getArgument(int idx) const -{ - int count = 0; - for (vector<const SchemaArgument*>::const_iterator iter = arguments.begin(); - iter != arguments.end(); iter++, count++) - if (idx == count) - return (*iter); - return 0; -} - -void SchemaMethodImpl::updateHash(SchemaHash& hash) const -{ - hash.update(name); - hash.update(description); - for (vector<const SchemaArgument*>::const_iterator iter = arguments.begin(); - iter != arguments.end(); iter++) - (*iter)->impl->updateHash(hash); -} - -SchemaPropertyImpl::SchemaPropertyImpl(Buffer& buffer) -{ - FieldTable map; - map.decode(buffer); - - name = map.getAsString("name"); - typecode = (Typecode) map.getAsInt("type"); - access = (Access) map.getAsInt("access"); - index = map.getAsInt("index") != 0; - optional = map.getAsInt("optional") != 0; - unit = map.getAsString("unit"); - description = map.getAsString("desc"); -} - -SchemaProperty* SchemaPropertyImpl::factory(Buffer& buffer) -{ - SchemaPropertyImpl* impl(new SchemaPropertyImpl(buffer)); - return new SchemaProperty(impl); -} - -void SchemaPropertyImpl::encode(Buffer& buffer) const -{ - FieldTable map; - - map.setString("name", name); - map.setInt("type", (int) typecode); - map.setInt("access", (int) access); - map.setInt("index", index ? 1 : 0); - map.setInt("optional", optional ? 1 : 0); - if (!unit.empty()) - map.setString("unit", unit); - if (!description.empty()) - map.setString("desc", description); - - map.encode(buffer); -} - -void SchemaPropertyImpl::updateHash(SchemaHash& hash) const -{ - hash.update(name); - hash.update(typecode); - hash.update(access); - hash.update(index); - hash.update(optional); - hash.update(unit); - hash.update(description); -} - -SchemaStatisticImpl::SchemaStatisticImpl(Buffer& buffer) -{ - FieldTable map; - map.decode(buffer); - - name = map.getAsString("name"); - typecode = (Typecode) map.getAsInt("type"); - unit = map.getAsString("unit"); - description = map.getAsString("desc"); -} - -SchemaStatistic* SchemaStatisticImpl::factory(Buffer& buffer) -{ - SchemaStatisticImpl* impl(new SchemaStatisticImpl(buffer)); - return new SchemaStatistic(impl); -} - -void SchemaStatisticImpl::encode(Buffer& buffer) const -{ - FieldTable map; - - map.setString("name", name); - map.setInt("type", (int) typecode); - if (!unit.empty()) - map.setString("unit", unit); - if (!description.empty()) - map.setString("desc", description); - - map.encode(buffer); -} - -void SchemaStatisticImpl::updateHash(SchemaHash& hash) const -{ - hash.update(name); - hash.update(typecode); - hash.update(unit); - hash.update(description); -} - -SchemaClassKeyImpl::SchemaClassKeyImpl(const string& p, const string& n, const SchemaHash& h) : package(p), name(n), hash(h) {} - -SchemaClassKeyImpl::SchemaClassKeyImpl(Buffer& buffer) : package(packageContainer), name(nameContainer), hash(hashContainer) -{ - buffer.getShortString(packageContainer); - buffer.getShortString(nameContainer); - hashContainer.decode(buffer); -} - -SchemaClassKey* SchemaClassKeyImpl::factory(const string& package, const string& name, const SchemaHash& hash) -{ - SchemaClassKeyImpl* impl(new SchemaClassKeyImpl(package, name, hash)); - return new SchemaClassKey(impl); -} - -SchemaClassKey* SchemaClassKeyImpl::factory(Buffer& buffer) -{ - SchemaClassKeyImpl* impl(new SchemaClassKeyImpl(buffer)); - return new SchemaClassKey(impl); -} - -void SchemaClassKeyImpl::encode(Buffer& buffer) const -{ - buffer.putShortString(package); - buffer.putShortString(name); - hash.encode(buffer); -} - -bool SchemaClassKeyImpl::operator==(const SchemaClassKeyImpl& other) const -{ - return package == other.package && - name == other.name && - hash == other.hash; -} - -bool SchemaClassKeyImpl::operator<(const SchemaClassKeyImpl& other) const -{ - if (package < other.package) return true; - if (package > other.package) return false; - if (name < other.name) return true; - if (name > other.name) return false; - return hash < other.hash; -} - -const string& SchemaClassKeyImpl::str() const -{ - Uuid printableHash(hash.get()); - stringstream str; - str << package << ":" << name << "(" << printableHash << ")"; - repr = str.str(); - return repr; -} - -SchemaObjectClassImpl::SchemaObjectClassImpl(Buffer& buffer) : hasHash(true), classKey(SchemaClassKeyImpl::factory(package, name, hash)) -{ - buffer.getShortString(package); - buffer.getShortString(name); - hash.decode(buffer); - - uint16_t propCount = buffer.getShort(); - uint16_t statCount = buffer.getShort(); - uint16_t methodCount = buffer.getShort(); - - for (uint16_t idx = 0; idx < propCount; idx++) { - const SchemaProperty* property = SchemaPropertyImpl::factory(buffer); - addProperty(property); - } - - for (uint16_t idx = 0; idx < statCount; idx++) { - const SchemaStatistic* statistic = SchemaStatisticImpl::factory(buffer); - addStatistic(statistic); - } - - for (uint16_t idx = 0; idx < methodCount; idx++) { - SchemaMethod* method = SchemaMethodImpl::factory(buffer); - addMethod(method); - } -} - -SchemaObjectClass* SchemaObjectClassImpl::factory(Buffer& buffer) -{ - SchemaObjectClassImpl* impl(new SchemaObjectClassImpl(buffer)); - return new SchemaObjectClass(impl); -} - -void SchemaObjectClassImpl::encode(Buffer& buffer) const -{ - buffer.putOctet((uint8_t) CLASS_OBJECT); - buffer.putShortString(package); - buffer.putShortString(name); - hash.encode(buffer); - //buffer.putOctet(0); // No parent class - buffer.putShort((uint16_t) properties.size()); - buffer.putShort((uint16_t) statistics.size()); - buffer.putShort((uint16_t) methods.size()); - - for (vector<const SchemaProperty*>::const_iterator iter = properties.begin(); - iter != properties.end(); iter++) - (*iter)->impl->encode(buffer); - for (vector<const SchemaStatistic*>::const_iterator iter = statistics.begin(); - iter != statistics.end(); iter++) - (*iter)->impl->encode(buffer); - for (vector<const SchemaMethod*>::const_iterator iter = methods.begin(); - iter != methods.end(); iter++) - (*iter)->impl->encode(buffer); -} - -const SchemaClassKey* SchemaObjectClassImpl::getClassKey() const -{ - if (!hasHash) { - hasHash = true; - hash.update(package); - hash.update(name); - for (vector<const SchemaProperty*>::const_iterator iter = properties.begin(); - iter != properties.end(); iter++) - (*iter)->impl->updateHash(hash); - for (vector<const SchemaStatistic*>::const_iterator iter = statistics.begin(); - iter != statistics.end(); iter++) - (*iter)->impl->updateHash(hash); - for (vector<const SchemaMethod*>::const_iterator iter = methods.begin(); - iter != methods.end(); iter++) - (*iter)->impl->updateHash(hash); - } - - return classKey.get(); -} - -void SchemaObjectClassImpl::addProperty(const SchemaProperty* property) -{ - properties.push_back(property); -} - -void SchemaObjectClassImpl::addStatistic(const SchemaStatistic* statistic) -{ - statistics.push_back(statistic); -} - -void SchemaObjectClassImpl::addMethod(const SchemaMethod* method) -{ - methods.push_back(method); -} - -const SchemaProperty* SchemaObjectClassImpl::getProperty(int idx) const -{ - int count = 0; - for (vector<const SchemaProperty*>::const_iterator iter = properties.begin(); - iter != properties.end(); iter++, count++) - if (idx == count) - return *iter; - return 0; -} - -const SchemaStatistic* SchemaObjectClassImpl::getStatistic(int idx) const -{ - int count = 0; - for (vector<const SchemaStatistic*>::const_iterator iter = statistics.begin(); - iter != statistics.end(); iter++, count++) - if (idx == count) - return *iter; - return 0; -} - -const SchemaMethod* SchemaObjectClassImpl::getMethod(int idx) const -{ - int count = 0; - for (vector<const SchemaMethod*>::const_iterator iter = methods.begin(); - iter != methods.end(); iter++, count++) - if (idx == count) - return *iter; - return 0; -} - -SchemaEventClassImpl::SchemaEventClassImpl(Buffer& buffer) : hasHash(true), classKey(SchemaClassKeyImpl::factory(package, name, hash)) -{ - buffer.getShortString(package); - buffer.getShortString(name); - hash.decode(buffer); - - uint16_t argCount = buffer.getShort(); - - for (uint16_t idx = 0; idx < argCount; idx++) { - SchemaArgument* argument = SchemaArgumentImpl::factory(buffer); - addArgument(argument); - } -} - -SchemaEventClass* SchemaEventClassImpl::factory(Buffer& buffer) -{ - SchemaEventClassImpl* impl(new SchemaEventClassImpl(buffer)); - return new SchemaEventClass(impl); -} - -void SchemaEventClassImpl::encode(Buffer& buffer) const -{ - buffer.putOctet((uint8_t) CLASS_EVENT); - buffer.putShortString(package); - buffer.putShortString(name); - hash.encode(buffer); - buffer.putShort((uint16_t) arguments.size()); - - for (vector<const SchemaArgument*>::const_iterator iter = arguments.begin(); - iter != arguments.end(); iter++) - (*iter)->impl->encode(buffer); -} - -const SchemaClassKey* SchemaEventClassImpl::getClassKey() const -{ - if (!hasHash) { - hasHash = true; - hash.update(package); - hash.update(name); - for (vector<const SchemaArgument*>::const_iterator iter = arguments.begin(); - iter != arguments.end(); iter++) - (*iter)->impl->updateHash(hash); - } - return classKey.get(); -} - -void SchemaEventClassImpl::addArgument(const SchemaArgument* argument) -{ - arguments.push_back(argument); -} - -const SchemaArgument* SchemaEventClassImpl::getArgument(int idx) const -{ - int count = 0; - for (vector<const SchemaArgument*>::const_iterator iter = arguments.begin(); - iter != arguments.end(); iter++, count++) - if (idx == count) - return (*iter); - return 0; -} - - -//================================================================== -// Wrappers -//================================================================== - -SchemaArgument::SchemaArgument(const char* name, Typecode typecode) { impl = new SchemaArgumentImpl(name, typecode); } -SchemaArgument::SchemaArgument(SchemaArgumentImpl* i) : impl(i) {} -SchemaArgument::SchemaArgument(const SchemaArgument& from) : impl(new SchemaArgumentImpl(*(from.impl))) {} -SchemaArgument::~SchemaArgument() { delete impl; } -void SchemaArgument::setDirection(Direction dir) { impl->setDirection(dir); } -void SchemaArgument::setUnit(const char* val) { impl->setUnit(val); } -void SchemaArgument::setDesc(const char* desc) { impl->setDesc(desc); } -const char* SchemaArgument::getName() const { return impl->getName().c_str(); } -Typecode SchemaArgument::getType() const { return impl->getType(); } -Direction SchemaArgument::getDirection() const { return impl->getDirection(); } -const char* SchemaArgument::getUnit() const { return impl->getUnit().c_str(); } -const char* SchemaArgument::getDesc() const { return impl->getDesc().c_str(); } - -SchemaMethod::SchemaMethod(const char* name) : impl(new SchemaMethodImpl(name)) {} -SchemaMethod::SchemaMethod(SchemaMethodImpl* i) : impl(i) {} -SchemaMethod::SchemaMethod(const SchemaMethod& from) : impl(new SchemaMethodImpl(*(from.impl))) {} -SchemaMethod::~SchemaMethod() { delete impl; } -void SchemaMethod::addArgument(const SchemaArgument* argument) { impl->addArgument(argument); } -void SchemaMethod::setDesc(const char* desc) { impl->setDesc(desc); } -const char* SchemaMethod::getName() const { return impl->getName().c_str(); } -const char* SchemaMethod::getDesc() const { return impl->getDesc().c_str(); } -int SchemaMethod::getArgumentCount() const { return impl->getArgumentCount(); } -const SchemaArgument* SchemaMethod::getArgument(int idx) const { return impl->getArgument(idx); } - -SchemaProperty::SchemaProperty(const char* name, Typecode typecode) : impl(new SchemaPropertyImpl(name, typecode)) {} -SchemaProperty::SchemaProperty(SchemaPropertyImpl* i) : impl(i) {} -SchemaProperty::SchemaProperty(const SchemaProperty& from) : impl(new SchemaPropertyImpl(*(from.impl))) {} -SchemaProperty::~SchemaProperty() { delete impl; } -void SchemaProperty::setAccess(Access access) { impl->setAccess(access); } -void SchemaProperty::setIndex(bool val) { impl->setIndex(val); } -void SchemaProperty::setOptional(bool val) { impl->setOptional(val); } -void SchemaProperty::setUnit(const char* val) { impl->setUnit(val); } -void SchemaProperty::setDesc(const char* desc) { impl->setDesc(desc); } -const char* SchemaProperty::getName() const { return impl->getName().c_str(); } -Typecode SchemaProperty::getType() const { return impl->getType(); } -Access SchemaProperty::getAccess() const { return impl->getAccess(); } -bool SchemaProperty::isIndex() const { return impl->isIndex(); } -bool SchemaProperty::isOptional() const { return impl->isOptional(); } -const char* SchemaProperty::getUnit() const { return impl->getUnit().c_str(); } -const char* SchemaProperty::getDesc() const { return impl->getDesc().c_str(); } - -SchemaStatistic::SchemaStatistic(const char* name, Typecode typecode) : impl(new SchemaStatisticImpl(name, typecode)) {} -SchemaStatistic::SchemaStatistic(SchemaStatisticImpl* i) : impl(i) {} -SchemaStatistic::SchemaStatistic(const SchemaStatistic& from) : impl(new SchemaStatisticImpl(*(from.impl))) {} -SchemaStatistic::~SchemaStatistic() { delete impl; } -void SchemaStatistic::setUnit(const char* val) { impl->setUnit(val); } -void SchemaStatistic::setDesc(const char* desc) { impl->setDesc(desc); } -const char* SchemaStatistic::getName() const { return impl->getName().c_str(); } -Typecode SchemaStatistic::getType() const { return impl->getType(); } -const char* SchemaStatistic::getUnit() const { return impl->getUnit().c_str(); } -const char* SchemaStatistic::getDesc() const { return impl->getDesc().c_str(); } - -SchemaClassKey::SchemaClassKey(SchemaClassKeyImpl* i) : impl(i) {} -SchemaClassKey::SchemaClassKey(const SchemaClassKey& from) : impl(new SchemaClassKeyImpl(*(from.impl))) {} -SchemaClassKey::~SchemaClassKey() { delete impl; } -const char* SchemaClassKey::getPackageName() const { return impl->getPackageName().c_str(); } -const char* SchemaClassKey::getClassName() const { return impl->getClassName().c_str(); } -const uint8_t* SchemaClassKey::getHash() const { return impl->getHash(); } -const char* SchemaClassKey::asString() const { return impl->str().c_str(); } -bool SchemaClassKey::operator==(const SchemaClassKey& other) const { return *impl == *(other.impl); } -bool SchemaClassKey::operator<(const SchemaClassKey& other) const { return *impl < *(other.impl); } - -SchemaObjectClass::SchemaObjectClass(const char* package, const char* name) : impl(new SchemaObjectClassImpl(package, name)) {} -SchemaObjectClass::SchemaObjectClass(SchemaObjectClassImpl* i) : impl(i) {} -SchemaObjectClass::SchemaObjectClass(const SchemaObjectClass& from) : impl(new SchemaObjectClassImpl(*(from.impl))) {} -SchemaObjectClass::~SchemaObjectClass() { delete impl; } -void SchemaObjectClass::addProperty(const SchemaProperty* property) { impl->addProperty(property); } -void SchemaObjectClass::addStatistic(const SchemaStatistic* statistic) { impl->addStatistic(statistic); } -void SchemaObjectClass::addMethod(const SchemaMethod* method) { impl->addMethod(method); } -const SchemaClassKey* SchemaObjectClass::getClassKey() const { return impl->getClassKey(); } -int SchemaObjectClass::getPropertyCount() const { return impl->getPropertyCount(); } -int SchemaObjectClass::getStatisticCount() const { return impl->getStatisticCount(); } -int SchemaObjectClass::getMethodCount() const { return impl->getMethodCount(); } -const SchemaProperty* SchemaObjectClass::getProperty(int idx) const { return impl->getProperty(idx); } -const SchemaStatistic* SchemaObjectClass::getStatistic(int idx) const { return impl->getStatistic(idx); } -const SchemaMethod* SchemaObjectClass::getMethod(int idx) const { return impl->getMethod(idx); } - -SchemaEventClass::SchemaEventClass(const char* package, const char* name, Severity s) : impl(new SchemaEventClassImpl(package, name, s)) {} -SchemaEventClass::SchemaEventClass(SchemaEventClassImpl* i) : impl(i) {} -SchemaEventClass::SchemaEventClass(const SchemaEventClass& from) : impl(new SchemaEventClassImpl(*(from.impl))) {} -SchemaEventClass::~SchemaEventClass() { delete impl; } -void SchemaEventClass::addArgument(const SchemaArgument* argument) { impl->addArgument(argument); } -void SchemaEventClass::setDesc(const char* desc) { impl->setDesc(desc); } -const SchemaClassKey* SchemaEventClass::getClassKey() const { return impl->getClassKey(); } -Severity SchemaEventClass::getSeverity() const { return impl->getSeverity(); } -int SchemaEventClass::getArgumentCount() const { return impl->getArgumentCount(); } -const SchemaArgument* SchemaEventClass::getArgument(int idx) const { return impl->getArgument(idx); } - diff --git a/cpp/src/qmf/engine/SchemaImpl.h b/cpp/src/qmf/engine/SchemaImpl.h deleted file mode 100644 index 8b079a5ec6..0000000000 --- a/cpp/src/qmf/engine/SchemaImpl.h +++ /dev/null @@ -1,227 +0,0 @@ -#ifndef _QmfEngineSchemaImpl_ -#define _QmfEngineSchemaImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/Schema.h" -#include "qpid/framing/Buffer.h" - -#include <string> -#include <vector> -#include <memory> - -namespace qmf { -namespace engine { - - // TODO: Destructors for schema classes - // TODO: Add "frozen" attribute for schema classes so they can't be modified after - // they've been registered. - - class SchemaHash { - uint8_t hash[16]; - public: - SchemaHash(); - void encode(qpid::framing::Buffer& buffer) const; - void decode(qpid::framing::Buffer& buffer); - void update(const char* data, uint32_t len); - void update(uint8_t data); - void update(const std::string& data) { update(data.c_str(), data.size()); } - void update(Typecode t) { update((uint8_t) t); } - void update(Direction d) { update((uint8_t) d); } - void update(Access a) { update((uint8_t) a); } - void update(bool b) { update((uint8_t) (b ? 1 : 0)); } - const uint8_t* get() const { return hash; } - bool operator==(const SchemaHash& other) const; - bool operator<(const SchemaHash& other) const; - bool operator>(const SchemaHash& other) const; - }; - - struct SchemaArgumentImpl { - std::string name; - Typecode typecode; - Direction dir; - std::string unit; - std::string description; - - SchemaArgumentImpl(const char* n, Typecode t) : name(n), typecode(t), dir(DIR_IN) {} - SchemaArgumentImpl(qpid::framing::Buffer& buffer); - static SchemaArgument* factory(qpid::framing::Buffer& buffer); - void encode(qpid::framing::Buffer& buffer) const; - void setDirection(Direction d) { dir = d; } - void setUnit(const char* val) { unit = val; } - void setDesc(const char* desc) { description = desc; } - const std::string& getName() const { return name; } - Typecode getType() const { return typecode; } - Direction getDirection() const { return dir; } - const std::string& getUnit() const { return unit; } - const std::string& getDesc() const { return description; } - void updateHash(SchemaHash& hash) const; - }; - - struct SchemaMethodImpl { - std::string name; - std::string description; - std::vector<const SchemaArgument*> arguments; - - SchemaMethodImpl(const char* n) : name(n) {} - SchemaMethodImpl(qpid::framing::Buffer& buffer); - static SchemaMethod* factory(qpid::framing::Buffer& buffer); - void encode(qpid::framing::Buffer& buffer) const; - void addArgument(const SchemaArgument* argument); - void setDesc(const char* desc) { description = desc; } - const std::string& getName() const { return name; } - const std::string& getDesc() const { return description; } - int getArgumentCount() const { return arguments.size(); } - const SchemaArgument* getArgument(int idx) const; - void updateHash(SchemaHash& hash) const; - }; - - struct SchemaPropertyImpl { - std::string name; - Typecode typecode; - Access access; - bool index; - bool optional; - std::string unit; - std::string description; - - SchemaPropertyImpl(const char* n, Typecode t) : name(n), typecode(t), access(ACCESS_READ_ONLY), index(false), optional(false) {} - SchemaPropertyImpl(qpid::framing::Buffer& buffer); - static SchemaProperty* factory(qpid::framing::Buffer& buffer); - void encode(qpid::framing::Buffer& buffer) const; - void setAccess(Access a) { access = a; } - void setIndex(bool val) { index = val; } - void setOptional(bool val) { optional = val; } - void setUnit(const char* val) { unit = val; } - void setDesc(const char* desc) { description = desc; } - const std::string& getName() const { return name; } - Typecode getType() const { return typecode; } - Access getAccess() const { return access; } - bool isIndex() const { return index; } - bool isOptional() const { return optional; } - const std::string& getUnit() const { return unit; } - const std::string& getDesc() const { return description; } - void updateHash(SchemaHash& hash) const; - }; - - struct SchemaStatisticImpl { - std::string name; - Typecode typecode; - std::string unit; - std::string description; - - SchemaStatisticImpl(const char* n, Typecode t) : name(n), typecode(t) {} - SchemaStatisticImpl(qpid::framing::Buffer& buffer); - static SchemaStatistic* factory(qpid::framing::Buffer& buffer); - void encode(qpid::framing::Buffer& buffer) const; - void setUnit(const char* val) { unit = val; } - void setDesc(const char* desc) { description = desc; } - const std::string& getName() const { return name; } - Typecode getType() const { return typecode; } - const std::string& getUnit() const { return unit; } - const std::string& getDesc() const { return description; } - void updateHash(SchemaHash& hash) const; - }; - - struct SchemaClassKeyImpl { - const std::string& package; - const std::string& name; - const SchemaHash& hash; - mutable std::string repr; - - // The *Container elements are only used if there isn't an external place to - // store these values. - std::string packageContainer; - std::string nameContainer; - SchemaHash hashContainer; - - SchemaClassKeyImpl(const std::string& package, const std::string& name, const SchemaHash& hash); - SchemaClassKeyImpl(qpid::framing::Buffer& buffer); - static SchemaClassKey* factory(const std::string& package, const std::string& name, const SchemaHash& hash); - static SchemaClassKey* factory(qpid::framing::Buffer& buffer); - - const std::string& getPackageName() const { return package; } - const std::string& getClassName() const { return name; } - const uint8_t* getHash() const { return hash.get(); } - - void encode(qpid::framing::Buffer& buffer) const; - bool operator==(const SchemaClassKeyImpl& other) const; - bool operator<(const SchemaClassKeyImpl& other) const; - const std::string& str() const; - }; - - struct SchemaObjectClassImpl { - std::string package; - std::string name; - mutable SchemaHash hash; - mutable bool hasHash; - std::auto_ptr<SchemaClassKey> classKey; - std::vector<const SchemaProperty*> properties; - std::vector<const SchemaStatistic*> statistics; - std::vector<const SchemaMethod*> methods; - - SchemaObjectClassImpl(const char* p, const char* n) : - package(p), name(n), hasHash(false), classKey(SchemaClassKeyImpl::factory(package, name, hash)) {} - SchemaObjectClassImpl(qpid::framing::Buffer& buffer); - static SchemaObjectClass* factory(qpid::framing::Buffer& buffer); - - void encode(qpid::framing::Buffer& buffer) const; - void addProperty(const SchemaProperty* property); - void addStatistic(const SchemaStatistic* statistic); - void addMethod(const SchemaMethod* method); - - const SchemaClassKey* getClassKey() const; - int getPropertyCount() const { return properties.size(); } - int getStatisticCount() const { return statistics.size(); } - int getMethodCount() const { return methods.size(); } - const SchemaProperty* getProperty(int idx) const; - const SchemaStatistic* getStatistic(int idx) const; - const SchemaMethod* getMethod(int idx) const; - }; - - struct SchemaEventClassImpl { - std::string package; - std::string name; - mutable SchemaHash hash; - mutable bool hasHash; - std::auto_ptr<SchemaClassKey> classKey; - std::string description; - Severity severity; - std::vector<const SchemaArgument*> arguments; - - SchemaEventClassImpl(const char* p, const char* n, Severity sev) : - package(p), name(n), hasHash(false), classKey(SchemaClassKeyImpl::factory(package, name, hash)), severity(sev) {} - SchemaEventClassImpl(qpid::framing::Buffer& buffer); - static SchemaEventClass* factory(qpid::framing::Buffer& buffer); - - void encode(qpid::framing::Buffer& buffer) const; - void addArgument(const SchemaArgument* argument); - void setDesc(const char* desc) { description = desc; } - - const SchemaClassKey* getClassKey() const; - Severity getSeverity() const { return severity; } - int getArgumentCount() const { return arguments.size(); } - const SchemaArgument* getArgument(int idx) const; - }; -} -} - -#endif - diff --git a/cpp/src/qmf/engine/SequenceManager.cpp b/cpp/src/qmf/engine/SequenceManager.cpp deleted file mode 100644 index 4a4644a8b9..0000000000 --- a/cpp/src/qmf/engine/SequenceManager.cpp +++ /dev/null @@ -1,96 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/SequenceManager.h" - -using namespace std; -using namespace qmf::engine; -using namespace qpid::sys; - -SequenceManager::SequenceManager() : nextSequence(1) {} - -void SequenceManager::setUnsolicitedContext(SequenceContext::Ptr ctx) -{ - unsolicitedContext = ctx; -} - -uint32_t SequenceManager::reserve(SequenceContext::Ptr ctx) -{ - Mutex::ScopedLock _lock(lock); - if (ctx.get() == 0) - ctx = unsolicitedContext; - uint32_t seq = nextSequence; - while (contextMap.find(seq) != contextMap.end()) - seq = seq < 0xFFFFFFFF ? seq + 1 : 1; - nextSequence = seq < 0xFFFFFFFF ? seq + 1 : 1; - contextMap[seq] = ctx; - ctx->reserve(); - return seq; -} - -void SequenceManager::release(uint32_t sequence) -{ - Mutex::ScopedLock _lock(lock); - - if (sequence == 0) { - if (unsolicitedContext.get() != 0) - unsolicitedContext->release(); - return; - } - - map<uint32_t, SequenceContext::Ptr>::iterator iter = contextMap.find(sequence); - if (iter != contextMap.end()) { - if (iter->second != 0) - iter->second->release(); - contextMap.erase(iter); - } -} - -void SequenceManager::releaseAll() -{ - Mutex::ScopedLock _lock(lock); - contextMap.clear(); -} - -void SequenceManager::dispatch(uint8_t opcode, uint32_t sequence, const string& routingKey, qpid::framing::Buffer& buffer) -{ - Mutex::ScopedLock _lock(lock); - bool done; - - if (sequence == 0) { - if (unsolicitedContext.get() != 0) { - done = unsolicitedContext->handleMessage(opcode, sequence, routingKey, buffer); - if (done) - unsolicitedContext->release(); - } - return; - } - - map<uint32_t, SequenceContext::Ptr>::iterator iter = contextMap.find(sequence); - if (iter != contextMap.end()) { - if (iter->second != 0) { - done = iter->second->handleMessage(opcode, sequence, routingKey, buffer); - if (done) { - iter->second->release(); - contextMap.erase(iter); - } - } - } -} - diff --git a/cpp/src/qmf/engine/SequenceManager.h b/cpp/src/qmf/engine/SequenceManager.h deleted file mode 100644 index 9e47e38610..0000000000 --- a/cpp/src/qmf/engine/SequenceManager.h +++ /dev/null @@ -1,68 +0,0 @@ -#ifndef _QmfEngineSequenceManager_ -#define _QmfEngineSequenceManager_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qpid/sys/Mutex.h" -#include <boost/shared_ptr.hpp> -#include <map> - -namespace qpid { - namespace framing { - class Buffer; - } -} - -namespace qmf { -namespace engine { - - class SequenceContext { - public: - typedef boost::shared_ptr<SequenceContext> Ptr; - SequenceContext() {} - virtual ~SequenceContext() {} - - virtual void reserve() = 0; - virtual bool handleMessage(uint8_t opcode, uint32_t sequence, const std::string& routingKey, qpid::framing::Buffer& buffer) = 0; - virtual void release() = 0; - }; - - class SequenceManager { - public: - SequenceManager(); - - void setUnsolicitedContext(SequenceContext::Ptr ctx); - uint32_t reserve(SequenceContext::Ptr ctx = SequenceContext::Ptr()); - void release(uint32_t sequence); - void releaseAll(); - void dispatch(uint8_t opcode, uint32_t sequence, const std::string& routingKey, qpid::framing::Buffer& buffer); - - private: - mutable qpid::sys::Mutex lock; - uint32_t nextSequence; - SequenceContext::Ptr unsolicitedContext; - std::map<uint32_t, SequenceContext::Ptr> contextMap; - }; - -} -} - -#endif - diff --git a/cpp/src/qmf/engine/ValueImpl.cpp b/cpp/src/qmf/engine/ValueImpl.cpp deleted file mode 100644 index f9ebbf5028..0000000000 --- a/cpp/src/qmf/engine/ValueImpl.cpp +++ /dev/null @@ -1,571 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include "qmf/engine/ValueImpl.h" -#include <qpid/framing/FieldValue.h> -#include <qpid/framing/FieldTable.h> -#include <qpid/framing/List.h> -#include <qpid/log/Statement.h> - -using namespace std; -using namespace qmf::engine; -//using qpid::framing::Buffer; -//using qpid::framing::FieldTable; -//using qpid::framing::FieldValue; -using namespace qpid::framing; - -ValueImpl::ValueImpl(Typecode t, Buffer& buf) : typecode(t) -{ - uint64_t first; - uint64_t second; - FieldTable ft; - List fl; - - switch (typecode) { - case TYPE_UINT8 : value.u32 = (uint32_t) buf.getOctet(); break; - case TYPE_UINT16 : value.u32 = (uint32_t) buf.getShort(); break; - case TYPE_UINT32 : value.u32 = (uint32_t) buf.getLong(); break; - case TYPE_UINT64 : value.u64 = buf.getLongLong(); break; - case TYPE_SSTR : buf.getShortString(stringVal); break; - case TYPE_LSTR : buf.getMediumString(stringVal); break; - case TYPE_ABSTIME : value.s64 = buf.getLongLong(); break; - case TYPE_DELTATIME : value.u64 = buf.getLongLong(); break; - case TYPE_BOOL : value.boolVal = (buf.getOctet() != 0); break; - case TYPE_FLOAT : value.floatVal = buf.getFloat(); break; - case TYPE_DOUBLE : value.doubleVal = buf.getDouble(); break; - case TYPE_INT8 : value.s32 = (int32_t) ((int8_t) buf.getOctet()); break; - case TYPE_INT16 : value.s32 = (int32_t) ((int16_t) buf.getShort()); break; - case TYPE_INT32 : value.s32 = (int32_t) buf.getLong(); break; - case TYPE_INT64 : value.s64 = buf.getLongLong(); break; - case TYPE_UUID : buf.getBin128(value.uuidVal); break; - case TYPE_REF: - first = buf.getLongLong(); - second = buf.getLongLong(); - refVal.impl->setValue(first, second); - break; - - case TYPE_MAP: - ft.decode(buf); - initMap(ft); - break; - - case TYPE_LIST: - fl.decode(buf); - initList(fl); - break; - - case TYPE_ARRAY: - case TYPE_OBJECT: - default: - break; - } -} - -ValueImpl::ValueImpl(Typecode t, Typecode at) : typecode(t), valid(false), arrayTypecode(at) -{ -} - -ValueImpl::ValueImpl(Typecode t) : typecode(t) -{ - ::memset(&value, 0, sizeof(value)); -} - -Value* ValueImpl::factory(Typecode t, Buffer& b) -{ - ValueImpl* impl(new ValueImpl(t, b)); - return new Value(impl); -} - -Value* ValueImpl::factory(Typecode t) -{ - ValueImpl* impl(new ValueImpl(t)); - return new Value(impl); -} - -ValueImpl::~ValueImpl() -{ -} - -void ValueImpl::initMap(const FieldTable& ft) -{ - for (FieldTable::ValueMap::const_iterator iter = ft.begin(); - iter != ft.end(); iter++) { - const string& name(iter->first); - const FieldValue& fvalue(*iter->second); - uint8_t amqType = fvalue.getType(); - - if (amqType == 0x32) { - Value* subval(new Value(TYPE_UINT64)); - subval->setUint64(fvalue.get<int64_t>()); - insert(name.c_str(), subval); - } else if ((amqType & 0xCF) == 0x02) { - Value* subval(new Value(TYPE_UINT32)); - switch (amqType) { - case 0x02 : subval->setUint(fvalue.get<int>()); break; - case 0x12 : subval->setUint(fvalue.get<int>()); break; - case 0x22 : subval->setUint(fvalue.get<int>()); break; - } - insert(name.c_str(), subval); - } else if (amqType == 0x31) { // int64 - Value* subval(new Value(TYPE_INT64)); - subval->setInt64(fvalue.get<int64_t>()); - insert(name.c_str(), subval); - } else if ((amqType & 0xCF) == 0x01) { // 0x01:int8, 0x11:int16, 0x21:int21 - Value* subval(new Value(TYPE_INT32)); - subval->setInt((int32_t)fvalue.get<int>()); - insert(name.c_str(), subval); - } else if (amqType == 0x85 || amqType == 0x95) { - Value* subval(new Value(TYPE_LSTR)); - subval->setString(fvalue.get<string>().c_str()); - insert(name.c_str(), subval); - } else if (amqType == 0x23 || amqType == 0x33) { - Value* subval(new Value(TYPE_DOUBLE)); - subval->setDouble(fvalue.get<double>()); - insert(name.c_str(), subval); - } else if (amqType == 0xa8) { - FieldTable subFt; - bool valid = qpid::framing::getEncodedValue<FieldTable>(iter->second, subFt); - if (valid) { - Value* subval(new Value(TYPE_MAP)); - subval->impl->initMap(subFt); - insert(name.c_str(), subval); - } - } else if (amqType == 0xa9) { - List subList; - bool valid = qpid::framing::getEncodedValue<List>(iter->second, subList); - if (valid) { - Value* subval(new Value(TYPE_LIST)); - subval->impl->initList(subList); - insert(name.c_str(), subval); - } - } else if (amqType == 0x08) { - Value* subval(new Value(TYPE_BOOL)); - subval->setBool(fvalue.get<int>() ? true : false); - insert(name.c_str(), subval); - } else { - QPID_LOG(error, "Unable to decode unsupported AMQP typecode=" << amqType << " map index=" << name); - } - } -} - -void ValueImpl::mapToFieldTable(FieldTable& ft) const -{ - FieldTable subFt; - - for (map<string, Value>::const_iterator iter = mapVal.begin(); - iter != mapVal.end(); iter++) { - const string& name(iter->first); - const Value& subval(iter->second); - - switch (subval.getType()) { - case TYPE_UINT8: - case TYPE_UINT16: - case TYPE_UINT32: - ft.setUInt64(name, (uint64_t) subval.asUint()); - break; - case TYPE_UINT64: - case TYPE_DELTATIME: - ft.setUInt64(name, subval.asUint64()); - break; - case TYPE_SSTR: - case TYPE_LSTR: - ft.setString(name, subval.asString()); - break; - case TYPE_INT64: - case TYPE_ABSTIME: - ft.setInt64(name, subval.asInt64()); - break; - case TYPE_BOOL: - ft.set(name, FieldTable::ValuePtr(new BoolValue(subval.asBool()))); - break; - case TYPE_FLOAT: - ft.setFloat(name, subval.asFloat()); - break; - case TYPE_DOUBLE: - ft.setDouble(name, subval.asDouble()); - break; - case TYPE_INT8: - case TYPE_INT16: - case TYPE_INT32: - ft.setInt(name, subval.asInt()); - break; - case TYPE_MAP: - subFt.clear(); - subval.impl->mapToFieldTable(subFt); - ft.setTable(name, subFt); - break; - case TYPE_LIST: - { - List subList; - subval.impl->listToFramingList(subList); - ft.set(name, - ::qpid::framing::FieldTable::ValuePtr( - new ListValue( - subList))); - } break; - case TYPE_ARRAY: - case TYPE_OBJECT: - case TYPE_UUID: - case TYPE_REF: - default: - break; - } - } - } - - -void ValueImpl::initList(const List& fl) -{ - for (List::const_iterator iter = fl.begin(); - iter != fl.end(); iter++) { - const FieldValue& fvalue(*iter->get()); - uint8_t amqType = fvalue.getType(); - - if (amqType == 0x32) { - Value* subval(new Value(TYPE_UINT64)); - subval->setUint64(fvalue.get<int64_t>()); - appendToList(subval); - } else if ((amqType & 0xCF) == 0x02) { - Value* subval(new Value(TYPE_UINT32)); - switch (amqType) { - case 0x02 : subval->setUint(fvalue.get<int>()); break; // uint8 - case 0x12 : subval->setUint(fvalue.get<int>()); break; // uint16 - case 0x22 : subval->setUint(fvalue.get<int>()); break; // uint32 - } - appendToList(subval); - } else if (amqType == 0x31) { // int64 - Value* subval(new Value(TYPE_INT64)); - subval->setInt64(fvalue.get<int64_t>()); - appendToList(subval); - } else if ((amqType & 0xCF) == 0x01) { // 0x01:int8, 0x11:int16, 0x21:int32 - Value* subval(new Value(TYPE_INT32)); - subval->setInt((int32_t)fvalue.get<int>()); - appendToList(subval); - } else if (amqType == 0x85 || amqType == 0x95) { - Value* subval(new Value(TYPE_LSTR)); - subval->setString(fvalue.get<string>().c_str()); - appendToList(subval); - } else if (amqType == 0x23 || amqType == 0x33) { - Value* subval(new Value(TYPE_DOUBLE)); - subval->setDouble(fvalue.get<double>()); - appendToList(subval); - } else if (amqType == 0xa8) { - FieldTable subFt; - bool valid = qpid::framing::getEncodedValue<FieldTable>(*iter, subFt); - if (valid) { - Value* subval(new Value(TYPE_MAP)); - subval->impl->initMap(subFt); - appendToList(subval); - } - } else if (amqType == 0xa9) { - List subList; - bool valid = qpid::framing::getEncodedValue<List>(*iter, subList); - if (valid) { - Value *subVal(new Value(TYPE_LIST)); - subVal->impl->initList(subList); - appendToList(subVal); - } - } else if (amqType == 0x08) { - Value* subval(new Value(TYPE_BOOL)); - subval->setBool(fvalue.get<int>() ? true : false); - appendToList(subval); - } else { - QPID_LOG(error, "Unable to decode unsupported AMQP typecode =" << amqType); - } - } -} - -void ValueImpl::listToFramingList(List& fl) const -{ - for (vector<Value>::const_iterator iter = vectorVal.begin(); - iter != vectorVal.end(); iter++) { - const Value& subval(*iter); - - switch (subval.getType()) { - case TYPE_UINT8: - case TYPE_UINT16: - case TYPE_UINT32: - fl.push_back(List::ValuePtr(new Unsigned64Value((uint64_t) subval.asUint()))); - break; - case TYPE_UINT64: - case TYPE_DELTATIME: - fl.push_back(List::ValuePtr(new Unsigned64Value(subval.asUint64()))); - break; - case TYPE_SSTR: - case TYPE_LSTR: - fl.push_back(List::ValuePtr(new Str16Value(subval.asString()))); - break; - case TYPE_INT64: - case TYPE_ABSTIME: - fl.push_back(List::ValuePtr(new Integer64Value(subval.asInt64()))); - break; - case TYPE_BOOL: - fl.push_back(List::ValuePtr(new BoolValue(subval.asBool() ? 1 : 0))); - break; - case TYPE_FLOAT: - fl.push_back(List::ValuePtr(new FloatValue(subval.asFloat()))); - break; - case TYPE_DOUBLE: - fl.push_back(List::ValuePtr(new DoubleValue(subval.asDouble()))); - break; - case TYPE_INT8: - case TYPE_INT16: - case TYPE_INT32: - fl.push_back(List::ValuePtr(new IntegerValue(subval.asInt()))); - break; - case TYPE_MAP: - { - FieldTable subFt; - subval.impl->mapToFieldTable(subFt); - fl.push_back(List::ValuePtr(new FieldTableValue(subFt))); - - } break; - case TYPE_LIST: - { - List subList; - subval.impl->listToFramingList(subList); - fl.push_back(List::ValuePtr(new ListValue(subList))); - } break; - - case TYPE_ARRAY: - case TYPE_OBJECT: - case TYPE_UUID: - case TYPE_REF: - default: - break; - } - } - } - - - -void ValueImpl::encode(Buffer& buf) const -{ - FieldTable ft; - List fl; - - switch (typecode) { - case TYPE_UINT8 : buf.putOctet((uint8_t) value.u32); break; - case TYPE_UINT16 : buf.putShort((uint16_t) value.u32); break; - case TYPE_UINT32 : buf.putLong(value.u32); break; - case TYPE_UINT64 : buf.putLongLong(value.u64); break; - case TYPE_SSTR : buf.putShortString(stringVal); break; - case TYPE_LSTR : buf.putMediumString(stringVal); break; - case TYPE_ABSTIME : buf.putLongLong(value.s64); break; - case TYPE_DELTATIME : buf.putLongLong(value.u64); break; - case TYPE_BOOL : buf.putOctet(value.boolVal ? 1 : 0); break; - case TYPE_FLOAT : buf.putFloat(value.floatVal); break; - case TYPE_DOUBLE : buf.putDouble(value.doubleVal); break; - case TYPE_INT8 : buf.putOctet((uint8_t) value.s32); break; - case TYPE_INT16 : buf.putShort((uint16_t) value.s32); break; - case TYPE_INT32 : buf.putLong(value.s32); break; - case TYPE_INT64 : buf.putLongLong(value.s64); break; - case TYPE_UUID : buf.putBin128(value.uuidVal); break; - case TYPE_REF : refVal.impl->encode(buf); break; - case TYPE_MAP: - mapToFieldTable(ft); - ft.encode(buf); - break; - case TYPE_LIST: - listToFramingList(fl); - fl.encode(buf); - break; - - case TYPE_ARRAY: - case TYPE_OBJECT: - default: - break; - } -} - -uint32_t ValueImpl::encodedSize() const -{ - FieldTable ft; - List fl; - - switch (typecode) { - case TYPE_UINT8 : - case TYPE_BOOL : - case TYPE_INT8 : return 1; - - case TYPE_UINT16 : - case TYPE_INT16 : return 2; - - case TYPE_UINT32 : - case TYPE_INT32 : - case TYPE_FLOAT : return 4; - - case TYPE_UINT64 : - case TYPE_INT64 : - case TYPE_DOUBLE : - case TYPE_ABSTIME : - case TYPE_DELTATIME : return 8; - - case TYPE_UUID : - case TYPE_REF : return 16; - - case TYPE_SSTR : return 1 + stringVal.size(); - case TYPE_LSTR : return 2 + stringVal.size(); - case TYPE_MAP: - mapToFieldTable(ft); - return ft.encodedSize(); - - case TYPE_LIST: - listToFramingList(fl); - return fl.encodedSize(); - - case TYPE_ARRAY: - case TYPE_OBJECT: - default: - break; - } - - return 0; -} - -bool ValueImpl::keyInMap(const char* key) const -{ - return typecode == TYPE_MAP && mapVal.count(key) > 0; -} - -Value* ValueImpl::byKey(const char* key) -{ - if (keyInMap(key)) { - map<string, Value>::iterator iter = mapVal.find(key); - if (iter != mapVal.end()) - return &iter->second; - } - return 0; -} - -const Value* ValueImpl::byKey(const char* key) const -{ - if (keyInMap(key)) { - map<string, Value>::const_iterator iter = mapVal.find(key); - if (iter != mapVal.end()) - return &iter->second; - } - return 0; -} - -void ValueImpl::deleteKey(const char* key) -{ - mapVal.erase(key); -} - -void ValueImpl::insert(const char* key, Value* val) -{ - pair<string, Value> entry(key, *val); - mapVal.insert(entry); -} - -const char* ValueImpl::key(uint32_t idx) const -{ - map<string, Value>::const_iterator iter = mapVal.begin(); - for (uint32_t i = 0; i < idx; i++) { - if (iter == mapVal.end()) - break; - iter++; - } - - if (iter == mapVal.end()) - return 0; - else - return iter->first.c_str(); -} - -Value* ValueImpl::arrayItem(uint32_t) -{ - return 0; -} - -void ValueImpl::appendToArray(Value*) -{ -} - -void ValueImpl::deleteArrayItem(uint32_t) -{ -} - - -//================================================================== -// Wrappers -//================================================================== - -Value::Value(const Value& from) : impl(new ValueImpl(*(from.impl))) {} -Value::Value(Typecode t, Typecode at) : impl(new ValueImpl(t, at)) {} -Value::Value(ValueImpl* i) : impl(i) {} -Value::~Value() { delete impl;} - -Typecode Value::getType() const { return impl->getType(); } -bool Value::isNull() const { return impl->isNull(); } -void Value::setNull() { impl->setNull(); } -bool Value::isObjectId() const { return impl->isObjectId(); } -const ObjectId& Value::asObjectId() const { return impl->asObjectId(); } -void Value::setObjectId(const ObjectId& oid) { impl->setObjectId(oid); } -bool Value::isUint() const { return impl->isUint(); } -uint32_t Value::asUint() const { return impl->asUint(); } -void Value::setUint(uint32_t val) { impl->setUint(val); } -bool Value::isInt() const { return impl->isInt(); } -int32_t Value::asInt() const { return impl->asInt(); } -void Value::setInt(int32_t val) { impl->setInt(val); } -bool Value::isUint64() const { return impl->isUint64(); } -uint64_t Value::asUint64() const { return impl->asUint64(); } -void Value::setUint64(uint64_t val) { impl->setUint64(val); } -bool Value::isInt64() const { return impl->isInt64(); } -int64_t Value::asInt64() const { return impl->asInt64(); } -void Value::setInt64(int64_t val) { impl->setInt64(val); } -bool Value::isString() const { return impl->isString(); } -const char* Value::asString() const { return impl->asString(); } -void Value::setString(const char* val) { impl->setString(val); } -bool Value::isBool() const { return impl->isBool(); } -bool Value::asBool() const { return impl->asBool(); } -void Value::setBool(bool val) { impl->setBool(val); } -bool Value::isFloat() const { return impl->isFloat(); } -float Value::asFloat() const { return impl->asFloat(); } -void Value::setFloat(float val) { impl->setFloat(val); } -bool Value::isDouble() const { return impl->isDouble(); } -double Value::asDouble() const { return impl->asDouble(); } -void Value::setDouble(double val) { impl->setDouble(val); } -bool Value::isUuid() const { return impl->isUuid(); } -const uint8_t* Value::asUuid() const { return impl->asUuid(); } -void Value::setUuid(const uint8_t* val) { impl->setUuid(val); } -bool Value::isObject() const { return impl->isObject(); } -const Object* Value::asObject() const { return impl->asObject(); } -void Value::setObject(Object* val) { impl->setObject(val); } -bool Value::isMap() const { return impl->isMap(); } -bool Value::keyInMap(const char* key) const { return impl->keyInMap(key); } -Value* Value::byKey(const char* key) { return impl->byKey(key); } -const Value* Value::byKey(const char* key) const { return impl->byKey(key); } -void Value::deleteKey(const char* key) { impl->deleteKey(key); } -void Value::insert(const char* key, Value* val) { impl->insert(key, val); } -uint32_t Value::keyCount() const { return impl->keyCount(); } -const char* Value::key(uint32_t idx) const { return impl->key(idx); } -bool Value::isList() const { return impl->isList(); } -uint32_t Value::listItemCount() const { return impl->listItemCount(); } -Value* Value::listItem(uint32_t idx) { return impl->listItem(idx); } -void Value::appendToList(Value* val) { impl->appendToList(val); } -void Value::deleteListItem(uint32_t idx) { impl->deleteListItem(idx); } -bool Value::isArray() const { return impl->isArray(); } -Typecode Value::arrayType() const { return impl->arrayType(); } -uint32_t Value::arrayItemCount() const { return impl->arrayItemCount(); } -Value* Value::arrayItem(uint32_t idx) { return impl->arrayItem(idx); } -void Value::appendToArray(Value* val) { impl->appendToArray(val); } -void Value::deleteArrayItem(uint32_t idx) { impl->deleteArrayItem(idx); } - diff --git a/cpp/src/qmf/engine/ValueImpl.h b/cpp/src/qmf/engine/ValueImpl.h deleted file mode 100644 index 8de8c5329f..0000000000 --- a/cpp/src/qmf/engine/ValueImpl.h +++ /dev/null @@ -1,166 +0,0 @@ -#ifndef _QmfEngineValueImpl_ -#define _QmfEngineValueImpl_ - -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ - -#include <qmf/engine/Value.h> -#include <qmf/engine/ObjectIdImpl.h> -#include <qmf/engine/Object.h> -#include <qpid/framing/Buffer.h> -#include <string> -#include <string.h> -#include <map> -#include <vector> -#include <boost/shared_ptr.hpp> - -namespace qpid { -namespace framing { - class FieldTable; - class List; -} -} - -namespace qmf { -namespace engine { - - // TODO: set valid flag on all value settors - // TODO: add a modified flag and accessors - - struct ValueImpl { - const Typecode typecode; - bool valid; - - ObjectId refVal; - std::string stringVal; - std::auto_ptr<Object> objectVal; - std::map<std::string, Value> mapVal; - std::vector<Value> vectorVal; - Typecode arrayTypecode; - - union { - uint32_t u32; - uint64_t u64; - int32_t s32; - int64_t s64; - bool boolVal; - float floatVal; - double doubleVal; - uint8_t uuidVal[16]; - } value; - - ValueImpl(const ValueImpl& from) : - typecode(from.typecode), valid(from.valid), refVal(from.refVal), stringVal(from.stringVal), - objectVal(from.objectVal.get() ? new Object(*(from.objectVal)) : 0), - mapVal(from.mapVal), vectorVal(from.vectorVal), arrayTypecode(from.arrayTypecode), - value(from.value) {} - - ValueImpl(Typecode t, Typecode at); - ValueImpl(Typecode t, qpid::framing::Buffer& b); - ValueImpl(Typecode t); - static Value* factory(Typecode t, qpid::framing::Buffer& b); - static Value* factory(Typecode t); - ~ValueImpl(); - - void encode(qpid::framing::Buffer& b) const; - uint32_t encodedSize() const; - - Typecode getType() const { return typecode; } - bool isNull() const { return !valid; } - void setNull() { valid = false; } - - bool isObjectId() const { return typecode == TYPE_REF; } - const ObjectId& asObjectId() const { return refVal; } - void setObjectId(const ObjectId& o) { refVal = o; } // TODO - - bool isUint() const { return typecode >= TYPE_UINT8 && typecode <= TYPE_UINT32; } - uint32_t asUint() const { return value.u32; } - void setUint(uint32_t val) { value.u32 = val; } - - bool isInt() const { return typecode >= TYPE_INT8 && typecode <= TYPE_INT32; } - int32_t asInt() const { return value.s32; } - void setInt(int32_t val) { value.s32 = val; } - - bool isUint64() const { return typecode == TYPE_UINT64 || typecode == TYPE_DELTATIME; } - uint64_t asUint64() const { return value.u64; } - void setUint64(uint64_t val) { value.u64 = val; } - - bool isInt64() const { return typecode == TYPE_INT64 || typecode == TYPE_ABSTIME; } - int64_t asInt64() const { return value.s64; } - void setInt64(int64_t val) { value.s64 = val; } - - bool isString() const { return typecode == TYPE_SSTR || typecode == TYPE_LSTR; } - const char* asString() const { return stringVal.c_str(); } - void setString(const char* val) { stringVal = val; } - - bool isBool() const { return typecode == TYPE_BOOL; } - bool asBool() const { return value.boolVal; } - void setBool(bool val) { value.boolVal = val; } - - bool isFloat() const { return typecode == TYPE_FLOAT; } - float asFloat() const { return value.floatVal; } - void setFloat(float val) { value.floatVal = val; } - - bool isDouble() const { return typecode == TYPE_DOUBLE; } - double asDouble() const { return value.doubleVal; } - void setDouble(double val) { value.doubleVal = val; } - - bool isUuid() const { return typecode == TYPE_UUID; } - const uint8_t* asUuid() const { return value.uuidVal; } - void setUuid(const uint8_t* val) { ::memcpy(value.uuidVal, val, 16); } - - bool isObject() const { return typecode == TYPE_OBJECT; } - Object* asObject() const { return objectVal.get(); } - void setObject(Object* val) { objectVal.reset(val); } - - bool isMap() const { return typecode == TYPE_MAP; } - bool keyInMap(const char* key) const; - Value* byKey(const char* key); - const Value* byKey(const char* key) const; - void deleteKey(const char* key); - void insert(const char* key, Value* val); - uint32_t keyCount() const { return mapVal.size(); } - const char* key(uint32_t idx) const; - - bool isList() const { return typecode == TYPE_LIST; } - uint32_t listItemCount() const { return vectorVal.size(); } - Value* listItem(uint32_t idx) { return idx < listItemCount() ? &vectorVal[idx] : 0; } - const Value* listItem(uint32_t idx) const { return idx < listItemCount() ? &vectorVal[idx] : 0; } - void appendToList(Value* val) { vectorVal.push_back(*val); } - void deleteListItem(uint32_t idx) { if (idx < listItemCount()) vectorVal.erase(vectorVal.begin()+idx); } - - bool isArray() const { return typecode == TYPE_ARRAY; } - Typecode arrayType() const { return arrayTypecode; } - uint32_t arrayItemCount() const { return 0; } - Value* arrayItem(uint32_t idx); - void appendToArray(Value* val); - void deleteArrayItem(uint32_t idx); - - private: - void mapToFieldTable(qpid::framing::FieldTable& ft) const; - void initMap(const qpid::framing::FieldTable& ft); - - void listToFramingList(qpid::framing::List& fl) const; - void initList(const qpid::framing::List& fl); - }; -} -} - -#endif - diff --git a/cpp/src/qmf/exceptions.cpp b/cpp/src/qmf/exceptions.cpp deleted file mode 100644 index be212f62f7..0000000000 --- a/cpp/src/qmf/exceptions.cpp +++ /dev/null @@ -1,37 +0,0 @@ -/* - * - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - * - */ -#include "qmf/exceptions.h" - -namespace qmf { - - QmfException::QmfException(const std::string& msg) : qpid::types::Exception(msg) {} - QmfException::~QmfException() throw() {} - - KeyNotFound::KeyNotFound(const std::string& msg) : QmfException("Key Not Found: " + msg) {} - KeyNotFound::~KeyNotFound() throw() {} - - IndexOutOfRange::IndexOutOfRange() : QmfException("Index out-of-range") {} - IndexOutOfRange::~IndexOutOfRange() throw() {} - - OperationTimedOut::OperationTimedOut() : QmfException("Timeout Expired") {} - OperationTimedOut::~OperationTimedOut() throw() {} -} - |