Skip to content

Seashell Syntax (STALE)

Rachit Nigam edited this page Feb 10, 2019 · 1 revision

Documentation

This page describes the behavior and syntax of Seashell.

Table of Contents

Types

Available Types

  • float
  • int
  • bool

Type Aliases

Create a type alias like so:

type number = int;

Then number can be used in place of int anywhere in your program.

Assignment

Assign an expression to a variable (no type declaration required):

let x = 2;

Reassignment:

x := 5;

Functions

Define a function with the following syntax:

func my_func(array_arg: int[10] bank(5), int_arg: int) {
  ...
}

Functions in Seashell represent hardware functions. These must be called from host code written in C.

Argument Annotations

Arguments require type annotations. For arrays, you must supply the size. Supplying the banking factor as in the example above is optional: the default banking factor (if none is supplied) is 1.

Return Statements

There are no return statements in Seashell.

Arrays

Declaration

Currently arrays cannot be explicitly declared: they are passed in as function arguments from the host code. The type annotations in the function will impose the appropriate type constraints on the body of the function.

Access

There are two ways to access arrays in Seashell: physically and logically.

Physical Array Access

To physically access an array, you need to supply the bank you'd like to access, and then an index into this bank. The syntax looks like this:

array_name{bank_number}[index_into_bank]

In general, bank_number should be a static integer, if you don't want any multiplexing. If you want to use multiplexing to dynamically select a bank, you must explicitly declare so. See the section on mulitiplexing for more information.

Constraints on Array Accesses

For explicit access, you can only index into a particular bank once. This means that in the body of a for loop, the expression a[0][1] cannot appear more than once. It's overly restrictive, as it would be safe to access it multiple times for reads - but to accomplish this, you'll need to make use of a local variable to store the array access read.

For implicit access, say we have a loop that's unrolled 5 times: an implicit access like in the implicit access example would index into every single bank of the array at once, so no more array accesses would be permitted.

Loops

Loops have this syntax:

for (let i = 0..9) {
  ...
}

You can also specify an unrolling factor like this:

for (let i = 0..9) unroll 3 {
  ...
}

The unroll keyword will influence the type of i; indeed, it will become a special index type with a static component and a dynamic component - it'll represent multiple values simultaneously. See the access section for information on its usage.

Multiplexers

You can use multiplexers to dynamically select banks in a memory. You must first declare a multiplexer, using syntax like this:

mux 5 mux_name(array_name);

Here, 5 is the number of input lines in the mux. You can then dynamically access banks in array_name using any kind of access you like.

For example, physical access:

for (let i = 0..4) {
  mux_name{i}[0] := 5;
}

Or logical access (where otherwise you'd need to use an index type with static information):

for (let i = 0..4) {
  mux_name[i] := 5;
}