SIC-1 Assembly Language

From Esolang
Jump to navigation Jump to search

SIC-1 Assembly Language is the primary (and, currently, only) language used for programming SIC Systems's Single-Instruction Computer, Mark 1 (SIC-1). The SIC-1 is a fictional 8-bit computer used in a web-based programming game (of the same name--see #External Resources for a link) that, as its name implies, only supports a single instruction: subleq (subtract and branch if less than or equal to zero).

Language Overview

Command Description
subleq A B [C] mem[A] = mem[A] - mem[B]; branch to C if result <= 0
@label Associates a label with the address of the following command
.data X Sets the next byte of memory to a value at compile time

Note that if the third address (C) for subleq is omitted, the address of the next instruction is used (in other words, the branch would have no noticeable effect).

Binary representation and offsets

Each subleq A B C instruction is stored as 3 consecutive addresses (each one byte): ABC.

When referring to a label, you can include an offset (specified in bytes), e.g. @label+1. See the self-modifying code example for a practical application of this.

Built-in labels

The following predefined lables are always available:

  • @MAX (252): Maximum user-modifiable address
  • @IN (253): Reads a value from input (writes are ignored)
  • @OUT (254): Writes a result to output (reads as zero)
  • @HALT (255): Terminates the program when executed

Examples

Negation

This program negates one input value and outputs the negated value.

subleq @OUT, @IN

Continuous negation

This program reads values, negates them, and outputs them in an infinite loop.

@loop:
subleq @OUT, @IN
subleq @zero, @zero, @loop

@zero: .data 0

Self-modifying/referencing code

The sample program below reads its own compiled code and outputs it by incrementing the second address of the instruction at @loop (i.e. modifying address @loop+1).

@loop:
subleq @tmp, 0           ; Second address (initially zero) will be incremented
subleq @OUT, @tmp        ; Output the value
subleq @loop+1, @n_one   ; Here is where the increment is performed
subleq @tmp, @tmp, @loop

@tmp: .data 0
@n_one: .data -1

External Resources