Skip to main content

oaknut-file

PyPI version CI Python versions License: MIT

Acorn file metadata handling for the oaknut package family.

oaknut-file is the shared metadata layer used across the oaknut family — by oaknut-dfs, oaknut-adfs, oaknut-afs, oaknut-zip, and the disc CLI. It provides:

  • The Access IntFlag enum for Acorn file attribute bytes
  • The AcornMeta dataclass for load/exec addresses and attributes
  • INF sidecar file parsing and formatting (traditional and PiEconetBridge variants)
  • Filename metadata encoding (,xxx, ,llllllll,eeeeeeee, ,load-exec)
  • Extended attribute read/write under user.acorn.* and user.econet_*

Installation

Using uv (recommended):

uv add oaknut-file

pip install oaknut-file also works.

The xattr package is automatically installed on macOS, where it is required for extended attribute support. Linux uses os.setxattr from the standard library and needs no additional dependency. Windows does not support extended attributes; the xattr functions will raise on use.

Quick start

Access flags

The Access IntFlag enum represents the standard Acorn OSFILE attribute byte, as stored in traditional .inf files and the user.acorn.attr extended attribute. (PiEconetBridge's own perm byte uses a different layout; see below.)

from oaknut.file import Access

# Compose flags with bitwise OR
flags = Access.R | Access.W | Access.L
print(repr(flags))  # <Access.LWR: 11>
print(hex(flags))  # 0xb
Flag Value Meaning
Access.R 0x01 Owner read
Access.W 0x02 Owner write
Access.E 0x04 Owner execute
Access.L 0x08 Locked — prevents delete, overwrite, and rename on the disc filing systems
Access.PR 0x10 Public read
Access.PW 0x20 Public write

A *RUN-only file — one that may be *RUN but not *LOADed, the cassette/ROM copy protection — is owner E without R, which Access.is_run_only tests. It is a distinct axis from Access.L (locked): a delete-locked disc file is not run-only. Access.WR and Access.LWR are provided as convenience composites for the common owner-read+write and locked-owner-read+write cases.

INF sidecar files

Two INF sidecar formats are supported. parse_inf_line() auto-detects which format a line uses, while format_trad_inf_line() and format_pieb_inf_line() let you choose explicitly when writing.

Traditional .inf files are read and written per the Stardot INF format specification, with J.G. Harston's defaults (Storing Acorn/BBC metadata on other systems) where it leaves room: a missing access field means &33, a Locked or bare L marker &19, and a missing exec address is the load address. Quoted and percent-encoded names, the TAPE prefix, extra fields such as CRC= and NEXT are understood, and six-digit DFS-style addresses (FF0E00) are widened to &FFFF0E00. A name is held in its medium's own character set: format_trad_inf_line, parse_inf_line and read_inf_file take that codec as encoding (for example "acorn" for DFS, where £ is byte &60), and export_with_metadata and import_with_metadata take it as name_encoding. Each defaults to Latin-1.

PiEconetBridge's perm byte swaps the lock (0x04) and execute-only (0x08) bits relative to the Acorn byte, and uses 0x80 for hidden. The PiEB INF and user.econet_perm functions translate it, so callers always see the Acorn byte.

from oaknut.file import (
    Access,
    format_trad_inf_line,
    format_pieb_inf_line,
    parse_inf_line,
)

# Traditional INF: filename load exec length [attr]
trad = format_trad_inf_line(
    filename="HELLO",
    load_address=0x1900,
    exec_address=0x8023,
    length=0x100,
    attr=int(Access.R | Access.W),
)
print(trad)
# HELLO       00001900 00008023 00000100 03

# PiEconetBridge INF: owner load exec perm
pieb = format_pieb_inf_line(
    load_address=0xFFFFDD00,
    exec_address=0xFFFFDD00,
    attr=int(Access.R | Access.W | Access.L | Access.PR),
)
print(pieb)
# 0 ffffdd00 ffffdd00 17   (LWR/R in PiEB's own perm layout)

# Auto-detect format on parse (returns (source_label, AcornMeta))
source, meta = parse_inf_line(trad)
print(meta.load_address, meta.exec_address, meta.access)
# 6400 32803 3

source, meta = parse_inf_line(pieb)
print(hex(meta.load_address), hex(meta.access), hex(meta.infer_filetype()))
# 0xffffdd00 0x1b 0xfdd

Filename metadata encoding

Three filename suffix conventions are supported for embedding load/exec addresses or RISC OS filetypes in host filenames.

from oaknut.file import parse_encoded_filename

# RISC OS filetype suffix (3 hex digits)
clean, meta = parse_encoded_filename("PROG,ffb")
print(clean, hex(meta.infer_filetype()))
# PROG 0xffb

# MOS load-exec suffix (variable-width hex)
clean, meta = parse_encoded_filename("PROG,1900-801f")
print(clean, hex(meta.load_address), hex(meta.exec_address))
# PROG 0x1900 0x801f

Filetype-stamped load addresses

When a load address has its top 12 bits set to 0xFFF, the next 12 bits encode a RISC OS filetype.

from oaknut.file import AcornMeta

meta = AcornMeta(load_address=0xFFFF0E10)
print(meta.is_filetype_stamped, hex(meta.infer_filetype()))
# True 0xf0e

Extended attributes

from oaknut.file import write_acorn_xattrs, read_acorn_xattrs

# Write to user.acorn.* namespace
write_acorn_xattrs(
    "myfile.bin",
    load_address=0x1900,
    exec_address=0x8023,
    attr=0x03,
)

# Read back (falls through to user.econet_* if user.acorn.* is absent)
meta = read_acorn_xattrs("myfile.bin")
print(meta.load_address, meta.exec_address, meta.access)

Public API

Module Exports
oaknut.file.access Access, parse_access, parse_access_spec, format_access_hex, format_access_text
oaknut.file.access_convention AccessConvention, AccessContext, FILE_CONTEXT, DIRECTORY_CONTEXT, translate_access
oaknut.file.pieb PiEconetBridgeAccessConvention, PIEB_ACCESS
oaknut.file.meta AcornMeta
oaknut.file.formats MetaFormat, SOURCE_* labels
oaknut.file.inf parse_inf_line, format_trad_inf_line, format_pieb_inf_line, read_inf_file, write_inf_file
oaknut.file.filename_encoding parse_encoded_filename, build_filename_suffix, build_mos_filename_suffix
oaknut.file.xattr read_acorn_xattrs, write_acorn_xattrs, read_econet_xattrs, write_econet_xattrs

All public symbols are also re-exported from the top-level oaknut.file package.

License

MIT

Metadata

Release files for oaknut-file 13.1.3

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for oaknut-file 13.1.3
File Size Uploaded
oaknut_file-13.1.3.tar.gz 58.5 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for oaknut-file 13.1.3
File Interpreter ABI Platform
oaknut_file-13.1.3-py3-none-any.whl Python 3 none any Details

Total release size: 102.0 kB

Release files / oaknut_file-13.1.3.tar.gz

Download URL oaknut_file-13.1.3.tar.gz
Size 58.5 kB
Tags Source
SHA-256 checksum
How to use checksums
d39409f8283d63d409e3d0d92d9dc964c537db284ff71480426210e2b9e35d8a
BLAKE2b-256 checksum
How to use checksums
d2a3cba36316ccb3cb7d1723025cc487d29d3f27d95676d395b1c06a1b06c752
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.12.22 {"installer":{"name":"uv","version":"0.12.22","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release files / oaknut_file-13.1.3-py3-none-any.whl

Download URL oaknut_file-13.1.3-py3-none-any.whl
Size 43.4 kB
Tags Python 3
SHA-256 checksum
How to use checksums
2ed9965c2db435b6b71491f23c3b3c87ea647a980bd08a6e906846557a448ff3
BLAKE2b-256 checksum
How to use checksums
6a91d32efa3b966a74ffe9f312c172d614b69c481e67b3702aa579a164d26beb
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via uv/0.12.22 {"installer":{"name":"uv","version":"0.12.22","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}

Release history Release notifications | RSS feed

13.4.0

2 release files

13.3.1

2 release files

This release

13.1.3 This release

2 release files

13.1.0

2 release files

13.0.0

2 release files

12.9.0

2 release files

12.8.2

2 release files

12.8.1

2 release files

12.8.0

2 release files

12.7.2

2 release files

12.7.1

2 release files

12.7.0

2 release files

12.5.0

2 release files

12.4.1

2 release files

12.4.0

2 release files

12.3.0

2 release files

12.2.0

2 release files

12.1.0

2 release files

12.0.1

2 release files

12.0.0

2 release files

11.2.0

2 release files

11.1.0

2 release files

11.0.2

2 release files

11.0.1

2 release files

11.0.0

2 release files

10.7.0

2 release files

10.6.0

2 release files

10.5.0

2 release files

10.4.0

2 release files

10.3.0

2 release files

10.2.0

2 release files

10.1.0

2 release files

10.0.5

2 release files

10.0.4

2 release files

10.0.3

2 release files

10.0.2

2 release files

10.0.1

2 release files

1.0.0

2 release files

0.1.3

1 release file

0.1.2

1 release file

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page