This email is a written version of my talk at the Scheme Workshop this week. 
You can also watch the recording 
<https://www.youtube.com/live/Zl-M3avRPXI?si=hb651QDhylQBlakt&t=25780> or read 
a version with hyperlinks and some extra footnotes at 
<https://crumbles.blog/posts/2025-10-18-scheme-reports-at-fifty.html>

* * *

In December this year, the Scheme reports will turn fifty. As chair of the 
working group entrusted with the next major revision of the report, I want to 
start a discussion in the Scheme community about what a good Scheme report 
looks like in 2025, and how it’s different from what it looked like in 1975, 
and from other times when the Scheme report was revised.

== Who is the Scheme report for? ==

When making any document, we have to consider who we’re writing for, how 
they’re going to use it, and what they want and need from it in order to do 
their thing. For the Scheme report, the obvious two groups are users and 
implementers. These are very vague groupings, and like any attempt to divide up 
a group as large and diverse as the Scheme user base, one can’t at all pretend 
like every member of these groupings has the same views on every issue. 
Nonetheless, a rule of thumb is that users want their pet features added, 
creating pressure to grow the report;1 implementers want to be able to actually 
create a compiler, creating pressure to keep the report smaller and simpler. 
But there are also clear subdivisions where even this clear breakdown falls 
apart, like in the embedded space, where both users and implementers want 
something that can work on limited-resource environments.

Another tension still rarely recognized is between users in education – 
students learning the language – and long-time Schemers who know it very well. 
The How to Design Programs approach seems to have worked for many more 
beginning students than Structure and Interpretation of Computer Programs ever 
did, because HtDP acknowledges from the start that assuming brand new students 
will be able to learn with a tool designed for people who are already experts 
means that tool can’t be as helpful to those just finding their feet in a new 
way of thinking.

But in Scheme we often get into philosophical and even political debates when 
we talk about what the Scheme report should be like; debates which have much 
more to do with an ideological belief about the nature of the language than 
with the direct, practical needs of the debaters.2

== Big and little languages ==

A classic such argument is over whether certain versions of Scheme – usually 
R6RS, and sometimes also the one that my working group is producing – are ‘too 
big’. On the other hand, Scheme reports that don’t have this quality can be 
seen as being too ‘little’ for doing real programming work in.

Earlier, littler Scheme reports are often described by the makers of these 
arguments as a ‘diamond-like jewel’, or similar. The ‘diamond-like jewel’ 
wording is, I think, from the infamous ‘Worse is Better’ section of Richard P. 
Gabriel’s paper ‘Lisp: Good News, Bad News, and How to Win Big’.

In 1998 Guy L. Steele, co-inventor of Scheme, read a keynote paper at OOPSLA 
entitled ‘Growing a Language’ (transcript). In the paper, he talks a lot about 
the tension between the qualities of a big language vs a little language, and 
in particular talks about Scheme, saying:

> Could not “The Right Thing” be a small language, not hard to port but with no 
> warts?
>
> I guess it could be done, but I, for one, am not that smart (or have not had 
> that much luck). But in fact I think it can not be done. Five-and-twenty 
> years ago, when users did not want that much from a programming language, one 
> could try. Scheme was my best shot at it.
>
> But users will not now with glad cries glom on to a language that gives them 
> no more than what Scheme or Pascal gave them. They need to paint bits, lines, 
> and boxes on the screen in hues bright and wild; they need to talk to 
> printers and servers through the net; they need to load code on the fly; they 
> need their programs to work with other code they don’t trust; they need to 
> run code in many threads and on many machines; they need to deal with text 
> and sayings in all the world’s languages. A small programming language just 
> won’t cut it.

From the things he names as examples of what users want to do with languages, 
it’s clear that Steele’s mind was very much on Java, and Java in 1998 at that. 
Some of these things just aren’t in fashion any more: some were thought to be 
good ideas at the time, but now seen as bad ideas; some of them just never 
caught on. But some of them are just as important as ever.
Of the things that are just as important as ever, though, many of those no 
longer seem like things a language should have to take care of; they are, 
rather, the province of third-party libraries.

That, in fact, is how Steele concludes ‘Growing a Language’: users should be 
able to grow the language itself by adding libraries.

But, it seems, the base of Scheme as it was in 1975, and even in 1998, was not 
enough. Most people today would agree that a programming language without even 
a standard error-handling mechanism is quite deficient, even if it does give 
one the ability to build one for oneself.

And, in fact, most Schemers agree that the best way for Scheme to go forward is 
to find better ways for Scheme users to grow the language. Our disagreement, 
then, is not about ‘bigness’ per se, but where the bigness comes from. Few 
would swallow a thousand-page Scheme report; setting aside the actual labour of 
designing and implementing it, most people would be perfectly content with 
using their own personal library of language extensions whose documentation 
would run to a thousand pages if it were all documented.3 Our disagreement is 
over how big the base needs to be in order to provide a foundation to grow 
from; and over what needs to be in the foundation, to enable users to give 
themselves this bigness.

== Dynamic systems, static languages ==

So big vs little is one axis of disagreement within the Scheme community. How 
about another?

In 2012 Richard P. Gabriel wrote an essay paper, ‘The Structure of a 
Programming Language Revolution’. He talks about how he took a break from 
programming languages in the early 1990s in order to do a fine arts degree. 
When he came back in the late 1990s, everything had changed. When he left, 
people in programming languages talked about dynamic, evolving systems like 
Common Lisp and Smalltalk. By the time he returned, the conversation had 
changed to static languages like Haskell.
I think one of the other axes of division in the Scheme community is around 
this matter, and the reason is that our community lived through this paradigm 
shift without, collectively, noticing it. Some of the community moved on to the 
new paradigm; others continued to think in terms of the old.4 The two sides do 
not understand one another’s concerns.

The dynamic systems viewpoint is epitomized by the R5RS, whose only entrypoint 
for programs is the interactive top level, and which even began to lay the 
groundwork for a library and namespacing system that would have been based on 
first-class environments and the eval procedure. Implementations which follow 
the dynamic systems model include MIT Scheme and Guile.

The static languages viewpoint is epitomized by the R6RS, which doesn’t have an 
interactive top level at all. Implementations which adhere to this model 
include Chez, Racket, and Loko, but also niche implementations like Stalin 
which don’t have their own interactive top level at all.

Put briefly, the dynamic languages people see Scheme as a dynamic language, 
plain and simple, and want to be able to do all the run-time modification that 
they should be able to do in any such language. The static languages people see 
Scheme as a static language

== And yet more ==

Already with these two dimensions of belief about what kind of language Scheme 
is – big vs little, static vs dynamic – we have a huge range of potential 
expectations for what the Scheme report might be like. When we compare these 
viewpoints in terms of the models their advocates might prefer to take as 
guidance for the future development of the language, we can see just how far 
apart these ideas are.

Those who want a little, dynamic language will look to earlier versions of the 
report, and maybe to the cores of languages like Lua and JavaScript. A little 
static language might look like SML. Common Lisp might be a model to follow for 
a big dynamic language, or Haskell for a big static language. I’ve seen almost 
every one of these languages used to suggest what a suitable future direction 
for Scheme might look like.

These are hugely different rôle models to follow. Clearly, we can’t satisfy all 
of these expectations at once.

== Does a Scheme report still make sense? ==

Given these deep divisions over the essential nature of the Scheme language, 
does it even make sense that we still keep making a Scheme report?

‘No’ is an entirely possible answer to this question. Already in the R6RS and 
R7RS small days, people were arguing that Scheme standardization should stop.

If we went this way then, just like Racket in its default mode no longer claims 
to be a Scheme report implementation, Schemes would slowly diverge into 
different languages. Guile Scheme would one day simply be Guile; Chicken Scheme 
would be Chicken, and so on. Like the many descendants of Algol 60 and 68, and 
the many dialects of those descendants, each of these languages would have a 
strongly recognizable common ancestor, but each would still be distinct and, 
ultimately, likely incompatible.

It shouldn’t surprise you that I don’t think this is the way to go. As a user 
of Scheme, I can still see ways I want to extend the common core of all of 
these implementations. It’s much better to be able to do this once and have my 
extension available on many implementations, than to have to work hard to port 
my extension to multiple different languages. All implementations benefit by 
agreeing on a common core that works to be able to grow the language.

Racket is already a cautionary tale. It has some amazing features, but those of 
us on other implementations can’t take advantage of them because Racket’s 
implementations of those features aren’t portable. Even Guile has this problem, 
because it’s still culturally normal among users of that implementation to use 
its own define-module declaration instead of the standard R6RS or R7RS library 
or define-library, even if your code only uses standard Scheme features and 
maybe some common SRFIs. There’s much Guile code I’d like to use on Chez for 
more speed, or on Chibi for a smaller implementation footprint, that currently 
requires at least some porting effort for not much good reason.

This is more or less the same rationale for Scheme reports that there has 
always been, and I think it continues to apply today.

== R6RS and R7RS small considered more alike than widely believed == 

So our thoughts must naturally turn to unification. The co-existence and 
incompatibility of R6RS and R7RS small have become emblematic of the splits in 
our community. The R6RS editors and community are, to some extent, justified in 
feeling that R7RS small unfairly abandoned their work. But in fact the two are 
more similar than is widely recognized, and in many cases the design of R7RS 
small in fact vindicates the decisions of the R6RS editors.

This may seem a shocking claim about a division which some predicted would end 
up killing Scheme as a programming language. But, I think, WG1 stumbled their 
way towards a realization, which I’ll get to just below, which led them to a 
develop a library system working on basically the same model as R6RS. R7RS 
small library declarations support conditional compilation and other features 
which, in R6RS, is exclusively the province of the ‘main’ level language; but 
once all the cond-expands in define-library are dealt with, the two are 
essentially the same. R7RS small’s define-library declarations can be compiled 
entirely ahead of time to R6RS’s library style – there is already a program 
which does this, Akku.

Between 2007 and 2013 the landscape of programming tools also shifted so some 
of the things which were criticized in R6RS’s day – bytevectors for binary 
data, and Unicode throughout – now seem perfectly normal. It now seems wrong 
for a programming language not to support these. R7RS small also adopted, for 
example, the same exception raising and handling mechanism as R6RS.5

The changing landscape of programming tools around Scheme means that 
programmers now have a much different sense of the ‘littleness’ of a language 
than in 2007. Since Rust there’s increasing recognition that memory safety 
should be treated as non-optional even in most low-level programming, and is 
cheap to implement; it now seems strange that R5RS and below, and R7RS small, 
make bounds violations undefined behaviour in the C sense.6

Moreover, what R7RS small’s authors seemed to realize is that the report will 
always be a minimum, and not a maximum. I think this is why, although it came 
from a group of users who started out highly critical of the R6RS for its 
static model of libraries and programs, R7RS small adopted essentially that 
model. It doesn’t restrict implementations from providing more dynamic library 
features.

The small/large report split helps even more, because now the report offers two 
different minimums for implementations to choose from, according to what their 
needs are. The minimum for ‘the practical needs of mainstream software 
development’ is, as Guy Steele says, much bigger than it used to be, and that’s 
fine!

== Join, or die ==

This is my appeal to the Scheme community, then. If we don’t have a Scheme 
report that the majority of implementations and users accept, Scheme as a 
coherent single language will simply die. Not all implementations – it’ll be 
like if, as above, we stopped making Scheme reports and everyone went their own 
way. But even the implementations which survived would clearly be weaker for 
not being able to share the libraries of the others.

R7RS is our best shot at joining together to still be able to share code with 
one another, and to grow the language together – not only in the report itself, 
but much more in the tools we build with it.

== The sacred craft ==

Joining, however, means compromising.

Nobody will look at any Scheme report and say it is perfect. I can’t look at 
any version of the report, not even R5RS, and say it was a ‘diamond-like 
jewel’.7 Even if it were perfect for one person, it cannot be all things to all 
people. Scheme has historically been too shy of compromise; the uncompromising 
pursuit of perfection, even though perfection is a quality nobody will ever 
agree on, may be why we have struggled so much to move onwards while other 
languages have not.

‘Compromise’ is a dirty word for some people, but I would like to offer another 
perspective. Although R7RS is sometimes perceived as anti-R6RS, two of the 
small report’s editors actually voted in favour of R6RS ratification.8 One of 
them, John Cowan – also my predecessor as chair of WG2 for the large language – 
wrote in the rationale to his vote:

> a well-crafted compromise is in my opinion the most sacred thing that a 
> secular age knows

We may not be able to have a diamond-like jewel, but we can have the most 
sacred thing a secular age can make.

* * *

I hope this will spark a real conversation about the future direction of the 
report.


Daphne

Reply via email to