Right, good analysis! I have further important additions to #1 and #2: #1 of course is difficult. It should be split up: -----------------------------------------------------
1a. malicious JSP/script code Injecting a script that gets executed by Sling can be a lot easier (incorrect ACLs on production systems) than deploying a bundle (which should only possible with admin). This is definitely a goal that Sling should have: that you can make sure scripts can be fully sandboxed. There are 2 important separations: access to java APIs and - since it is core to Sling - access to the resources / jcr. The first should be possible by just whitelisting APIs a script can use (e.g. no System.exit()) while the latter requires a fully safe authentication mechanism that is handled on the jcr side. 1b. malicious bundles reading from JCR through the API Even if a bundle could be installed, IMO it is not clear that it should have access to the data in the resource tree (JCR). A service user mapping config _could_ in theory be implemented safely so that you cannot circumvent it through Java code (that's what I was refering to in my original mail). This would make the JCR safe (ignoring the issue of reading the repo via the file system or reloading the repo bundle). 1c. malicious bundles in general Of course, if an attacker can install bundles, he could do: - malicious code: things like System.exit(), endless loops - access critical infra services (OSGi admins, crypto service etc.) - try to read osgi config data from the filesystem - try to read the repository data directly through the filesystem (i.e. using a customized jackrabbit bundle without authentication) Ignoring how much work it would be in the end, solutions that IMO are at least possible: - a new "OSGi sandboxing", so that they cannot import all packages/classes, but just a subset (e.g. no "System.*"; a simpler way than JaaS); to avoid permission management hell for normal product development, you'd only do this in production with a "seal now" button, so that permissions are restricted only for newly added (malicious) bundles - similarly, disable file system permissions through JaaS, as a whitelist on a production system (configured in the filesystem and not through a web UI provided by Sling itself, or at least not with a replaceable bundle, so you couldn't hack the configuration) - remember, the JCR access was protected already through safe authentication; no need for making the jcr packages invisible or inventing a JaaS permission, as JCR already has an auth mechanism With 1b and 1c in place, even a malicious bundle could not steal arbitrary data from the repository (unless exposed by other services through an API, internally using a loginByService() with a more powerful user; which in most cases is wrong; note that all other code would be implicitly using the request session). If you say "it's impossible" it will be a self-fulfilling prophecy: you add new stuff that doesn't care about the clear boundaries, and then it is indeed impossible to find a way to shield things from each other. Before you can think about using JaaS, you have to have clear APIs and boundaries, so that permissions are simple and obvious and not too complex. Also, there is an important case for #2: ----------------------------------------------------- 2. 3rd party "app bundles" Running 3rd party apps on a multi-tenant Sling instance, managed by one organization, but apps provided by others. Here the requirement to make sure code cannot circumvent users listed in the sling user mapper might be more important. A safe mechanism would be useful here to reduce the things the bundle has to be tested and reviewed for. Also, here you maybe want deliberate sandboxing with just a few APIs accessible (similar to 1a with scripts). Conclusion: ------------------ We should definitely aim for #1a, #2 and #3. #1b and c should be designed for, even if we can't implement that mechanism right away. BTW, Something that comes to my mind whenever I mention "sandboxing" above is the "Object capability model" [1], where code can only do what interfaces it gets access to. This is hard in a Java context which can load any class on the classpath by default, giving it access to everything. Instead of the JaaS approach, which simply acknowledges this fact, and thus has to add a permission concept to deny access, you could also think about simply disabling the importing in the first class, which should be feasible with a pure OSGi system. [1] http://en.wikipedia.org/wiki/Object-capability_model Cheers, Alex
