;;;; ;;;; s e c u r i t y . s t k -- Secure environments building ;;;; ;;;; ;;;; Copyright © 1996-1999 Erick Gallesio - I3S-CNRS/ESSI ;;;; ;;;; Permission to use, copy, modify, distribute,and license this ;;;; software and its documentation for any purpose is hereby granted, ;;;; provided that existing copyright notices are retained in all ;;;; copies and that this notice is included verbatim in any ;;;; distributions. No written agreement, license, or royalty fee is ;;;; required for any of the authorized uses. ;;;; This software is provided ``AS IS'' without express or implied ;;;; warranty. ;;;; ;;;; Author: Erick Gallesio [eg@unice.fr] ;;;; Creation date: 11-Nov-1996 20:03 ;;;; Last file update: 3-Sep-1999 19:54 (eg) ;; Security is achieved by the function "set-security-level!". This function ;; sets the desired level of security. Levels are defined as is ;; level 0 -- no control ;; level 1 -- no system + send procedures ;; level 2 -- no eval and environment manipulation ;; level 3 -- no file opening / closing ;; level 4 -- no output port procedures ;; level 5 -- no input port procedures ;; ;; The function "secure-environment" returns an environment with the unsecure ;; function re-defined to an error procedure. ;;; ;;; Exported procedures ;;; (define set-security-level! #f) (define security-level #f) (define secure-environment #f) ;============================================================================= (let () (define current-level 0) ; The current security level (define cached-environment (global-environment)) ; current secure env (define security-table (vector ; Security table ;; level 0 -- no control ' () ;; level 1 -- no system procedure '(system exit bye quit send) ;; level 2 -- no eval and environment manipulation '(extend-environment eval global-environment environment->list procedure-environment eval-hook) ;; level 3 -- no file opening / closing '(with-output-to-file open-output-file close-output-port open-file close-port with-input-from-file open-input-file close-input-port) ;; level-4 -- no output port procedure '(write display newline write-char when-port-writable format error flush) ;; level 5 -- no input port procedure '(read read-char peek-char eof-object? char-ready? load try-load autoload when-port-readable))) ;;; ;;; Set-security-level! ;;; (set! set-security-level! (lambda (n) ; make-invalid-procedure (define (make-invalid-procedure name) (lambda args (security-alert name))) ; security-alert (define (security-alert name) (letrec ((find-level (lambda (name lev) (if (member name (vector-ref security-table lev)) lev (find-level name (+ lev 1)))))) (error "Security alert: Procedure \"~A\" is unsecure.\nIt is at level ~A and current level security is ~A." name (find-level name 0) current-level))) ; all-symbols (define (all-symbols n) (if (= n 0) '() (append (vector-ref security-table n) (all-symbols (- n 1))))) ; make-environment (define (make-environment) (let ((bindings (map (lambda (x) (list x (make-invalid-procedure x))) (all-symbols current-level)))) (eval `(let ,bindings (the-environment))))) ;; ;; Set-security-level! starts here ;; (unless (= current-level n) (set! current-level (min n (1- (vector-length security-table)))) (set! cached-environment (make-environment))))) ;;; ;;; security-level ;;; (set! security-level (lambda () current-level)) ;;; ;;; Secure-environment ;;; (set! secure-environment (lambda () cached-environment)) ) (provide "security")