summaryrefslogtreecommitdiff
path: root/cpp/src/IceBT
diff options
context:
space:
mode:
authorMark Spruiell <mes@zeroc.com>2015-11-20 14:53:32 -0800
committerMark Spruiell <mes@zeroc.com>2015-11-20 14:53:32 -0800
commit3d0f671afa1645ab51e265b5fc0cf404f02fdccf (patch)
tree872349d3737066cc6c96b1155c39cd90a139f842 /cpp/src/IceBT
parentinitial BlueZ 4 implementation (diff)
downloadice-3d0f671afa1645ab51e265b5fc0cf404f02fdccf.tar.bz2
ice-3d0f671afa1645ab51e265b5fc0cf404f02fdccf.tar.xz
ice-3d0f671afa1645ab51e265b5fc0cf404f02fdccf.zip
BT fixes
Diffstat (limited to 'cpp/src/IceBT')
-rw-r--r--cpp/src/IceBT/EndpointI.cpp34
-rw-r--r--cpp/src/IceBT/EndpointI.h12
-rw-r--r--cpp/src/IceBT/Engine.cpp21
-rw-r--r--cpp/src/IceBT/Engine.h2
-rw-r--r--cpp/src/IceBT/TransceiverI.cpp3
5 files changed, 54 insertions, 18 deletions
diff --git a/cpp/src/IceBT/EndpointI.cpp b/cpp/src/IceBT/EndpointI.cpp
index 41fa5e579bd..bf1608a28e7 100644
--- a/cpp/src/IceBT/EndpointI.cpp
+++ b/cpp/src/IceBT/EndpointI.cpp
@@ -21,6 +21,7 @@
#include <Ice/Logger.h>
#include <Ice/Object.h>
#include <Ice/Properties.h>
+#include <IceUtil/Random.h>
#include <IceUtil/StringUtil.h>
using namespace std;
@@ -29,6 +30,19 @@ using namespace IceBT;
IceUtil::Shared* IceBT::upCast(EndpointI* p) { return p; }
+namespace
+{
+
+struct RandomNumberGenerator : public std::unary_function<ptrdiff_t, ptrdiff_t>
+{
+ ptrdiff_t operator()(ptrdiff_t d)
+ {
+ return IceUtilInternal::random(static_cast<int>(d));
+ }
+};
+
+}
+
IceBT::EndpointI::EndpointI(const InstancePtr& instance, const string& addr, const string& uuid, const string& name,
Int channel, Int timeout, const string& connectionId, bool compress) :
_instance(instance),
@@ -175,7 +189,7 @@ IceBT::EndpointI::transceiver() const
}
void
-IceBT::EndpointI::connectors_async(EndpointSelectionType, const IceInternal::EndpointI_connectorsPtr& cb) const
+IceBT::EndpointI::connectors_async(EndpointSelectionType selType, const IceInternal::EndpointI_connectorsPtr& cb) const
{
IceUtil::Monitor<IceUtil::Mutex>::Lock lock(_lock);
@@ -189,7 +203,7 @@ IceBT::EndpointI::connectors_async(EndpointSelectionType, const IceInternal::End
ostr << "searching for service " << _uuid << " at " << _addr;
_instance->logger()->trace(_instance->traceCategory(), ostr.str());
}
- _instance->engine()->findService(_addr, _uuid, new FindCallbackI(const_cast<EndpointI*>(this)));
+ _instance->engine()->findService(_addr, _uuid, new FindCallbackI(const_cast<EndpointI*>(this), selType));
}
const_cast<vector<IceInternal::EndpointI_connectorsPtr>&>(_callbacks).push_back(cb);
@@ -603,11 +617,21 @@ IceBT::EndpointI::checkOption(const string& option, const string& argument, cons
}
void
-IceBT::EndpointI::findCompleted(int channel)
+IceBT::EndpointI::findCompleted(const vector<int>& channels, EndpointSelectionType selType)
{
+ assert(!channels.empty());
+
vector<IceInternal::ConnectorPtr> connectors;
- assert(channel >= 0);
- connectors.push_back(new ConnectorI(_instance, createAddr(_addr, channel), _uuid, _timeout, _connectionId));
+ for(vector<int>::const_iterator p = channels.begin(); p != channels.end(); ++p)
+ {
+ connectors.push_back(new ConnectorI(_instance, createAddr(_addr, *p), _uuid, _timeout, _connectionId));
+ }
+
+ if(selType == Ice::Random && connectors.size() > 1)
+ {
+ RandomNumberGenerator rng;
+ random_shuffle(connectors.begin(), connectors.end(), rng);
+ }
vector<IceInternal::EndpointI_connectorsPtr> callbacks;
diff --git a/cpp/src/IceBT/EndpointI.h b/cpp/src/IceBT/EndpointI.h
index 7d895812df3..d26bdb04a98 100644
--- a/cpp/src/IceBT/EndpointI.h
+++ b/cpp/src/IceBT/EndpointI.h
@@ -65,21 +65,22 @@ private:
void hashInit();
bool checkOption(const std::string&, const std::string&, const std::string&);
- void findCompleted(int);
+ void findCompleted(const std::vector<int>&, Ice::EndpointSelectionType);
void findException(const Ice::LocalException&);
class FindCallbackI : public FindServiceCallback
{
public:
- FindCallbackI(const EndpointIPtr& e) :
- _endpoint(e)
+ FindCallbackI(const EndpointIPtr& e, Ice::EndpointSelectionType selType) :
+ _endpoint(e),
+ _selType(selType)
{
}
- virtual void completed(int channel)
+ virtual void completed(const std::vector<int>& channels)
{
- _endpoint->findCompleted(channel);
+ _endpoint->findCompleted(channels, _selType);
}
virtual void exception(const Ice::LocalException& ex)
@@ -88,6 +89,7 @@ private:
}
EndpointIPtr _endpoint;
+ Ice::EndpointSelectionType _selType;
};
friend class FindCallbackI;
diff --git a/cpp/src/IceBT/Engine.cpp b/cpp/src/IceBT/Engine.cpp
index 878deec1f73..46e67f47016 100644
--- a/cpp/src/IceBT/Engine.cpp
+++ b/cpp/src/IceBT/Engine.cpp
@@ -544,7 +544,8 @@ public:
void runFindService(const IceUtil::ThreadPtr& thread, const string& addr, const string& uuid,
const FindServiceCallbackPtr& cb)
{
- int channel = -1;
+ vector<int> channels;
+ bool failed = false;
try
{
@@ -724,9 +725,10 @@ public:
if(ch)
{
string val = ch->getAttribute("value");
+ int channel;
if(sscanf(val.c_str(), "%x", &channel) == 1)
{
- break;
+ channels.push_back(channel);
}
}
}
@@ -770,23 +772,34 @@ public:
catch(const DBus::Exception& ex)
{
cb->exception(BluetoothException(__FILE__, __LINE__, ex.reason));
+ failed = true;
}
catch(const LocalException& ex)
{
cb->exception(ex);
+ failed = true;
}
catch(const std::exception& ex)
{
cb->exception(UnknownException(__FILE__, __LINE__, ex.what()));
+ failed = true;
}
catch(...)
{
cb->exception(UnknownException(__FILE__, __LINE__, "unknown C++ exception"));
+ failed = true;
}
- if(channel != -1)
+ if(!failed)
{
- cb->completed(channel);
+ if(channels.empty())
+ {
+ cb->exception(BluetoothException(__FILE__, __LINE__, "no service found for " + uuid + " at " + addr));
+ }
+ else
+ {
+ cb->completed(channels);
+ }
}
{
diff --git a/cpp/src/IceBT/Engine.h b/cpp/src/IceBT/Engine.h
index fe2aba60a7d..8c557f42dbb 100644
--- a/cpp/src/IceBT/Engine.h
+++ b/cpp/src/IceBT/Engine.h
@@ -23,7 +23,7 @@ class FindServiceCallback : public IceUtil::Shared
{
public:
- virtual void completed(int) = 0;
+ virtual void completed(const std::vector<int>&) = 0;
virtual void exception(const Ice::LocalException&) = 0;
};
typedef IceUtil::Handle<FindServiceCallback> FindServiceCallbackPtr;
diff --git a/cpp/src/IceBT/TransceiverI.cpp b/cpp/src/IceBT/TransceiverI.cpp
index c81791c3799..f4d06cf33ba 100644
--- a/cpp/src/IceBT/TransceiverI.cpp
+++ b/cpp/src/IceBT/TransceiverI.cpp
@@ -37,9 +37,6 @@ IceBT::TransceiverI::initialize(IceInternal::Buffer& readBuffer, IceInternal::Bu
IceInternal::SocketOperation
IceBT::TransceiverI::closing(bool initiator, const Ice::LocalException&)
{
- //
- // Bluetooth sockets seem to need this in order to shut down in a timely fashion.
- //
::shutdown(_stream->fd(), SHUT_RDWR);
//