RISCOS.com

www.riscos.com Technical Support:
Programmer's Reference Manual

 

FileCore


Introduction and Overview

Under RISC OS 3.5 and earlier, FileCore-based filing systems can support 4 hard discs, each with a maximum size of 512 MB, giving a maximum storage capacity per filing system of 2 GB.

This limitation means that using hard discs larger than 512 MB would involve mounting separate partitions as 'discs'; and using discs larger than 2 GB would require multiple filing systems per disc.

With the continuing push by hard disc manufacturers to reduce the cost per megabyte of their devices, drives with less than 512 MB capacity will cease to be the most cost-effective ones. Furthermore, higher capacity drives are now becoming readily available at affordable prices.

Clearly the limitations of FileCore-based filing systems are becoming increasingly restrictive. RISC OS 3.6 introduces extensions to the logical format of FileCore-based filing systems that remove many of these restrictions, as a result of which:

  • the recommended maximum hard disc size is 4 GB
  • the maximum size of a file (and hence of an image filing system) is 231-1 bytes (2 GB)
  • the maximum number of disc objects remains 215-2 (32766).

FileSwitch based systems remain as before:

  • the maximum hard disc size is dependent on the underlying file system
  • the maximum size of a file (and hence of an image filing system) is 232-1 bytes (4 GB)
  • the maximum number of disc objects is dependent on the underlying file system.

Technical details

Disc record

The Disc record has been extended to support large discs. This uses some of the reserved bytes at the end of the record, the tail end of which now is as follows:

Offset Name Meaning
36 disc_size_2 Most significant word of disc size, in bytes
40 share_size bits 0 - 3: log2 (sharing granularity in sectors)
bits 4 - 7: reserved - must be zero
41 big_flag bit 0: set => RISC OS partition is > 512 MB
bits 1 - 7: reserved - must be zero
42 - 59 Reserved - must be zero

The disc_size_2 field gives the most significant word of the disc size, and so is used for discs of over 4 GB. (The least significant word is held in the disc_size field.)

The big_flag bit is so FileCore can tell at mount time whether or not the RISC OS filing system on the disc is big (ie > 512 MB in size), and hence whether or not it uses the new logical format. It cannot use the disc_size fields for this, since a disc of over 512 MB may only have a small RISC OS partition, and use the rest of the disc for RISC iX.

The share_size field controls the granularity of sharing. See Internal disc addresses.

Disc addresses

Physical disc addresses

FileCore performs all low-level disc access through two entry points - DiscOp and MiscOp - provided by FileCore modules such as ADFS. Disc addresses are passed to these entry points as a 32 bit quantity.

Under RISC OS 3.5 and earlier, the physical disc address combines both the drive number (0 - 7, held in bits 29 - 31), and the byte offset into the disc (0 - 512 MB, held in bits 0 - 28). It is this offset field that restricts FileCore discs to a maximum size of 512 MB.

However, some bits in the offset are redundant, since all programmer interfaces use sector aligned addresses. In RISC OS 3.6 FileCore has been enhanced to make use of these bits; it now also supports disc addresses where the offset is given in sectors, rather than in bytes. So with the resulting 29 bit sector number, and a sector size of 512 bytes (as typically used on IDE hard discs), this gives a maximum theoretical disc size of 229 × 512 bytes, or 256 GB.

Internal disc addresses

FileCore can share the use of a disc object on a new map disc (ie a logical group of fragments) between many objects (ie files or directories). The objects must either be a directory and files within that directory, or files that have the same parent directory. There may not be more than one directory in any disc object, since the directory must always be at the start of the disc object.

New map discs use an internal disc address (see Internal disc addresses) to refer to shared objects, specifying them in terms of their fragment id (0 - &7FFF), and their offset within the disc object (0 - 254, stored as 1 - 255). Under RISC OS 3.5 and earlier, the offset is in units of sectors, which with a 512 byte sector size corresponds to 0 - 127 KB. Thus FileCore can only share the first 254 sectors (127 KB for our example) of a shared disc object, and if the smallest fragment size is larger than this FileCore cannot share all the space in shared disc objects.

From RISC OS 3.6 onwards, you can increase the granularity of the offset within the disc object. It now gives the offset in units of 2share_size sectors, where share_size comes from the disc record. You should ensure that if you format a disc, share_size is sufficiently large for the following to be true:

smallest fragment size ≤ (254 × 2log2secsize × 2share_size)

FileCore can then share all the space within a shared disc object.

Defect list

The Defect list has been extended by appending a second defect list containing all defects more than 512 MB from the start of the disc. The list works similarly to the first one, but all disc addresses are stored as absolute sector numbers, and the final marker word is &400000yy. The byte yy is a check-byte calculated from the previous words in the second defect list only. It is calculated in the same way as the check-byte for the first defect list. Thus a new defect list would look like:

defect byte address(es)
&200000xx
defect sector address(es)
&400000yy

An empty defect list would now be:

&20000000
&40000000

To determine whether the second defect list is present, you should examine the big_flag byte (see Disc record). If bit 0 is set then the second defect list must be present.

Maximum practical disc size

As discs get larger, so does the smallest fragment size required to format them. For example on a 4 GB disc the smallest fragment size rises to 128K, for two reasons:

  • The maximum length of a new map is 64 KB, because the FreeLink field in the map block header (see Header) must be able to point to the end of the map, and is only two bytes long. There are hence 512K (64K × 8) allocation bits in the map.

    The allocation size is disc size / allocation bits, which is 4GB / 512K, or 8 KB.

    Therefore, the smallest fragment size is (idlen + 1) × allocation unit, which is (15 + 1) × 8 KB, or 128 KB.

  • The number of possible fragment ids is 2idlen. Since idlen cannot exceed 15, this is a maximum of 215.

    Each fragment much have available its own fragment id. The smallest fragment size is therefore (disc size / maximum fragment id), which is 4 GB / 215, or 128 KB.

You can use larger discs, but with smallest fragment sizes of 256 KB or more, you are likely to waste high proportions of disc space in normal use. For this reason we don't recommend you do so.

Disc formats

D format hard discs are not supported from RISC OS 3.5 onwards.

The RISC OS 3.6 version of FileCore supports all current E and F format discs.

Changes to existing SWIs

FileCore_DiscOp

With previous versions of FileCore, on exit from the call, R2 contains the disc address of the next byte to be transferred. From RISC OS 3.6 onwards the address returned is rounded down to be sector aligned.

FileCore_Create

The descriptor block pointed to by R0 has had a new flag bit added to indicate support for sector addressing. See Descriptor block.

FileCore_FreeSpace

The values this call returns may now be too large to represent in a single register. To avoid such problems, the values returned are limited to a maximum of &7FFFFFFF, which you may take to mean 'at least 2 GB'.

See also FileCore_FreeSpace64, a new SWI which provides facilities for returning 64 bit values.

New SWIs

The following new SWIs have been added to FileCore:

  • FileCore_MiscOp has had two reason codes added:

    FileCore_MiscOp 6 reads the information passed in a descriptor block when creating a new instantiation of a FileCore based filing system. The main use of this is to determine whether a filing system supports sector addressing, or only byte addressing.

    FileCore_MiscOp 7 returns the status of a drive; under RISC OS 3.6, this information is restricted to whether or not a drive is locked.

  • FileCore_SectorOp provides the same functionality as FileCore_DiscOp, save that it uses sector addresses rather than byte addresses.
  • FileCore_FreeSpace64 provides the same functionality as FileCore_FreeSpace, but uses 64 bit values rather than 32 bit ones.

SWI Calls


FileCore_MiscOp 6
(SWI &40549)

Reads information from a FileCore module's descriptor block

On entry

R0 = 6 (reason code)
R8 = pointer to FileCore instance private word.

On exit

R0 = pointer to block:

Offset Contains
0 bit flags from FileCore module's descriptor block
3 filing system number
4 address of filing system title
8 address of boot text
12 address of low-level disc op entry
18 address of low-level miscellaneous entry
Use

This call reads information from a FileCore module's Descriptor block, as passed to FileCore_Create. However this call returns addresses, rather than the offsets into the module that you pass to FileCore_Create.

The main use of this call is to determine whether a filing system supports sector addressing (bit 2 of the bit flags is set), or only byte addressing (bit 2 of the bit flags is clear).

This call is only available from RISC OS 3.6 onwards.


FileCore_MiscOp 7
(SWI &40549)

Returns the status of the given drive

On entry

R0 = 7 (reason code)
R1 = drive number
R8 = pointer to FileCore instance private word.

On exit

R2 = flag word:

bit 0 set => drive is locked
all other bits reserved

Use

This call returns the status of the given drive. It can be called in the background

The main use of this call is so that FileCore can cleanly check whether or not a drive is locked before restarting a background read or write operation.

This call is only available from RISC OS 3.6 onwards.


FileCore_SectorOp
(SWI &4054A)

Performs various operations on a disc using sector addressing

On entry

R1

bits 0 - 3 = reason code
bits 4 - 7 = option bits
bits 8 - 31 = bits 2 - 25 of pointer to alternative disc record, or zero

R2 = disc address
R3 = pointer to buffer
R4 = length in bytes
R6 = cache handle
R8 = pointer to FileCore instance private word

On exit

R1 preserved
R2 = disc address of next sector to which to transfer
R3 = pointer to next buffer location to be transferred
R4 = number of bytes not transferred

Interrupts

Interrupt status is undefined
Fast interrupts are enabled

Processor mode

Processor is in SVC mode

Re-entrancy

Not defined

Use

This call performs various disc operations as specified by bits 0 - 3 of R1:

Value Meaning Uses Updates
0 Verify R2, R4 R2, R4
1 Read sectors R2, R3, R4 R2, R3, R4
2 Write sectors R2, R3, R4 R2, R3, R4
3 Floppy disc: read track R2, R3
Hard disc: read Id R2, R3
4 Write track R2, R3
5 Seek (used only to park) R2
6 Restore R2
7 Floppy disc: step in †
8 Floppy disc: step out †
9 Read sectors via cache R2, R3, R4, R6 R2, R3, R4, R6
15 Hard disc: specify R2

† These reason codes are only valid with the 1772 disc controller. They are not supported on 710/711 based machines (such as the A5000) and should be avoided for future compatibility.

This call provides the same functionality as FileCore_DiscOp, save that it uses sector addresses rather than byte addresses. It is only available from RISC OS 3.6 onwards.

Option bits

The option bits have the following meanings:

Bit 4

This bit is set if an alternate defect list for a hard disc is to be used. This is assumed to be in RAM 64 bytes after the start of the disc record pointed to by bits 8 - 31 of R1 shifted left 6 bits (so they form bits 2 - 25 of the pointer).

This bit may only be set for old map discs.

Bit 5

If this bit is set, then the meaning of R3 is altered. It does not point to the area of RAM to or from which the disc data is to be transferred. Instead, it points to a word-aligned list of memory address/length pairs. All but the last of these lengths must be a multiple of the sector size. These word-pairs are used for the transfer until the total number of bytes given in R4 has been transferred.

On exit, R3 points to the first pair which wasn't fully used, and this pair is updated to reflect the new start address/bytes remaining, so that a subsequent call would continue from where this call has finished.

This bit may only be set for reason codes 0 - 2.

Bit 6

If this bit is set then escape conditions are ignored during the operation, otherwise they cause it to be aborted.

Bit 7

If this bit is set, then the usual timeout for floppy discs of 1 second is not used. Instead FileCore will wait (forever if necessary) for the drive to become ready.

Disc address

The disc address is a sector offset from the start of the disc. It must be on a track boundary for reason codes other than 0-2 and 9. Note that you must make allowances for any defects, as the disc address is not corrected for them.

For reason code 6 (restore), the disc address is only used for the drive number; the bottom 29 bits should be set to zero.

Where the transfer length is not a multiple of the sector size, the end disc address specifies the sector holding the byte after the last one that was transferred.

The specify disc command (reason code 15) sets up the defective sector list, hardware information and disc description from the disc record supplied. Note that in memory, this information must be stored in the order disc record, then defect list/hardware parameters.

Read Track/ID (reason code 3)

If the alternate defect list option bit (bit 4) is set in R1 on entry when reading a track/ID, then a whole track's worth of ID fields is read. This usage is not available under RISC OS 2.

The call reads 4 bytes of sector ID information into the buffer pointed to by R3 for every sector on the track. The order of data is:

Cylinder
Head
Sector number
Sector size (0= 128, 1= 256, etc)

For floppy discs, the operation is terminated after 200mS (1 revolution).

The first sector ID transferred will normally be that following the index mark (it may be the second if there is abnormal interrupt latency from the index pulse interrupt). The first two ID's read may also be duplicated at the buffer end due to interrupt latency. Consequently the buffer should be at least 16 bytes longer than the maximum number of IDs expected (512 bytes at most).

The disc record provided is updated to return the actual number of sectors per track found (at offset 1). Note to use this option you must provide a valid defect list following on after the disc record. The minimal defect list is a word of &20000000 for small discs (ie byte addressed), or two words of &20000000 followed by &40000000 for large discs (ie sector addressed).

Write Track (reason code 4)

If R3 (the buffer pointer) is non-zero on entry, this reason code is used to write a track. This usage is specific to the 1772 disc controller.

If R3 is zero on entry, this reason code is instead used to format a track; R4 then points to a disc format structure. This usage is available with all controllers, but is not available under RISC OS 2.

The disc format structure pointed to by R4 is as follows:

Offset Length Meaning
0 4 Sector size in bytes (which must be a multiple of 128)
4 4 Gap1
8 4 Reserved - must be zero
12 4 Gap3
16 1 Sectors per track
17 1 Density:
1 single density (125Kbps FM)
2 double density (250Kbps FM)
3 double+ density (300Kbps FM)
(ie higher rotation speed double density)
4 quad density (500Kbps FM)
8 octal density (1000Kbps FM)
18 1 Options:
bit 0 1 index mark required
bit 1 1 double step
bits 2-3 0 interleave sides
1 - 3 sequence sides
bits 4-7 reserved - must be 0
19 1 Sector fill value
20 4 Cylinders per drive (normally 80)
24 12 Reserved - must be 0
36 ? Sector ID buffer, 1 word per sector:
bits 0 - 7 Cylinder number mod 256
bits 8 - 15 Head (0 for side 1, 1 for side 2)
bits 16 - 23 Sector number
bits 24 - 31 Log2 (sector size) - 7, eg 1 for 256 byte sector

An error is generated if the specified format is not possible to generate, or if the track requested is outside the valid range. The tracks are numbered from 0 to (number of tracks) - 1. The mapping of the address is controlled by the disc structure record.

Read sectors via cache (reason code 9)

This reason code reads sectors via a cache held in the RMA. It is not available under RISC OS 2.

To start a sequence of these operations, set R6 (the cache handle) to zero on entry. Its value will be updated on exit, and subsequent calls should use this new value.

Bits 4 - 7 of R1 should be zero, and are ignored if set.

To discard the cache once finished, call FileCore_DiscardReadSectorsCache.

Related SWIs

None

Related vectors

None


FileCore_FreeSpace64
(SWI &4054B)

Returns 64 bit information on a disc's free space

On entry

R0 = pointer to disc specifier (null terminated)
R8 = pointer to FileCore instance private word

On exit

R0 = bits 0 - 31 of total free space on disc
R1 = bits 32 - 63 of total free space on disc
R2 = size of largest object that can be created, or &7FFFFFFF if 2 GB or more

Interrupts

Interrupt status is undefined
Fast interrupts are enabled

Processor mode

Processor is in SVC mode

Re-entrancy

Not defined

Use

This call returns the total free space on the given disc, and the largest object that can be created on it. As with FileCore_FreeSpace, the returned size of largest object is restricted to a maximum of &7FFFFFFF, meaning 'at least 2 GB'.

This call is only available from RISC OS 3.6 onwards.

Related SWIs

None

Related vectors

None

This edition Copyright © 3QD Developments Ltd 2015
Last Edit: Tue,03 Nov 2015