Module: DFMC-Management Synopsis: How to compile & test a source fragment as though it were a library. Author: Steve Rowley, Keith Playford, Jonathan Bachrach Copyright: Original Code is Copyright (c) 1995-2004 Functional Objects, Inc. All rights reserved. License: Functional Objects Library Public License Version 1.0 Dual-license: GNU Lesser General Public License Warranty: Distributed WITHOUT WARRANTY OF ANY KIND /// Basic classes for source records that represent a template. /// (This whole exercise could easily be repeated, using strings instead /// of templates for the source.) /// define class () // A source record whos source comes from a template closure. constant slot source-record-template :: , required-init-keyword: template:; constant slot source-record-module-name :: , required-init-keyword: module:; // Name for this source record (more conventionally a file name base). // Used for name of init function in c-back-end link phase, as well as // giving the source records names for printing purposes. constant slot source-record-name :: , required-init-keyword: name:; end; define method print-object (tsr :: , stream :: ) => () // How to print a , reasonably informatively. format(stream, "{Template SrcRec: %s}", source-record-name(tsr)) end; /// /// How to get the reader to read input from a template source record. /// define class () // Use this to suborn the reader into thinking it read the template. constant slot stream-source-record :: , required-init-keyword: source-record:; slot stream-done? :: = #f; end class; define method call-with-source-record-input-stream (fn :: , tsr :: , #key) fn(make(, source-record: tsr)); end method; define method read-top-level-fragment (stream :: , cr, offset, #key on-end-of-stream) => (fragment, lexer) // Here's where the actual reading over the fake stream occurs. We either // return the template (via matching), or take eof action. if (stream-done?(stream)) on-end-of-stream else stream-done?(stream) := #t; dynamic-bind (*fragment-context* = cr.compilation-record-module) macro-case (source-record-template(stream-source-record(stream))()) { ?stuff:body } => stuff end end end end;