Here's Kent Pittman's :TEACH;LISP from ITS, which is a MACLISP program that teaches you how to program in MACLISP. (That's "Man And Computer Lisp" from "Project MAC", not "Macintosh Lisp".)
https://github.com/PDP-10/its/tree/master/src/teach
https://en.wikipedia.org/wiki/Incompatible_Timesharing_Syste...
https://en.wikipedia.org/wiki/Maclisp
https://en.wikipedia.org/wiki/MIT_Computer_Science_and_Artif...
Scheme or Lisp? Kent M Pitman explains the deep philosophical differences:
https://www.reddit.com/r/programming/comments/6fa5r/scheme_o...
https://groups.google.com/g/comp.lang.lisp/c/TEk4O4-zsA8/m/H...
>You should definitely learn both if you can afford the time. They are not redundant with one another, in spite of their superficial syntactic similarity.
>Others divide up this space differently than I, but for most purposes, I personally regard them as distinct langauges, not mere dialectal variations, although plainly they are from what I would call the same language family.
>You will probably prefer to use one or the other in the end, but they each have things to teach you. Even if you prefer to use neither, you will use the things you learn from these languages in your future thinking, becuase they will give you metaphors for thinking about things that other languages do not.
This is like catnip for people interested in the sociological and cultural aspects of programming language design:
Common Lisp: The Untold Story; Kent M. Pitman, HyperMeta Inc.
https://www.nhplace.com/kent/Papers/cl-untold-story.html
Here's a description of :TEACH;LISP that I posted to reddit 11 years ago:
https://www.reddit.com/r/programming/comments/t4rre/comment/...
>xardox 11 yr. ago
>Kent Pitman's a great guy who's done a lot of pioneering work to teach people Lisp.
>KMP wrote a Lisp program to teach MACLISP on the MIT AI Lab's ITS systems called ":TEACH;LISP", which I used to learn Lisp (but which Jerry Pournelle cited in a not-friendly light).
>KMP kindly took the time to personally teach me some LISP, by challenging me to a dual! We both ran our own LISP processes, and loaded a function called EVAL-IN-OTHER-LISP that used "core link interrupts" to send s-expressions from one LISP to another, so we could evaluate code in each other's LISP. That made it easy for him to define and call functions in my LISP, which was quite fun, but then he set my numeric output base to roman numerals! He won that dual.
Core Link Interrupts (ITS's interprocess communication mechanism, sending messages through actual core memory on a PDP-10):
https://web.archive.org/web/20110904184550/http://www.avanth...
How Jerry Pournelle got kicked off the ARPANET:
http://www.art.net/~hopkins/Don/text/pourne-smut.html
>From: Kent M Pitman <KMP at SCRC-STONY-BROOK.ARPA>
>Subject: Pourne
>Personally, I'd just turn off his account. It's not like it's the first time, and he not only flaunts his use of our machines but stabs us in the back with grumblings about why he doesn't like this or that program of ours when he gets a chance. (Am thinking particularly of an article he wrote which condemned Lisp for reasons amounting to little more than his ignorance, but which cited Teach-Lisp in a not-friendly light... The man has learned nothing from his presence on MC and sets a bad example of what people might potentially accomplish there. I'd rather recycle his account for some bright 12-yr-old...)
Here's the source code to EVAL-IN-OTHER-LISP:
https://www.maclisp.info/pitmanual/system.html
The following is some sample code (complete with documentation) that I found in my notes and thought might be helpful:
;;; Notes about CLI interrupts:
;;;
;;; A CLI interrupt is what happens when another job sends to yours. It is
;;; normally the case that other jobs will send directly to a user's HACTRN.
;;; If, however, Lisp is interrupted by a CLI message, it can elect to handle
;;; handle the interrupt in an arbitrary way.
;;;
;;; To define a handler, two things must be done:
;;; [1] Place the name of the handler function (function of one arg)
;;; in the variable CLI-MESSAGE.
;;; [2] Enable CLI handling with (SSTATUS CLI T)
;;;
;;; The handler should take a single argument which it probably should ignore
;;; since I have no idea what it is likely to be.
;;;
;;; The handler should open the file "CLA:" in (CLA BLOCK) mode and immediately
;;; discard the first 8 characters which will be garbage.
;;;
;;; The remainder of the stream, until a control-C or an eof, will be the text
;;; of the message sent. It may be read with TYI, READ, etc. and handled
;;; however.
(eval-when (eval compile)
(cond ((not (get 'iota 'version))
(load "liblsp;iota"))))
(defun handle-cli-msg (ignore)
(iota ((stream '((cla)) '(cla block)))
(do ((i 0 (1+ i))) ((= i 8)) (tyi stream))
(do ((c (tyi stream -1) (tyi stream -1)))
((or (= c -1) (= c 3)))
(format t "~&~3,'0O ~@:C~%" c c)))) ;print out chars seen
(setq cli-message 'handle-cli-msg)
(sstatus cli t)
; --------
(defun eval-cli-msg (ignore) ;alternate handler
(iota ((stream '((cla)) '(block cla)))
(do ((i 0 (1+ i))) ((= i 8)) (tyi stream))
(do ((f (read stream nil) (read stream nil)))
((null f))
(errset (eval f) nil)))) ;Quietly evaluate forms...
;; Assumes the other lisp will have EVAL-CLI-MSG as value of CLI-MESSAGE
(defun eval-in-other-lisp (uname jname s-expression)
(iota ((stream `((cli) ,uname ,jname) '(out ascii block)))
(print s-expression stream)))