www.delorie.com/gnu/docs/gforth/gforth_135.html   search  
Buy GNU books!

Gforth Manual

[ < ] [ > ]   [ << ] [ Up ] [ >> ]         [Top] [Contents] [Index] [ ? ]

5.17 Blocks

When you run Gforth on a modern desk-top computer, it runs under the control of an operating system which provides certain services. One of these services is file services, which allows Forth source code and data to be stored in files and read into Gforth (see section 5.16 Files).

Traditionally, Forth has been an important programming language on systems where it has interfaced directly to the underlying hardware with no intervening operating system. Forth provides a mechanism, called blocks, for accessing mass storage on such systems.

A block is a 1024-byte data area, which can be used to hold data or Forth source code. No structure is imposed on the contents of the block. A block is identified by its number; blocks are numbered contiguously from 1 to an implementation-defined maximum.

A typical system that used blocks but no operating system might use a single floppy-disk drive for mass storage, with the disks formatted to provide 256-byte sectors. Blocks would be implemented by assigning the first four sectors of the disk to block 1, the second four sectors to block 2 and so on, up to the limit of the capacity of the disk. The disk would not contain any file system information, just the set of blocks.

On systems that do provide file services, blocks are typically implemented by storing a sequence of blocks within a single blocks file. The size of the blocks file will be an exact multiple of 1024 bytes, corresponding to the number of blocks it contains. This is the mechanism that Gforth uses.

Only one blocks file can be open at a time. If you use block words without having specified a blocks file, Gforth defaults to the blocks file `blocks.fb'. Gforth uses the Forth search path when attempting to locate a blocks file (see section Source Search Paths).

When you read and write blocks under program control, Gforth uses a number of block buffers as intermediate storage. These buffers are not used when you use load to interpret the contents of a block.

The behaviour of the block buffers is analagous to that of a cache. Each block buffer has three states:

Initially, all block buffers are unassigned. In order to access a block, the block (specified by its block number) must be assigned to a block buffer.

The assignment of a block to a block buffer is performed by block or buffer. Use block when you wish to modify the existing contents of a block. Use buffer when you don't care about the existing contents of the block(30).

Once a block has been assigned to a block buffer using block or buffer, that block buffer becomes the current block buffer. Data may only be manipulated (read or written) within the current block buffer.

When the contents of the current block buffer has been modified it is necessary, before calling block or buffer again, to either abandon the changes (by doing nothing) or mark the block as changed (assigned-dirty), using update. Using update does not change the blocks file; it simply changes a block buffer's state to assigned-dirty. The block will be written implicitly when it's buffer is needed for another block, or explicitly by flush or save-buffers.

word Flush writes all assigned-dirty blocks back to the blocks file on disk. Leaving Gforth with bye also performs a flush.

In Gforth, block and buffer use a direct-mapped algorithm to assign a block buffer to a block. That means that any particular block can only be assigned to one specific block buffer, called (for the particular operation) the victim buffer. If the victim buffer is unassigned or assigned-clean it is allocated to the new block immediately. If it is assigned-dirty its current contents are written back to the blocks file on disk before it is allocated to the new block.

Although no structure is imposed on the contents of a block, it is traditional to display the contents as 16 lines each of 64 characters. A block provides a single, continuous stream of input (for example, it acts as a single parse area) -- there are no end-of-line characters within a block, and no end-of-file character at the end of a block. There are two consequences of this:

In Gforth, when you use block with a non-existent block number, the current blocks file will be extended to the appropriate size and the block buffer will be initialised with spaces.

Gforth includes a simple block editor (type use blocked.fb 0 list for details) but doesn't encourage the use of blocks; the mechanism is only provided for backward compatibility -- ANS Forth requires blocks to be available when files are.

Common techniques that are used when working with blocks include:

See Frank Sergeant's Pygmy Forth to see just how well blocks can be integrated into a Forth programming environment.

doc-open-blocks doc-use doc-block-offset doc-get-block-fid doc-block-position

doc-list doc-scr

doc--gforthman-block doc-buffer

doc-empty-buffers doc-empty-buffer doc-update doc-updated? doc-save-buffers doc-save-buffer doc-flush

doc-load doc-thru doc-+load doc-+thru doc--gforthman---> doc-block-included

[ < ] [ > ]   [ << ] [ Up ] [ >> ]         [Top] [Contents] [Index] [ ? ]

  webmaster     delorie software   privacy  
  Copyright 2003   by The Free Software Foundation     Updated Jun 2003