Introduction

The build in assembler of logisim-evolution supports besides the instructions provided by the used processor several features as described in this help page.The assembler uses syntax highlighting and error detection. Furthermore it translates the instructions into byte-code that can be executed by the processor. Although the structure of the assembler would allow to write out an elf-file this feature is not yet implemented.

Using the GUI

When opening the assembler you are presented with a new window as shown below:

assembler

The GUI consists of three components:

  1. The tool bar which is on top of the editing area.
  2. The line indication bar with error indicators to the left of the editing area.
  3. The editing area.

The toolbar

The toolbar provides the main functions of the assembler by use of several icons:

load This icon activates the loading of an assembly file into the editing area. The load function can also be activated by the keyboard shortcut (Ctrl-L).

save This icon activates the saving of the current contents in the editing area. The save function can also be activated by the keyboard shortcut (Ctrl-S).

save as This icon activates the save-as function of the current contents in the editing area. The save-as function has no keyboard shortcut.

assemble This icon activates the assemble function of the current contents in the editing area. The assemble function cal also be activated by the keyboard shortcut (ALT-A).

previous error This icon jumps to an error detected before the current cursor position. This function is also available by the keyboard shortcut (Ctrl-P).

next error This icon jumps to an error detected after the current cursor position. This function is also available by the keyboard shortcut (Ctrl-N).

run This icon activated the assemble function and, when no errors are detected, loads the program into memory. The run function can also be activated by the keyboard shortcut (ALT-R).

help This icon show this help screen.

To the right of the toolbar the current line of the cursor and the total number of lines in the editing area are displayed. In case this indicator lights up yellow there are changes detected in the editing area.

The line indicator bar

The line indicator bar hold, besides the current line number, also the error indicator icons. Hovering over the error indicator bar will show (one of) the error(s) detected on the given line in the editing area.

The editing area

The editing area contains all the code you might want to use. In case your code contains errors (after activating the assemble or run function) the errors will be displayed by an error icon in the line indicator bar and a small red line underneath the text causing the problem. hovering over this text with the mouse will display the error cause. It is important to note that, when multiple errors are present in one line, only one will be displayed by the error marker in the line indicator bar. Furthermore, in case of calculations (like in line 17 in the above showed image) it might be that only the 8 is marked instead of the complete calculation.

Using calculations

The assembler supports two types of calculations:

  1. Program counter (PC) relative calculations
  2. Absolute calculations

Program counter relative calculations

In case an address is required relative to the current program counter these calculations can be performed by using the reserved register pc. Also the usage of labels and constants are allowed in these calculations.

Examples: pc+8 , pc-0x40, mylabel-pc, etc.

Absolute calculations

In absolute calculations a constant value is calculated. To perform absolute calculations labels and constants are allowed.

Calculation types

Following calculation types are supported:

Note: Currently the parentheses are not supported.

Calculation order

Important: For the moment the calculations are performed left-to-right independent of the hierarchy of the operator!

This means:

5+10*2 is calculated as (5+10)*2 = 30

10*2+5 is calculated as (10*2)+5 = 25

It is on the todo list to improve this poor calculation support.

Using macros

The build in assembler supports macros. The syntax for a macro is:

.macro <name> <nr_of_variables>

<BODY>

.endm

A macro definition needs two parameters:

  1. <name> This parameter is the name of the macro to be used in the rest of your program.
  2. <nr_of_variables> This parameter specifies the number of variables that are used inside the macro. This parameter should be a positive integer value (e.g. 0,1,2,....)

Allowed constructs inside a macro

Inside a macro you can use only instructions, labels, calculations, and calls to other macros. It is important to note that labels defined inside the <BODY> of a macro are local to the macro and cannot be referenced outside the macro.

Using variables inside a macro

If the parameter <nr_of_variables> is a number bigger than 0, the macro must be called with this number of values. Each of this values can be referenced inside a macro with the indicator @<x> where <x> is a number. Hence @1 references parameter 1, @2 parameter 2, etc.

Using macro calls inside a macro

Macros allow to call other macros, however there are two restrictions:

  1. A macro cannot call itself; recursive macros are not supported.
  2. Two macros cannot call each other; circular calls are not supported.

Assembler directives

There are several directives supported as described below.

Labels

Labels can be used by the syntax <name>: The <name> must start with a letter and may contain letters (a..z;A..Z), numbers (0..9), and underscores (_). Note that labels specified inside a macro are local to the macro. All other labels are global (hence a global label can be referenced inside a macro).

Named constants

Named constants can be defined by the syntax .equ <name> <value>. The <name> parameter must start with a letter and may contain letters (a..z;A..Z), numbers (0..9), and underscores (_). The <value> field can contain a number or a calculation.

Sections

You can divide your program into sections by using .section <name>. The <name> parameter must start with a letter and may contain letters (a..z;A..Z), numbers (0..9), and underscores (_). There are four predefined section names being .text, .data, .rodata, .bss. These do not require the .section keyword in front of them.

Remarks

Remarks are supported by placing a # in front of them and extend until the end of the line. Multi line remarks can be realized by putting in front of each line the #.

Strings

Strings can be specified by .string "<str>", .ascii"<str>", or .asciz"<str>". The <str> can contain any contents and may be multiple lines. Following escape codes can be used:

  1. \n -> insert a new-line character.
  2. \" -> insert a double quote.
  3. \t -> insert a tab-character.
  4. \r -> insert a carriage return character.
  5. \f -> insert a form feed.
  6. \\ -> insert a back slash.

Both .string and .asciz will automatically insert a zero character at the end of the string.

Memory addresses

By default the assembler will start at memory address 0x00000000. To be able to change the current memory address the directive .org <address> can be used, where the <address> is a value within a 32-bit address space. Note: only inter-section overlap will be checked by the assembler. If inside a section an address is specified that is already being occupied, the values are overwritten.

Constants

There are several ways to fill the memory with constant values. Besides from the byte-based way, all the others use a little-endian storage method, meaning that the least significant byte is stored at the lowest memory address, and the most significant byte at the highest memory address. The supported directives are:

  1. .byte <value1>[,<value2>,...] This directive stores the value(s) interpreted as bytes one after the other into memory.
  2. .half <value1>[,<value2>,...]
    .2byte <value1>[,<value2>,...]
    .short <value1>[,<value2>,...] These directives store the value(s) interpreted as 16-bit values one after the other into memory.
  3. .word <value1>[,<value2>,...]
    .4byte <value1>[,<value2>,...]
    .long <value1>[,<value2>,...] These directives store the value(s) interpreted as 32-bit values one after the other into memory.
  4. .dword <value1>[,<value2>,...]
    .8byte <value1>[,<value2>,...]
    .quad <value1>[,<value2>,...] These directives store the value(s) interpreted as 64-bit values one after the other into memory.