[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: 200alpha15 (security guards)

Will removing read-accept-compiled and the various forms of load from
the namespace eliminate the bytecode hole?


> The exp-tagged code in CVS for MzScheme and MrEd is now version
> 200alpha15.
> The main change in this version is the addition of "security guards" to
> check filesystem and network access.
> Security Guards
> ---------------
> In principle, programmers could always sand-box a program through a
> namespace that constains a retricted set of primitives. But
> constructing a useful and restricted namespace is tedious, at best.
> To make sand-boxing easier, we've added an access check around each
> access of the filesystem or network in MzScheme's primitives. The
> access check calls a function provided by the current security guard
> --- as determined by the new `current-security-guard' parameter ---
> giving the guard a pathname/hostname, plus an indication of the kind of
> access that is needed (read, write, etc.). If the function does not
> raise an exception, access is granted.
> For example, evaluating the following expression should cut off all
> filesystem and network access:
>  (current-security-guard
>      (make-security-guard (current-security-guard)
>          ;; filesystem check:
>          (lambda (who path mode) (raise 'no-filesystem!))
>          ;; network check:
>          (lambda (who host port-number) (raise 'no-network!))))
> A new security guard can be created only as a child of an existing
> security guard, and access checks always consult the parent as well as
> the child, so a program can't arbitrarily increase its access by
> creating a new security guard.
> See the latest documentation for details.
> Security and Extensions
> -----------------------
> Extension implementors must insert access check into their code using
> the following new functions:
>  void scheme_security_check_file(const char *who, char *filename, int guards);
>  void scheme_security_check_network(const char *who, char *host, int port);
> Of course, most sand-boxing security guards will simply disallow the
> loading of extensions.
> Why Security Guards Definitely Don't Work, Yet
> ----------------------------------------------
> A gaping security hole remains in MzScheme: bytecodes (usually from .zo
> files) are not fully validated, so ill-formed bytecodes can in
> principle do arbitrarily bad things. It's not enough to simply cut off
> filesystem access; an expression such as
>  (parameterize ([read-accept-compiled #t])
>     (read (open-input-string "#~...")))
> can do anything with a cleverly chosen "...", I think.
> Also, MrEd is still missing some access checks.
> These bugs will be fixed soon.
> Will Security Guards Ever Work?
> -------------------------------
> I think so, but I'm interested in feedback (either about the interface
> or the implementation) from anyone who knows something about security.
> There are *so many* things that can go wrong. For example, in my
> initial specification, the string and list passed to a security-guard
> procedure were mutable, so a child security guard could mutate the
> arguments before the parent security guard saw them. I caught that one,
> but I wonder how many other things I've missed.
> (Knowing just a little about security, and knowing a fair bit about the
> PLT Scheme infrastructure, my guess is that the problem is no more
> difficult than the problem of preventing seg faults --- but, almost by
> definition, also no easier.)
> Matthew