Next: , Previous: Memory Access, Up: Memory


5.7.5 Address arithmetic

Address arithmetic is the foundation on which you can build data structures like arrays, records (see Structures) and objects (see Object-oriented Forth).

ANS Forth does not specify the sizes of the data types. Instead, it offers a number of words for computing sizes and doing address arithmetic. Address arithmetic is performed in terms of address units (aus); on most systems the address unit is one byte. Note that a character may have more than one au, so chars is no noop (on platforms where it is a noop, it compiles to nothing).

The basic address arithmetic words are + and -. E.g., if you have the address of a cell, perform 1 cells +, and you will have the address of the next cell.

In ANS Forth you can perform address arithmetic only within a contiguous region, i.e., if you have an address into one region, you can only add and subtract such that the result is still within the region; you can only subtract or compare addresses from within the same contiguous region. Reasons: several contiguous regions can be arranged in memory in any way; on segmented systems addresses may have unusual representations, such that address arithmetic only works within a region. Gforth provides a few more guarantees (linear address space, dictionary grows upwards), but in general I have found it easy to stay within contiguous regions (exception: computing and comparing to the address just beyond the end of an array).

ANS Forth also defines words for aligning addresses for specific types. Many computers require that accesses to specific data types must only occur at specific addresses; e.g., that cells may only be accessed at addresses divisible by 4. Even if a machine allows unaligned accesses, it can usually perform aligned accesses faster.

For the performance-conscious: alignment operations are usually only necessary during the definition of a data structure, not during the (more frequent) accesses to it.

ANS Forth defines no words for character-aligning addresses. This is not an oversight, but reflects the fact that addresses that are not char-aligned have no use in the standard and therefore will not be created.

ANS Forth guarantees that addresses returned by CREATEd words are cell-aligned; in addition, Gforth guarantees that these addresses are aligned for all purposes.

Note that the ANS Forth word char has nothing to do with address arithmetic.

chars       n1 – n2         core       “chars”

n2 is the number of address units of n1 chars.""

char+       c-addr1 – c-addr2        core       “char-plus”

1 chars +.

cells       n1 – n2        core       “cells”

n2 is the number of address units of n1 cells.

cell+       a-addr1 – a-addr2        core       “cell-plus”

1 cells +

cell       – u         gforth       “cell”

Constant1 cells

aligned       c-addr – a-addr        core       “aligned”

a-addr is the first aligned address greater than or equal to c-addr.

floats       n1 – n2        float       “floats”

n2 is the number of address units of n1 floats.

float+       f-addr1 – f-addr2        float       “float-plus”

1 floats +.

float       – u         gforth       “float”

Constant – the number of address units corresponding to a floating-point number.

faligned       c-addr – f-addr        float       “f-aligned”

f-addr is the first float-aligned address greater than or equal to c-addr.

sfloats       n1 – n2        float-ext       “s-floats”

n2 is the number of address units of n1 single-precision IEEE floating-point numbers.

sfloat+       sf-addr1 – sf-addr2         float-ext       “s-float-plus”

1 sfloats +.

sfaligned       c-addr – sf-addr        float-ext       “s-f-aligned”

sf-addr is the first single-float-aligned address greater than or equal to c-addr.

dfloats       n1 – n2        float-ext       “d-floats”

n2 is the number of address units of n1 double-precision IEEE floating-point numbers.

dfloat+       df-addr1 – df-addr2         float-ext       “d-float-plus”

1 dfloats +.

dfaligned       c-addr – df-addr        float-ext       “d-f-aligned”

df-addr is the first double-float-aligned address greater than or equal to c-addr.

maxaligned       addr1 – addr2         gforth       “maxaligned”

addr2 is the first address after addr1 that satisfies all alignment restrictions. maxaligned"

cfaligned       addr1 – addr2         gforth       “cfaligned”

addr2 is the first address after addr1 that is aligned for a code field (i.e., such that the corresponding body is maxaligned).

ADDRESS-UNIT-BITS       – n         environment       “ADDRESS-UNIT-BITS”

Size of one address unit, in bits.

/w       – u         gforth       “slash-w”

address units for a 16-bit value

/l       – u         gforth       “slash-l”

address units for a 32-bit value