Notes on Medley Interlisp

Introduction

This document is a small collection of random, out of order, and largely incomprehensible notes I’ve written as I struggle to learn how to use the Medley Interlisp environment, which, so far, has been extremely fun.

Interacting with the System

Early Setup

It may be useful to set the following variables up:

For IL:DIRECTORIES I like to set:

("{DSK}<home>seth>medley>library>"
 "{DSK}<home>seth>medley>lispusers>"
 "{DSK}<home>seth>medley>internal>library>"
 "{DSK}<home>seth>medley>sources>"
 "{DSK}<home>seth>medley>rooms>"
 "{DSK}<home>seth>medley>clos>")

There are two ways to do this:

  1. Edit the variable directly and save your VM when you exit.
  2. Set and/or append to the variables in your Greet File (INIT)

Hint

Appending to a list can be done with, e.g.:

(NCONC1 DIRECTORIES "{DSK}<home>seth>medley>rooms>")

Working with Files

Working with files in Medley isn’t at all like working with files in Unix or Windows, or really anything else you’re probably used to. Although you can edit plain text files with TEdit, this isn’t how you go about creating a Lisp file.

First, there’s a problem with the term “file”, because Medley uses it to mean two distinct things:

  1. A collection of definitions of Lisp functions, variables, structures, macros, data, and commands in one logical unit.
  2. Actual files on disk.

They’re related, but not the same. The Medley Interlisp-D Reference Manual now carries the following warning at the top of Chapter 17, “File Manager”:

Warning: The subsystem within Medley used for managing collections of definitions (of functions, variables, etc.) is known as the “File Manager.” This terminology is confusing, because the word “file” is also used in the more conventional sense as meaning a collection of data stored on some physical media. Unfortunately, it is not possible to change this terminology at this time, because many functions and variables (MAKEFILE, FILEPKGTYPES, etc.) incorporate the word “file” in their names.

There is some confusing crossover here between collections of functions, variables, macros, commands, etc., that Medley refers to as “files”, and actual blocks of data on disk. The key thing to remember is that the File Manager functions deal explicitly with collections. These collections do get mapped to files on disk, but that is more or less opaque to the user.

The normal order of operations would then be:

  1. Define some new functions interactively in the Executive or Structural Editor, e.g. with (ED 'FOO 'FNS)
  2. Run (FILES?), which will prompt you for a collection name to store each newly created function in. If the collection does not yet exist, it will be created.
  3. Flush pending operations with the (CLEANUP) function.

Step 3 will actually create two collections to correspond to each collection “file”: one with the collection name, and one with the collection name suffixed with COMS, e.g., if you added a bunch of functions to the collection named FOO in step 2 above, when that collection is flushed to disk in step 3, you’ll end up with two collections, one named FOO and another named FOOCOMS.

FOOCOMS is a special structure, called a filecoms. You can edit FOOCOMS in the structural editor with (DV 'FOOCOMS), just like any other structure. The format is documented in the Medley Reference Manual. The FOO collection actually holds the definitions of the functions.

Shutting Down

The Interlisp function (LOGOUT) will log out, save the system, and shut down the emulator.

Called with (LOGOUT) or (il:logout).

The Magic of MAKESYS

I just discovered the MAKESYS function. Until now, I’ve been doing SYSOUT or LOGOUT to save my VM state, but MAKESYS is a better way to make a new, clean system file. I like it. It’s called with two arguments, file and name, for example:

(MAKESYS "{DSK}<home>seth>new-system.sysout" "Some New Name")

The file argument specifies what file to write the system out to. The name argument is optional, and, if supplied, will be used as the system banner when the new system starts up. If it’s NIL, the default banner “Medley 3.5” will be used.

Anyway, the reason I like it is because, unlike SYSOUT and LOGOUT, it undoes your greet history, clears out the EXEC that you did the command in, and writes out a clean startup system. With SYSOUT and LOGOUT, the whole state of the system is sort of preserved in-situ, which you probably want sometimes, but I like being able to make a canned, fresh startup.

Resetting History

If you want a clean Exec history, you can reset it in your GREET file. This history is stored in the global variable LISPXHISTORY (WARNING: Do NOT try to dump the contents of this variable, it will lead to an infinitely recursive call that will blow up the stack!!!!)

To do this, you’d add the following to your GREETFILE just before the end of the P section:

(SETQ LISPXHISTORY '(NIL 0 100 1000))

The initial state of LISPXHISTORY is (NIL 0 100 1000), in the form (EVENTS EVENT# SIZE MOD), where:

  1. EVENTS is a list of events and their side effects,
  2. EVENT# is the number for the most recent event on the EVENTS list,
  3. SIZE is the maximum number of events to allow on the list, after which the earlier events are lost,
  4. MOD is the maximum event number to use before they roll over.

Every time a command is run, the history number is bumped up until it rolls over. Setting this initial value just clears everything out and gives you a clean history.

Exploring Functions

There are two great ways of finding out more about functions, besides just reading the manual. The first is to search for a substring in all of the defined symbols using APROPOS. To get a list of all functions and symbols that contain the substring “WINDOW” (case insensitive), just type:

(APROPOS 'WINDOW)

The other, once you know the name of a function, is to use the man command. This isn’t a function, it’s an Exec command, so to open up the Interlisp Reference Manual to the entry about CREATEW, you’d type:

man CREATEW

The Who-Line

img

The Who-Line is a little bar at the top of the screen that shows some useful information, and which can be used to modify certain aspects of the system or current exec. This is enabled by loading the WHO-LINE Lisp User Module (this is enabled by default)

Defining Symbols

Use SETQ to set a global variable.

(SETQ MY.VAR '(A B C))

;; Get the value
MY.VAR  ; -> '(A B C)

Undefining Symbols

Common Lisp and XCL can remove the definition of a symbol with UNINTERN, and Interlisp-D can remove definitions of a symbol with DELDEF.

Common Lisp

(cl:unintern 'foo)

Interlisp

You do need to know the type of symbol you’re deleting the definition for (DWIM will prompt you for suggestions if there are multiple matches). For example, if there’s a global variable named FOO:

(DELDEF 'FOO 'VARS)

And if there’s a FNS function named BAR:

(DELDEF 'BAR 'FNS)

The Readtable

As far as I can tell, the Readtable is used by Medley to determine what kind of parser to use for a given TTY window / Exec process (I think I have that terminology correct). If you use the “Interlisp” Readtable, for example, everything is case sensitive. Interlisp expects functions to be in all upper-case, because that’s how they’re defined. You cannot, for example, use (lambda () ...), you must use (LAMBDA () ...). On the other hand, if you use the “XCL” Readtable, parsing is case insensitive.

Lisp User Modules

In addition to the base Lisp system, Medley could load contributed packages called Lisp User Modules or Lisp User Packages.

Loading Lisp User Modules

The general form is:

(FILESLOAD 'module)

where ’module is the name of one of the Lispusers modules. For example, to load the ADDRESSBOOK module, you’d type (FILESLOAD 'ADDRESSBOOK)

img

Information about Lispusers Modules

To see information about a Lispusers modules that has been loaded, use the PL command. This is not a Lisp function! It’s a direct exec command like CONN, no parentheses needed.

For example, to see information about the ADDRESSBOOK package, type:

PL ADDRESSBOOK

This will show the following information:

FILEDATES : ((" 8-Jul-88 16:36:22" . |{FS8:PARC:XEROX}<BOBROW>LISP>ADDRESSBOOK.;2|))
COPYRIGHT : ("Xerox Corporation" 1986 1988)
FILE : ((ADDRESSBOOKCOMS . Compiled))

Specific Modules

Here are some random notes about specific modules.

Background Images

The BACKGROUNDIMAGES module requires PUP and PRESS to be loaded firt.

To load the BACKGROUNDIMAGES module, do the following:

(FILESLOAD 'PRESS 'BACKGROUNDIMAGES)
(BACKGROUND.SETUP)

This should add a Background menu item to the background menu.

Miscellaneous

Rooms

ROOMS is a Lisp package that reminds me a lot of Hypercard on the Macintosh. It allows a sort of multiple desktop structure that allows for arbitrary links between the desktops, which are (naturally) called rooms.

Enabling the Library

First, ensure that the .../medly/rooms path has been added to your IL:DIRECTORIES global variable, or Medley won’t know where to look for the library.

Then, exec a new Interlisp and load the ROOMS library.

(FILESLOAD 'ROOMS)

This should automatically start the ROOMS environment and give you two unconnected Rooms named Original and Pockets. You can navigate between them using the newly created background menu item, or you can create doors between them.

Loading the Office Suite

If you want to load the pre-defined Office suite, do the following,

  1. Run (ED 'ROOMS:*SUITE-DIRCTORIES*) to edit the list of directories used to find suites, and set it appropriately, e.g. ("<home>seth>medley>rooms"). After setting the value, select Menu → Done & Close

  2. Restore the suite from the main menu, Menu → Rooms → Suites → Restore Suite. Enter OFFICE.SUITE when prompted.

Note that this does not seem to replace the two default rooms, it just adds to them.

Renaming Rooms

(ROOMS:RENAME-ROOM (ROOMS:ROOM-NAMED "Old Name") "New Name")

Stuff I Need To Figure Out

Undoing Things

One of the problems I’m running into is that I don’t know how to undo things like loading libraries. For example, if I load the STARBG package from Lispusers, and run (STARBG), I get an awesome background and a UFO cursor. It’s cute! But if I want to turn that off and unload the library, how do I do that?

The same goes for ROOMS. I have no idea how to turn it off and remove the library. For now, I’m just experimenting while keeping lots of backups of my lisp.virtualmem file so I can always go back to the last save.