Score Perfect Professional 1-4 file format
Article by Maarten Tromp | Published | 5389 words
Introduction
This document describes the *.son file format of Score Perfect Professional up to version 4, as far as it is known.
Background information on the project can be found on the project page. This document describes the .son files of Score Perfect Professional (SPP) 1.4 to 4.94, as far as they are understood: enough to convert their notes, lyrics, marks, slurs, hairpins, texts, voltas, clef changes, multi-measure rests, ottavas and grace notes to MusicXML. Each finding says how it was checked. What is known, guessed and still unknown is listed under Status.
Many fields are those of the SPP 5–7 format, in another arrangement: both are by the same developer. Where a code is the same, this page links to the SPP 5-7 file format page, which has the tables.
The converter, spp2musicxml, implements what is described here (spp4.py); where this document and the converter differ, the converter is more likely right.
In this article:
How far this format is understood, in numbers, and what is known, guessed and still open. The numbers are against the 116 songs of the corpus that SPP Lite 5.1 could open and save again in the SPP 5–7 format (the twins), and against PriMus' son2emil. Of the 119 songs of this format in the corpus, the 3 of SPP 1.0 cannot be opened by Lite; all 119 are read, and the 5 of SPP 1.2-K are another format.
| what | result
|
|---|
| songs read | 119 of 119; 116 with a twin
|
| measures | the number agrees with the twin in 116 of 116
|
| notes | 205,203 notes in the twins, 204,942 of them the same in type, dots, rest and pitch (99.9 %)
|
| time signatures, voltas | the same as the twin in 116 of 116 songs, measure by measure
|
| bar lines | 112 of 116 songs (the rest differ by multi-measure rests)
|
| grace notes | 369, the same as the twins in 116 of 116 songs
|
| marks and lyrics | 96 % of the notes that have them agree with the twins; most of the rest are one note off, in songs with several voices on a staff
|
| slurs | 7484 starts and stops the same as SPP Lite 5.1's, 344 only ours and 140 only SPP Lite's (where it differs it is shifted, as with voltas and texts)
|
| hairpins | 271 ends the same as son2emil's, 7 only ours and 5 only son2emil's
|
| tempo | equal to the twin in 116 of 116
|
| title | the same as the twin's in 67 of the 69 songs that kept one (the other two differ in the characters)
|
What the reader finds in these songs and does not understand (the finding, its count, and in how many songs):
| finding | count | songs | what it is
|
|---|
| tie to another pitch | 7 | 3 | a tie to a note that does not have the tone: 2 songs' worth of single cases (it was 2529 when the flag below was taken for all tones)
|
| slur ends outside the song | 82 | 15 | the slurs where SPP Lite's differs, above
|
unknown ornament 7e | 144 | 1 | a small zigzag below the note: tried in SPP Lite 5.1, see the marks of the SPP 5–7 format
|
unknown ornaments 84, 88, 90, 6b, 13, 12 | 24, 17, 12, 12, 9, 5 | 1 to 3 each | a bass clef sign, two short strokes, a small wave, a natural and a flat sign: tried in SPP Lite 5.1 (same marks page); the converter writes the natural and the flat
|
optional records not understood, mask 10 and 04 | 60 and 28 | 2 and 1 | a record after the tones with a mask bit that does not read as it should
|
Checked against the twins, son2emil or SPP's own screen (each finding below says how):
- The header, the staff records (vertical place, transposition, clef, number of measures, instrument), the time signature table and the three per-measure arrays (time signature, key, bar line).
- The notes: type, dots, stem, beams, cue, tones and accidentals, ties, rests; the tempo, the title rule; texts, voltas, clef changes, multi-measure rests, ottavas (codes 1 to 8), grace notes, tuplets.
- Optional records: lyrics, marks (the codes known from the SPP 5–7 format), slurs (also where they end), hairpins (also where they end, from the layout as son2emil does).
- The layout strings and the zoom of each line, which hairpins need.
Read and used, but not checked as far as they could be:
- Staff record byte 2 (the number of staff lines, 5, and 1 in the song of chord diagrams), byte 14 (the voice) and the widths in bytes 2 and 3 of a note (they grow with the lyric syllable).
- The 5 bytes after the ottava code of
f3 (the third perhaps where the line ends), and ottava codes other than the one seen.
f2: a jump up or down, perhaps a note drawn on the other staff; f1: two offsets.
- The
40 byte of the fd mask (a byte 5b to 72, read by son2emil and not used), and e8 (a dotted slur, hidden stems: from son2emil's names).
- Bit
80 of the bar line byte (hide staff) and the group barline style (bits 10 to 40 of the second measure): son2emil's names, not seen in SPP.
- The
e8 record (a drawing matter only: the notes it is on read the same in SPP Lite 5.1's resaves as those without) after f6 (5 notes in the corpus), the f6 record f5, and the values 01 and 04 of f5, f1, f0, ed, eb, ea, e9; bit 02 of the fd mask. Son2emil reads most and does not use them.
- The optional records with the masks
10 and 04 that do not read.
- The first list after the measure arrays, with records of 6 bytes (Voltas); the byte before the key and the 2 after it in the header.
- Everything that only decides the layout of the page, which this reader does not need, and which was left alone: most of the settings record of 122 bytes (the numbers for the spacing and the zoom are known), the numbered sections between the texts and the notes (
03, 04, 05, 08, 09, 0a, 0b, 0d, 0e), the stretches between the blocks, and the settings of the SPP 1.4 song (its layout is not found).
How the rest could be found
SPP 4's demos cannot save, but SPP Lite 5.1 opens the songs of this format and draws them. So a byte of an old song can be changed, the copy opened in Lite and looked at, and Lite's own resave compared with the twin of the original, as was done for the SPP 5–7 format. PriMus' son2emil is the other oracle: it names what it finds (the words of its text format), also for bytes that SPP Lite does not draw.
Files up to SPP 4 start with f0 ee ed. The corpus holds 119 of them: 18 of the songs the converter was written for, the songs that come with the SPP 4.0 demo, those of the SPS and SPE 4.0 demos, and 3 of the SPP 1.0 disk. Their version strings are 11.0, 11.4, 12.0, 12.1, 13.0, 13.1, 14.21, 14.90, 14.92, 14.93 and 14.94: a 1, then the version of SPP that saved them (son2emil names 13.0 format version 3, and 14.94 4.94), so from SPP 1.4 to 4.94. The layout found so far is the same in all of them.
SPP 1 and 2 ran on the Atari platform only. SPP 3 and 4 were also available for Windows, and later for the Mac, presumably by emulating the Atari: the Windows version of SPP 4 looks like an Atari program, drawing its own menu bar. The format fits that origin: big endian, the byte order of the Atari's 68000 processor, and text in the Atari's character set. SPP 5 was a rewrite, for Windows only, with the SPP 5–7 format. SPP 4 reads all these files; the demo of SPP 4.0 opens them but cannot save. SPP Lite 5.1 opens them too, down to SPP 1.4, and saves them in the SPP 5–7 format.
The Standard (SPS) and Education (SPE) editions are assumed to use the same format as SPP: Scoretec offered version 4.0 in all three, and later said that songs could be exchanged between them. Their 4.0 demos cannot save, but come with songs (8 for SPS, 26 for SPE): all start with f0 ee ed, carry the same version strings (11.4 to 14.93), read with the same reader and convert without errors. 15 of them are byte for byte the demo songs of SPP 1.4 to 4.21; the other 19 (from SPP 4.90 to 4.93) are not in the SPP demos.
SPP 1.0 (version string 11.0) writes this format already. SPP 1.2-K, the short version of 1.2 ("Kurzanleitung"; the program says 1988 and 15.7.1989, a year before SPP 1.0 of 26.6.1990) that came on the utility disk of the magazine KEYS and was made for it, by the same author, Klaus Kleinbrahm, a music teacher (his own words in the disk's LIESMICH.TXT; it needs an Atari ST with 1 MB and runs in the high resolution only, as all of them do: "läuft nur in der hohen Auflösung"). The text says that songs made with 1.2-K can be loaded and edited by the main program, Score Perfect itself. Unlike SPP 1.0, it does not write this format: its songs start with f0 ee ec and are text, lines ending in 0d 0a as written by a BASIC program: the version "1.2", the title, a line of numbers, then per measure a line with the length of its notes and a line with the notes in quotes, as fe, number, type, position records. Not decoded; the converter says "SPP 1.2 format: not supported". The corpus has 5 of them, from the SPP 1.2 disk image.
It is the format of the time before PriMus forked off from SPP: PriMus' son2emil.exe (in PriMus Free) converts these files to its text format, emil, and refuses the SPP 5–7 format.
One file of the SPP 4.0 demo (Lieder - ALTA_TRI.SON) is no song: all its 7708 bytes are e5, so the data was never written properly or was lost in copying.
Every song was saved again by SPP Lite 5.1, in the SPP 5–7 format, driven by a script under Wine; the converter reads those, and all 116 convert to valid MusicXML, with as many measures as son2emil counts where it has been run. The 3 songs of SPP 1.0 have no pair: SPP Lite 5.1 cannot open them, and saves an empty song; the SPE and SPS songs have no son2emil output. So each song comes as a pair: the same music in both formats. research/oldformat.py lines the SPP 1–4 file up against the converter's reading of the SPP 5–7 one, field by field; research/compare_older.py compares the converter's reading of both. son2emil's output of the originals is a second reference. In the corpus, the resaved songs are in songs/old_resaved_by_spp51/ and son2emil's output in songs/old_converted_by_son2emil/, each in the same collection and version folders as the originals.
What SPP 5.1 makes of these songs, and what that taught about the SPP 5–7 format, is on the SPP 5-7 file format page.
Later findings came from two other sources. PriMus' son2emil.exe was decompiled with Ghidra: it reads the notes' optional records, the lists after the measure arrays, the layout and the hairpins, so its code says what a field is (the f6 record, the hairpin walk). The test songs research/test_songs/maarten/ were made by hand in SPP for the SPP 5–7 format, with one thing changed at a time, and are on the SPP 5–7 format's page.
- Integers are big endian:
0c 00 is 3072.
- Strings have a 2-byte length in front:
00 06 4f 62 6f 65 20 32 is "Oboe 2".
- Text is in the Atari ST character set, which the converter reads as code page 437 with two exceptions,
9e ß and a9 ©: 81 ü, 84 ä, 94 ö, 9e ß ("Baß", "Händel"). But the Windows SPP 4.93 stored a typed © as a9, its Windows byte, which is ⌐ in the Atari set.
- Durations are in divisions of 768 per quarter note, as in the SPP 5–7 format.
- Staff positions count diatonic steps, C4 is 35, plus 100 for a note head on the other side of the stem, as in the SPP 5–7 format.
From the header to the time signature table, the file is read block by block (in SPP 2 and later); the notes are found by their shape, as the sections before them are not all decoded. research/layout_older.py prints this map for a song.
| block | contents | how it is found
|
|---|
| header | magic, version, title, counts, then 18 bytes: the first time signature, a byte, the key and 2 bytes | fixed layout
|
| staff records | per staff its name and 15 bytes | right after the header
|
| settings and staff groups | settings of a fixed length, then three lists of staff ranges and 2 bytes | right after the staff records
|
| time signatures, keys and bar lines | a table of time signatures, then three arrays of a byte per measure | right after the staff groups; by its shape in SPP 1.4
|
| lists | a list of records of 6 bytes (mostly empty), then the voltas, each a length and records | right after the arrays
|
| texts and sections | records separated by ff ff: the texts, then numbered sections: the clef changes (02), the MIDI mixer (06) and others, not decoded | right after the voltas
|
| layout strings | per measure a string with its width and the places of its columns, and one more | the last thing before the notes: chained back from where the notes start
|
| notes | per staff, one block per measure | by its shape, with the stored counts of the staff records
|
| lines | pages and lines: per line the zoom, its first and last measure | after the notes
|
All 119 songs are read this way.
Right after the header, per staff: its name, a string, then 15 bytes.
| bytes | meaning
|
|---|
| 0-1 | the vertical place, probably: about 60 apart from staff to staff
|
| 2 | the number of staff lines, probably: 05, and 01 in the song of chord diagrams
|
| 3 | the transposition
|
| 4 | ?
|
| 5-6 | the length of the first measure in divisions: less than the time signature's in an upbeat (the SPP 5–7 format's measure tag c9)
|
| 7 | the clef (00–04 are read), with the SPP 5–7 format's codes: 00 treble, 01 bass, 03 alto
|
| 8-9 | the number of measures stored for the staff, up to its last measure with notes: empty measures after it are left out
|
| 10 | ?
|
| 11 | the instrument: shared by its staves (a piano: Bach's fugue has four records, all instrument 01)
|
| 12-13 | ?
|
| 14 | the voice on the staff: 01, 02, or 00 when the staff has one. Two records with the same vertical place are two voices drawn on one staff: the fugue's records come in pairs (00 70, 00 b3), as do Beethoven 5's two flutes
|
Signed, in fifths: how much higher the written key is than the concert key. 02 clarinets in B♭, 03 horns in E♭, fe (−2) a part in D (Beethoven 5, Mozart). The sounding pitch is the written pitch minus 7 times that in semitones, within an octave: −2, +3 (or −9), +2. Checked against the MIDI pitches of the resaved songs.
Settings and staff groups
Right after the staff records: settings of a fixed length, 122 bytes from SPP 3.0 on, 121 in SPP 2 (the one song of SPP 1.4 has shorter ones, not worked out). The 6th short (bytes 10-11) is the tempo in beats per minute, equal to the tempo of the resaved songs in all 116; Bach's Toccata has 88. They start with 00 05 to 00 08 and hold the guitar tuning 34 39 3e 43 47 4c (E A D G B E, as in the SPP 5–7 format); not decoded further.
Then three lists of staff ranges: each its length in bytes, then pairs of staff numbers, first and last. The first list holds the braces, the second the brackets, as the SPP 5–7 format's part groups (in the other order); they agree with those of the resaved songs in all songs. The third list, other ranges, comes back unchanged as list 6 of the SPP 5–7 format. Beethoven 5: braces 19-20, brackets 1-8, 9-13 and 14-20. Then 2 bytes (00 01, 00 02 or 00 04), and then the time signature table.
Time signatures, keys and bar lines
A table of the time signatures the song uses: its length in bytes, then 12-byte entries:
| bytes | meaning
|
|---|
| 0 | the style, as in the SPP 5–7 format's time signature: 01 C, 02 cut C, 04 numbers; 00 in two songs, shown as numbers
|
| 1 | ?
|
| 2-3 | the beats and the beat type; 04 04 for C and cut C, which the style overrides, as in the SPP 5–7 format
|
| 4-9 | 04 04 04 04 00 00
|
| 10-11 | the measure length in divisions: 0c 00 is 3072, 4/4 (the SPP 5–7 format's measure tag c8)
|
After it three arrays, each the number of measures, then a byte per measure:
- the time signature: an index into the table, from 1 (MEL_10 changes from 3/8 to 2/4);
- the key, + 20, concert pitch;
- the bar line at the end of the measure: in the low 4 bits the SPP 5–7 format's bar line code minus 1, so
00 dotted, 01 normal, 02 double, 03 final, 04 repeat end, 05 repeat start of the next measure, 06 and 07 repeat end and start. Bits 10, 20, 40 and 80 are not the bar line: see below.
Against the resaved songs, the keys agree in 96 songs, the time signatures in 94 and the bar lines in 88; the rest differ by multi-measure rests and the bits below.
The bar line byte has more than the bar line, found by reading son2emil: bit 80 is "hide this staff" (son2emil writes HideStaff after the bar line, and ShowStaff where the next measure has the bit off), and bits 10, 20 and 40 of the second measure's byte are one song-wide number, the style of the barline through a staff group that son2emil writes in Set grouping: 0 continuous (1-2), 1 1:2, 2 m, 3 and others other characters (+ is 5, ' is 6). The other measures repeat the bits (Beethoven's Fifth: all 502 measures 3x, Locus iste: all 48 1x), which is why they are on every measure of a song or on none. The converter reads none of these.
Right after the per-measure arrays come lists, each with its length in bytes first. The first list has records of 6 bytes, ff, 00, a measure, a kind and 2 bytes, for example ff 00 0f 05 31 54; it is empty in most songs (00 00) and its meaning is unknown (kinds 1, 2, 4, 5, 7, 9, 11, 13 occur, and two measures of Beethoven's Fifth, second movement, where SPP Lite 5.1 numbers one lower have a kind 1 record). The second list holds the voltas: 00 7e bytes (7 per record), then per record ff ff and 5 bytes: 00, the measure (from 1), the number of the ending, 78 00. A volta of several measures has a record for each, so the first measure of a run of the same number is where SPP 5.1 puts it. After the voltas come the texts. All 115 voltas of the 97 songs are where SPP Lite 5.1 has them; before the first list was taken into account, five big songs had none and the records of the MEL songs seemed to have a first byte that was not 00.
The bar line codes 08 to 0f of the low bits are not known: the converter logs them. The bar line bits (see above) have nothing to do with voltas: none of the measures with a volta has any of them.
After the voltas: records separated by ff ff, first the texts, then the numbered sections (below). A text:
| length | meaning
|
|---|
| 1 | the staff, from 1
|
| 2 | the measure, from 1
|
| 2 + 2 | the place: x and y
|
| 1 | the style: 01 the title
|
| 3 | ?
|
| 1 | the length
|
| the length | the text
|
The converter puts every text above the staff; the title is the first of the texts in the title style (the lowest measure, then the lowest staff, then the first in the file: the same as SPP Lite 5.1 makes of it in 67 of the 69 songs that kept a title) and is not kept as a text, the others are texts, and a header title that is "Kein Titel" is none; there is no composer or subtitle field in this format, so Toccata's "J. S. Bach", in the same style, stays a text and not the title as the header's own title string has it, and a text outside the song, or one whose length does not fit, is skipped. The header's title is often "Kein Titel"; the text in the title's style is the real one ("Menuett II", "INVENTIO 1"). 565 of the 870 texts of the resaved songs match; SPP 5.1 itself drops texts and moves some in long songs (by 156 measures in Beethoven's Rondo), where son2emil agrees with the original.
After the texts the file goes on with records separated by ff ff, each starting with its number: 02 the clef changes, if there are any (see Clef changes); 03, 04 and 05, short and not decoded; 06 the MIDI mixer, with its labels in Atari text (LAUTSTÄRKE, HALL, CHORUS, PAN), not decoded; then in most songs 08, 09, 0a, 0b and 0d or 0e, not decoded; some songs have a section 00 before the texts. A section can hold ff ff itself, so they cannot be cut apart by splitting. In some songs section 09 holds a 2-byte number per measure, the measure numbers as SPP shows them, with a number repeated where a measure of a first ending repeats one; SPP Lite 5.1 does not keep them. The layout strings, the last thing before the notes, are not a section of this list (see Hairpins); so the notes block is still found by its shape.
After the texts: a record starting 02 (after ff ff), then per staff a length (6 per change), then per change ff ff and 4 bytes: the measure (2 bytes, from 1), the number of the note in it (from 1, rests count), the clef (the code of the SPP 5–7 format, 00 G, 01 F). In Bach's Toccata and Fugue: 02 | 00 00 | 00 0c | ff ff 00 11 01 01 ff ff 00 12 02 00 | 00 72 | ..., so no change in the first staff, then an F clef at the first note of measure 17 and a G clef at the second of measure 18 in the second. All 371 changes of 33 songs sit where SPP Lite 5.1 has them.
Per staff record (each voice, see staff records), one block per measure: a 2-byte length, then the notes; then an empty block, ending the staff (the last staff's can be missing). An empty measure is an empty block too, and the empty measures after the last one with notes are left out: the staff record says how many measures are stored. The block is found by its shape; as the search finds its first note, the first staff's leading empty blocks lie before that and are counted back. Found in all 97 songs. With the stored counts, note counts and pitches agree with the resaved songs in 99.6 % of the notes.
| bytes | meaning
|
|---|
| 0 | fe
|
| 1 | the number of the note in the measure, from 1
|
| 2-3 | widths: they grow with the lyric syllable under the note
|
| 4 | the column in the measure
|
| 5 | the type
|
| 6 | the stem byte
|
| 7 | a rest only: 64
|
| the tones, then optional records
|
The SPP 5–7 format's note types, rests 18 hex more, with one difference: the first of each three is dotted, where the SPP 5–7 format stores dots in a tag. So 07 is a dotted quarter, 08 a quarter, 09 a quarter triplet.
| bit | meaning
|
|---|
| 01 | an f6 record follows the note (on about 47000 notes)
|
| 02 | beam starts
|
| 04 | beam ends
|
| 08 | the stem direction is set explicitly (son2emil's H^ up and H, down, with bit 20)
|
| 10 | tied to the next note: set on all 2256 tied notes of the resaved songs. A tied note has a byte per tone more after its tones, and that byte says what the tie of that tone is: 10 a tie to the next note (start), 20 one from the note before (stop), 30 both (continue). Checked on 3000 tones of the resaved songs: 100 %. A note can carry the flag with some tones only stopping, and a chord with only some tones tied
|
| 20 | stem down
|
| 40 | cue note, printed small: set on all 632 cue notes
|
A count, then the staff positions only, without MIDI pitch. From 14 up the count is 14 hex (20) + the number of tones, followed by 00, the positions, and one accidental per tone, with the SPP 5–7 format's codes: 02 ♭, 03 ♮, 04 ♯. Staff positions agree with the resaved songs in 99 % of the tones.
As there is no MIDI pitch, it follows from the staff position, which gives the note name and octave, and an alteration: the last accidental at that position in the measure, or else the key signature. The written key is the concert key plus the staff's transposition. A tone tied from the note before keeps that note's pitch. This agrees with the MIDI pitch of the resaved songs in 99 % of the tones.
The missing pitch also shows in what SPP 5.1 makes of a tied-to tone: in some songs it saves MIDI pitch 0 for it.
After the tones, fd, a bit mask, then the records the mask announces, always in the order of the table (seen in all combinations in the corpus). Lengths include the record's code byte:
| bit | record | length | meaning
|
|---|
| 01 | e8 | ? | after the f6 record: a mask (bit 02 a dotted slur, in son2emil's (:) and records e7, e6, e5 (hide stem) and e3. Not read; on 5 notes of the corpus
|
| 02 | ? | ? | ?
|
| 04 | f9 | 2 + 5 × the count | the ornaments and marks, laid out like the SPP 5–7 format's tag e5: a count, then 5 bytes per item, the first the mark
|
| 08 | fa or fb | 13 | crescendo or diminuendo: a hairpin, see Hairpins
|
| 10 | fc | 2 + per slur 9 + 4 × the points | a count, then per slur a Bézier curve of 3 to 5 points (a pair of numbers per point, each in base 100 with an offset of about 1000, relative to the start note), then 4 pairs (high, low), the value high × 100 + low: a number, the measure where the slur ends (from 1, base 100 from measure 100 on: 03 2d is 345), the number of the end note in that measure (from 1; rests count), and a style minus 50 (32 03 is 3). The end is thus in the file, and no layout is needed. Of the slurs of the songs, 7395 starts and stops agree with SPP Lite 5.1's, 345 are only ours and 185 only SPP Lite's; where SPP Lite differs it is shifted, as with voltas and texts (Mozart's bassoon duet 5 by 4 measures)
|
| 20 | f8 | 2 + per verse 2 + its length | the lyrics: a count of verses, then per verse a 2-byte length, 4 bytes (a place?) and the syllable; ~ is the hyphen
|
| 40 | – | 1 | one byte, 5b to 72; not a mark code (read as one, fewer marks agree); read by son2emil and not used
|
Read this way, the marks and lyrics of 96 % of the notes that have them agree with the resaved songs; most of the rest are one note off, in songs with several voices on a staff. The f6 record follows many notes, after the fd records or without them: see The f6 record.
The optional record fa (crescendo) or fb (diminuendo), 13 bytes: the code, then pairs (high, low) with the value (high − 50) × 100 + low: the start offset a6, a y, the length a2, another y, and two more. It is the same record as SPP 5's tag d1 (there with 100 instead of 50). A crescendo is on its first note, a diminuendo on its last. The end is not in the file: PriMus' son2emil works it out from the places of the notes, and so does the converter (hairpins.py), found by reading son2emil with Ghidra:
- The target is the place of the note plus a2 × the zoom of the line / 200 + a6, in layout units. Forward (crescendo), from the next note on, the end is the note that is nearest to the target, nearest being the distance to the note's place plus 8, until a note is not nearer than the one before. At a barline the width of the measure is taken off the target. Backward (diminuendo) the same without the 8, and in both directions the first note has to be nearer to the target than the hairpin's own start is, that is, closer than |a2 × zoom / 200 + a6|, and the width of the measure before the one entered, counted from the one left, is added (an off-by-one in son2emil, followed here).
- The place of a note: its column (note byte 4) in the layout string of its measure, plus 2 and the first setting number (the 3rd short of the settings) × the zoom / 200. The width of a measure: the width in its layout string plus the 4th short of the settings × the zoom / 200.
- The layout strings, one per measure and one more, are the last thing before the notes: a 2-byte length, then 4 bytes, the width (2 bytes), 3 bytes, and records of 10 bytes (14 in later versions): the time, the x of the column, and 6 (or 10) more.
- The zoom belongs to a line, from the end of the file, after the notes: 9 shorts, the number of pages and a short, then per page the number of lines, and per line the zoom, the first and last measure, a short per staff and a string. A line with first measure 0 is no line. Measures that no line covers get the 7th short of the settings as zoom. When no note of the hairpin has a place in its layout string, the hairpin gets no other end and is left out.
Against son2emil's output for all songs: 271 hairpins agree, 5 are only in son2emil's output, 7 only ours. Of the songs with hairpins, only the SPP 1.4 one has no layout strings that can be found. A measure can have a short string (no columns); those of the MEL songs are, and without allowing them the chain does not add up.
After the fd records (or the tones) comes f6 and a mask byte, found by reading son2emil; records in this order. Lengths include the code byte:
| bit | record | length | meaning
|
|---|
| 01 | f5 | 2 | not understood
|
| 02 | f4 | 2 | the place in a multi-measure rest (see Multi-measure rests)
|
| 04 | f3 | 7 | the ottava code, then 5, the third perhaps where the line ends (see Ottavas)
|
| 08 | f2 | 5 | the first is 100 plus a jump up or down (son2emil writes JumpUp, JumpDown, JumpBack; perhaps a note drawn on the other staff)
|
| 10 | f1 | 5 | two pairs (high − 50) × 100 + low, an offset of something; son2emil reads them and does not use them (on 1155 notes)
|
| 20 | f0 | 6 + the length byte | a chord symbol or text: two pairs (the place), a length byte, the text (son2emil turns " into maj and ! into m). No song of the corpus has one
|
| 40 | ef | 2 + its records | a mask, then, each with its code byte (ee 5, a tuplet bracket; ed 2; ec 4, a grace note, the first of its 3 bytes says slashed; eb 2; ea 8; e9 2) for the bits 01, 02, 04, 08, 10 and 20; bit 02 of e5 is HideStem
|
Bit 01 of the stem byte says an f6 record follows (47000 notes). The 40 byte of the fd mask is read by son2emil and not used either.
The grace note: ec is there on all 369 grace notes SPP Lite 5.1 has and on no other note. The grace note keeps the duration of its type. After f6 may come e8, with the fd mask bit 01: a mask (bit 02 dotted slur, in son2emil's (:) and records e7, e6, e5 (hide stem) and e3; not read.
Not one record as in SPP 5: each measure of the run has its rest, ending in the record f6 02 f4 NN, NN the place in the run (1, 2, 3), as in fe 01 00 08 01 1a 21 64 01 32 f6 02 f4 02. A run is the measures marked 1, 2, ... in every staff; the converter makes them one measure with the count, as SPP 5 has it. In Mozart's bassoon duet 5, the only song where SPP Lite 5.1 made multi-measure rests, all four (3, 2, 3 and 3 measures) are found exactly where it has them.
The record f6 04 f3 CC (or f6 14 f3 CC, followed by an f1 record) and 5 more bytes (00 46 00 00 00 on the first note of a line, zeros after) is on every note under an octave line, CC the code of the SPP 5–7 format's e2 (only 01 occurs). A rest in between has none. In Beethoven's Für Elise (15 notes) and Das Lied vom Traum (152 notes) every note under a line is where SPP Lite 5.1 has it, with the same pitch in all but one.