GASOIL
A 2009 postfix esoteric language by the Esolang wiki user Morex. Programs are loaded onto a program stack and used up as they run, so there is no instruction pointer and every loop is recursion.
Created by Morex (pseudonymous Esolang wiki user)
GASOIL (General Application Stack Oriented Imperative Language) is an esoteric programming language created in August 2009 by Morex, a pseudonymous user of the Esolang wiki. All of its syntax is postfix, including operators, functions and control structures. Its central idea is that a program is not stored in fixed memory and stepped through by an instruction pointer. Instead it is loaded onto a program stack and used up as it runs: each instruction is popped and then it is gone. With no instruction pointer to jump backwards, recursion is the only way to write a loop. Morex said the language was inspired by the programming of two Hewlett-Packard calculators, the HP-41C and the HP-28S (whose language is RPL).
A note on the catalogue entry. The encyclopedia index lists this language as “GASOIL, 1963, Historical, last commercial 1975, Procedural, Simulation.” No source supports any of those values. HOPL, the online history of programming languages, lists the 1960s simulation languages in detail, including the whole GASP family. It has no entry called GASOIL, and searches of digitised literature turned up no 1960s language of that name. The name may have been confused with GASP, a real 1961 simulation language, or with the fuel “gas oil”. The only documented language called GASOIL is the 2009 esoteric language described here. Its Esolang article is dated 21 August 2009 and filed in the wiki’s 2009 category. This page describes that language. If a 1963 GASOIL does exist, it is not in any source that could be found.
History & Origins
Morex’s Esolang user page says they discovered esoteric programming languages in August 2009. It also lists their first programmable devices: a Casio fx-602P calculator, a Texas Instruments TI-99/4A, an HP-41CV calculator and a Sinclair Spectrum. GASOIL followed almost at once. The article went up on 21 August 2009. On the talk page, Morex introduced it as “a new esolang” and their “first time in the esolangs comunity”, and asked other users to correct their English.
The first version of the article was already close to complete. It included the instruction set, the program-stack execution model, examples up to a 99 Bottles of Beer program, and an interpreter. The interpreter was unusual for an esolang: it was a Microsoft Excel spreadsheet (gasoil_v0.81.xls). It was updated twice in the following week:
| Version | Date linked on Esolang | Form |
|---|---|---|
| 0.81 | 21 August 2009 | .xls spreadsheet |
| 0.82 | 26 August 2009 | .zip archive |
| 0.83 | 28 August 2009 | .zip archive on FileDen |
Version 0.83 came with a revised specification. It added CCALL, a conditional subroutine call. WHILE, UNTIL and FOR had been optional from the start. Now ITE (if-then-else) joined them in a new “Extended Flow Control” group, which “could be implemented or not in lightweight interpreters” because each can be written as a GASOIL subroutine built on CCALL. The next day, Esolang user Zzo38 went one step further on the talk page. They showed how CCALL itself could be defined with plain CALL, by turning the condition into the character 0 or 1 and calling a subroutine named 0ccall or 1ccall. Morex replied: “You are right!”
Design Philosophy
The design was a test of one idea: what happens if the program is a stack that is used up as it runs? The article states the goal as testing “a language (and interpreter) that instead of loading the program in a fixed memory, loads the program in a ‘program stack’”. As a result, “the program is freeing memory as it is executed”.
This gives the language several unusual properties, which the article lists:
- No instruction pointer. Nothing records “where” execution is. The next thing to run is simply whatever is on top of the program stack.
- Loops only through recursion. A loop is a subroutine that calls itself.
- Recursion without a call or return stack. The article says infinite recursive loops “do not overflow”. In every example, the recursive call comes last in the subroutine, so the subroutine’s body has been used up by the time it is reloaded and the program stack does not grow.
- Code as data. Program blocks can be pushed, stored, joined as strings and then executed. The article calls the language “reflection oriented (code can create code to be run on the fly)”, and the wiki files it under its Self-modifying category.
The HP calculator heritage shows in the postfix style and in instructions such as STO and RCL (store and recall), which use the same names as the HP-41C’s memory register commands.
Key Features
Two stacks and a memory area
A running GASOIL program uses three stores:
- the Program Stack (PS), which holds the code still to run;
- the Data Stack (DS), which holds operands and results;
- an addressable memory area, which
STOandRCLuse for variables.
Any cell in any of the three can hold one of four kinds of value: a floating-point number, a string in double quotes, a program instruction, or a program block in parentheses with its elements separated by semicolons, such as (1; 2; +).
The execution cycle
The interpreter repeats one step until the program stack is empty. It pops one element from the program stack. If the element is a valid instruction, it runs it. If it is a number, string or program block, it pushes it onto the data stack. Two instructions connect the stacks:
PARSEpops a program block (or a string containing one) from the data stack and pushes its elements onto the program stack in reverse order, so the first element runs next.CALLloads a named subroutine onto the program stack.CCALLdoes the same only if a condition is true.
Instruction set
| Group | Instructions |
|---|---|
| Flow control | PARSE, CALL, CCALL, STOP (pause; the user can resume), NOP (does nothing, and the rest of the element is ignored, so it doubles as a comment) |
| Extended flow control (optional) | ITE (if-then-else), WHILE, UNTIL, FOR |
| Arithmetic | +, -, *, /, MOD, SQRT, RND, INT |
| Stack | DROP…DROP4, DUP…DUP4, SWAP12, SWAP13, SWAP23, SWAP14, SWAP24, SWAP34 |
| Logic and comparison | =, >, >=, <, <=, !=, NOT, AND, OR, XOR |
| Memory | STO, RCL |
| I/O | READ, WRITE |
| Strings | & (concatenate), STRLEN, INSTR, SUBSTR, REPLACE, ASCII, CHR, STR2NUM, NUM2STR |
The stack instructions use numbered names instead of the usual Forth names such as OVER and ROT. SWAP13 exchanges the first and third elements, and DROP3 removes the third element.
Programs
In most of the wiki’s examples, a program is a series of named subroutines, each written as a name followed by a program block, and execution starts with main. (The prime-number example is a single unlabelled block.) Hello World is:
| |
Because the only way to loop is recursion, a Fibonacci sequence is a subroutine that calls itself while the newest term is below 100:
| |
DUP2 copies the two latest terms and + adds them. The new term is then compared with 100, and CCALL loads suma again only while the comparison is true. The extended structures let the same kind of loop be written as data. In (0;0;1;20;(0;RCL;+);FOR), the block (0;RCL;+) is pushed as a value and then run by FOR for each value from 1 to 20, with memory cell 0 as the counter.
Evolution
GASOIL’s whole recorded history fits into about a week. The first article and interpreter appeared on 21 August 2009 and version 0.83 on 28 August. After that, the article changed only through small edits by others: a link to Morex’s user page in September 2009, spelling and formatting fixes in 2009 and 2012, and the 2012 dead-link tag. The concepts carried on in Morex’s second language, BFI (“BrainFuck Itself”), published on 1 September 2009. BFI is a Brainfuck variant with procedures and recursion but without square brackets. Its article says its inspiration was “taken from the Brainfuck and GASOIL languages” and that, as in GASOIL, the program is loaded onto a program stack and “recursion is the only way to have loops”. Morex’s user page mentions “two or three new ideas that need some more maturity”. No further languages by Morex appear on the wiki.
Current Relevance
GASOIL is dormant. The Excel interpreter was only ever hosted on free file-hosting services: first nofeehost.com, then FileDen. The 0.83 link was tagged as dead in February 2012, and no surviving copy could be found. There is no Docker image, and no other implementation is known. The language survives only as its Esolang article. Because the article gives a complete instruction list and fully worked examples, someone could reimplement it from the article alone.
Why It Matters
GASOIL is a small but clear experiment in making the program itself consumable. Many stack languages, including Forth, PostScript and the HP calculators’ RPL, treat code as data, and they keep a return or execution stack to find their way back after a call. GASOIL drops both the fixed program store and the return stack. With nothing to jump back to, every loop has to be recursion, and according to the article such loops can run forever without overflowing, because a call made as the last step of a subroutine does not build up a return stack. The article’s own examples show the language can do practical work: a 99 Bottles of Beer program, a prime-number generator and a working Brainfuck interpreter. GASOIL also shows how the Esolang wiki worked in 2009: a newcomer could publish a language, an interpreter and examples, get a design suggestion from an established user within a week, and publish a follow-up language days later.
Timeline
Notable Uses & Legacy
Brainfuck interpreter
A Brainfuck interpreter written in GASOIL, added to the Esolang article on 26 August 2009. It reads Brainfuck source as a string, uses GASOIL memory cells as the tape, and defines a subroutine named after each Brainfuck command (>, <, +, -, ., ,, [, ]) so that each source character can be run with CALL
99 Bottles of Beer
Included in the very first version of the article. It builds the whole song as one string with the & concatenation operator, using small named subroutines for the repeated phrases and the singular/plural 'bottle(s)'
Prime number generator
A nested-FOR example on the Esolang article that tests numbers up to 50 for primality, dividing by numbers up to the integer square root. It uses an ITE block to flag non-primes and pushes a Spanish message (' es primo.') for each prime it finds