home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / mitsch75.zip / scheme-7_5_17-src.zip / scheme-7.5.17 / src / runtime / savres.scm < prev    next >
Text File  |  2000-03-01  |  5KB  |  158 lines

  1. #| -*-Scheme-*-
  2.  
  3. $Id: savres.scm,v 14.33 2000/03/01 23:47:06 cph Exp $
  4.  
  5. Copyright (c) 1988-2000 Massachusetts Institute of Technology
  6.  
  7. This program is free software; you can redistribute it and/or modify
  8. it under the terms of the GNU General Public License as published by
  9. the Free Software Foundation; either version 2 of the License, or (at
  10. your option) any later version.
  11.  
  12. This program is distributed in the hope that it will be useful, but
  13. WITHOUT ANY WARRANTY; without even the implied warranty of
  14. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  15. General Public License for more details.
  16.  
  17. You should have received a copy of the GNU General Public License
  18. along with this program; if not, write to the Free Software
  19. Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  20. |#
  21.  
  22. ;;;; Save/Restore World
  23. ;;; package: (runtime save/restore)
  24.  
  25. (declare (usual-integrations))
  26.  
  27. ;;; (DISK-SAVE  filename #!optional identify)
  28. ;;; (DUMP-WORLD filename #!optional identify)
  29. ;;; Saves a world image in FILENAME.  IDENTIFY has the following meaning:
  30. ;;;
  31. ;;;    [] Not supplied => ^G on restore (normal for saving band).
  32. ;;;    [] String => New world ID message, and ^G on restore.
  33. ;;;    [] #F => Returns normally on restore; value is true iff restored.
  34. ;;;    [] Otherwise => Returns normally, running `event:after-restart'.
  35. ;;;
  36. ;;; The image saved by DISK-SAVE does not include the "microcode", the
  37. ;;; one saved by DUMP-WORLD does, and is an executable file.
  38.  
  39. (define (initialize-package!)
  40.   (set! disk-save (setup-image disk-save/kernel))
  41.   (set! dump-world (setup-image dump-world/kernel))
  42.   unspecific)
  43.  
  44. (define disk-save)
  45. (define dump-world)
  46. (define *within-restore-window?* #f)
  47.  
  48. (define (setup-image save-image)
  49.   (lambda (filename #!optional identify)
  50.     (let ((identify
  51.        (if (default-object? identify) world-identification identify))
  52.       (time (local-decoded-time)))
  53.       (gc-clean)
  54.       (save-image
  55.        filename
  56.        (lambda ()
  57.      (set! time-world-saved time)
  58.      (if (string? identify) unspecific #f))
  59.        (lambda ()
  60.      (set! time-world-saved time)
  61.      (fluid-let ((*within-restore-window?* #t))
  62.        (event-distributor/invoke! event:after-restore))
  63.      (start-thread-timer)
  64.      (cond ((string? identify)
  65.         (set! world-identification identify)
  66.         (clear console-output-port)
  67.         (abort->top-level
  68.          (lambda (cmdl)
  69.            (identify-world (cmdl/port cmdl))
  70.            (event-distributor/invoke! event:after-restart))))
  71.            ((not identify)
  72.         #t)
  73.            (else
  74.         (event-distributor/invoke! event:after-restart)
  75.         #t)))))))
  76.  
  77. (define (disk-save/kernel filename after-suspend after-restore)
  78.   (let ((filename (->namestring (merge-pathnames filename))))
  79.     ((without-interrupts
  80.       (lambda ()
  81.     (call-with-current-continuation
  82.      (lambda (continuation)
  83.        ;; GC cannot be allowed before the fixed-objects-vector
  84.        ;; is reset after restoring.
  85.        (with-absolutely-no-interrupts
  86.            (lambda ()
  87.          (let ((fixed-objects (get-fixed-objects-vector)))
  88.            ((ucode-primitive call-with-current-continuation)
  89.             (lambda (restart)
  90.               (without-interrupts
  91.                (lambda ()
  92.              (gc-flip)
  93.              (do ()
  94.                  (((ucode-primitive dump-band) restart filename))
  95.                (with-simple-restart 'RETRY "Try again."
  96.                  (lambda ()
  97.                    (error "Disk save failed:" filename))))
  98.              (continuation after-suspend)))))
  99.            ((ucode-primitive set-fixed-objects-vector!)
  100.             fixed-objects))))
  101.        (re-read-microcode-tables!)
  102.        after-restore)))))))
  103.  
  104. (define (dump-world/kernel filename after-suspend after-restore)
  105.   (gc-flip)
  106.   ((with-absolutely-no-interrupts
  107.     (lambda ()
  108.       (if ((ucode-primitive dump-world 1) filename)
  109.       after-restore
  110.       after-suspend)))))
  111.  
  112. (define (disk-restore #!optional filename)
  113.   ;; Force order of events -- no need to run event:before-exit if
  114.   ;; there's an error here.
  115.   (let ((filename
  116.      (->namestring
  117.       (if (default-object? filename)
  118.           (merge-pathnames
  119.            (let ((filename ((ucode-primitive reload-band-name))))
  120.          (if (not filename)
  121.              (error "no default band name available"))
  122.          filename))
  123.           (let ((pathname (->pathname filename))
  124.             (try
  125.              (lambda (pathname)
  126.                (let ((pathname (merge-pathnames pathname)))
  127.              (and (file-exists? pathname)
  128.                   pathname)))))
  129.         (or (try pathname)
  130.             (if (pathname-type pathname)
  131.             (system-library-pathname pathname)
  132.             (let ((pathname (pathname-new-type pathname "com")))
  133.               (or (try pathname)
  134.                   (system-library-pathname pathname))))))))))
  135.     (event-distributor/invoke! event:before-exit)
  136.     ((ucode-primitive load-band) filename)))
  137.  
  138. (define world-identification "Scheme")
  139. (define time-world-saved #f)
  140.  
  141. (define (identify-world #!optional port)
  142.   (let ((port
  143.      (if (default-object? port)
  144.          (current-output-port)
  145.          (guarantee-output-port port))))
  146.     (write-string world-identification port)
  147.     (if time-world-saved
  148.     (begin
  149.       (write-string " saved on " port)
  150.       (write-string (decoded-time/date-string time-world-saved) port)
  151.       (write-string " at " port)
  152.       (write-string (decoded-time/time-string time-world-saved) port)))
  153.     (newline port)
  154.     (for-each (lambda (name)
  155.         (write-string "  " port)
  156.         (write-string (get-subsystem-identification-string name) port)
  157.         (newline port))
  158.           (get-subsystem-names))))