Thanks Michał,
I did consider that briefly, but then I realised there was no way to
determine through equality what constraints had been applied and if
unsure, the developer can apply constraints again.
It's a much bigger advantage to have equals working as expected.
Existing service utilities such as SDM apply the constraints for users,
who can set them in their configuration.
Regards,
Peter.
On 6/6/2020 3:08 AM, Kłeczek, Michał wrote:
Hi Peter,
I think we need to be careful here - basically the semantics should be:
MyServiceProxy originalProxy = ...
MethodConstraints localClientConstraints = ...
// THIS IS IMPORTANT!!!
((RemoteMethodControl)originalProxy).setConstraints(localClientConstraints).equals(originalProxy)
== false
If you break this contract the client might be vulnerable because it
could easily confuse constrained and unconstrained proxies.
The solution is to have two objects with different identities:
- the proxy
- service identity (not to be confused with Registrar ServiceID)
The identity of the service could only be verified using service
identity object:
// hypotthetical API
((RemoteMethodControl)originalProxy).getServiceIdentity().equals(((RemoteMethodControl)originalProxy).setConstraints(localClientConstraints).getServiceIdentity())
== true
My 2 cents :)
Thanks,
Michal
On 26/05/2020 10:10:50, "Peter Firmstone"
wrote:
Hello River folk.
As you are probably aware, I have an interest in security and have
been focused on simplifying the use of secure services.
In JGDMS the qa suite runs in jsse mode, which means the majority of
tests are run with a login Subject and services use SSL/TLS Endpoints.
A number of tests that passed with non secure Endpoint's failed with
SSL/TLS Endpoints. Activation also failed, like the failing tests, it
made assumptions on proxy identity.
One of the problems I faced was proxy identity is defined by the
underlying InvocationHandler's equals method, namely that of
BasicObjectEndpoint.
BasicObjectEndpoint was including the client's MethodConstraints in
the Proxy's identity.
This meant the service proxy's identity changed after the client
applied constraints, and as a result, the tests weren't passing
because the proxy's identity wasn't as expected. Also Activation
would fail as the ActivationID would be different.
A code comment in placed in ActivatableInvocationHandler:activate0()
method, for working around this issue.
/* Equality of ActivationID instances are influenced by the
* equality of their Activator proxy's InvocationHandler,
* when client constraints differ, and everything else is
* identical, they will not be equal. Proxy's deserialized
* by atomic input streams will inherit the constraints of
* the stream from which they were deserialized. */
// if (!id.equals(handler.id)) {
if (id.hashCode() != handler.getActivationID().hashCode()) {
// Same UID.
StringBuilder sb = new StringBuilder(128);
sb.append("unexpected activation id: ")
.append(handler.getActivationID())
.append(" expected: ")
.append(id);
throw new ActivateFailedException(sb.toString());
}
It got worse when I implemented AtomicILFactory, in Atomic streams,
when proxy's are unmarshalled, they inherit any client constraints
applied to the stream, to prevent elevation of privilege gadget
attacks, where a third party proxy might bypass an integrity or
privacy constraint for instance such as allow a connection that
wasn't encrypted, or not authenticated. Again this changed feature
the identity of the proxy and tests failed as the proxy the test had
to confirm the test passed didn't have client constraints applied.
So it appears to me that client's MethodConstraints shouldn't be part
of proxy identity.
Does anyone have a good reason why client MethodConstraints should be
part of proxy identity? It doesn't seem right to me that the client
is able to change the identity of a proxy, just by applying constraints.
This seems to have been overlooked in the implementation.
Also as a side note, I needed to make a lot of changes to existing
services to support secure endpoints, as the server's often didn't
reply to call back proxy's using their Subject, for example
EventLIstener's didn't work in a secure environment. I fixed that of
course.
These are changes I'd like to make to River, to make secure services
behave like insecure services, but with security. :) So that security
can be a configuration concern. So new developers can develop and
test their application, later configure it to be secure without it
breaking.
Thanks,
Peter.