Commit 3a1ed77c authored by tim@chromium.org's avatar tim@chromium.org

mojo: fail gracefully if ServiceRegistry can't find ServiceConnector

Previously, the newly added test would crash because the ServiceRegistry asserted it had a ServiceConnector for anything allowed through by AllowIncomingConnection.  Nothing actually prevents this from happening, so this patch makes sure it is handled gracefully by placing the InterfacePtr into an error state.

BUG=None

Review URL: https://codereview.chromium.org/343473005

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@278240 0039d316-1c4b-4281-b951-d872f2087c98
parent 21a25bab
......@@ -58,7 +58,9 @@ void ServiceRegistry::ConnectToService(const mojo::String& service_url,
const mojo::String& service_name,
ScopedMessagePipeHandle client_handle,
const mojo::String& requestor_url) {
if (!application_->AllowIncomingConnection(service_name, requestor_url)) {
if (name_to_service_connector_.find(service_name) ==
name_to_service_connector_.end() ||
!application_->AllowIncomingConnection(service_name, requestor_url)) {
client_handle.reset();
return;
}
......
......@@ -25,6 +25,20 @@ struct TestContext {
int num_loader_deletes;
};
class QuitMessageLoopErrorHandler : public ErrorHandler {
public:
QuitMessageLoopErrorHandler() {}
virtual ~QuitMessageLoopErrorHandler() {}
// |ErrorHandler| implementation:
virtual void OnConnectionError() OVERRIDE {
base::MessageLoop::current()->QuitWhenIdle();
}
private:
DISALLOW_COPY_AND_ASSIGN(QuitMessageLoopErrorHandler);
};
class TestServiceImpl : public InterfaceImpl<TestService> {
public:
explicit TestServiceImpl(TestContext* context) : context_(context) {
......@@ -114,7 +128,7 @@ class TestServiceLoader : public ServiceLoader {
// Used to test that the requestor url will be correctly passed.
class TestAImpl : public InterfaceImpl<TestA> {
public:
TestAImpl(Application* app) : app_(app) {}
explicit TestAImpl(Application* app) : app_(app) {}
virtual void LoadB() OVERRIDE {
TestBPtr b;
......@@ -135,7 +149,7 @@ class TestBImpl : public InterfaceImpl<TestB> {
class TestApp : public Application, public ServiceLoader {
public:
TestApp(std::string requestor_url)
explicit TestApp(std::string requestor_url)
: requestor_url_(requestor_url),
num_connects_(0) {
}
......@@ -354,6 +368,26 @@ TEST_F(ServiceManagerTest, ANoLoadB) {
EXPECT_EQ(0, b_app->num_connects());
}
TEST_F(ServiceManagerTest, NoServiceNoLoad) {
ServiceManager sm;
TestApp* b_app = new TestApp(std::string());
b_app->AddService<TestBImpl>();
sm.SetLoaderForURL(scoped_ptr<ServiceLoader>(b_app), GURL(kTestBURLString));
// There is no TestA service implementation registered with ServiceManager,
// so this cannot succeed (but also shouldn't crash).
TestAPtr a;
sm.ConnectTo(GURL(kTestBURLString), &a, GURL());
QuitMessageLoopErrorHandler quitter;
a.set_error_handler(&quitter);
a->LoadB();
loop_.Run();
EXPECT_TRUE(a.encountered_error());
EXPECT_EQ(0, b_app->num_connects());
}
TEST_F(ServiceManagerTest, Interceptor) {
ServiceManager sm;
TestServiceInterceptor interceptor;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment