MICROSOFT FLIGHT SIMULATOR DATA FILE STRUCTURES INTRODUCTION Document version 3, release data: 6 June 1993 Updates: ù Added records 0Ah, 11h, 39h, 47h, 57h, 59h ù Updated record 10h, 27h, 58h ù Extended the description of SC0 files (John Blackie's contribution) ù Extended .DRV description with checksum routine explained ù Added .DYN description with a reference for dynamic records (John Mechalas' contribution) ù Added .ADV description with a reference for dynamic records (John Mechalas' contribution) ù Added a short note on ATP SCNs (source: Simon Hradecky). ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Document version 2.2, release date: 10 February 1993 Updates: ù The descriptions of following records have been updated: 00h, 05h, 0Bh, 0Eh, 0Fh, 10h, 13h, 14h, 15h, 16h, 17h, 18h, 19h, 1Bh, 1Ch, 1Fh, 23h, 24h, 27h, 28h, 29h, 2Ah, 2Bh, 35h, 36h, 3Bh, 3Ch, 3Dh, 3Eh, 42h, 43h, 44h, 49h, 4Ah, 79h ù Extended variable treatment; the variable usage of the standard scenery F1 is described in some detail, many variables have been added ù F1 format description has been extended ù Added notes on the .SC0, .ELE and .DRV formats ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Document version 2.1, release date: 10 December 1992. Updates: ù Added 3 variables and all the records present in the default scenery F1 ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Document version 2.0, release date: 15 November 1992. Updates: ù Added static scenery record codes reference ù Completed 5Ah record in mountain description ù Corrected description of 0Bh, 0Eh, 16h, 25h records and "range" records ù Added ATC records and many records used in other kinds of scenery ù Added .DEM and .MOD file structures Many record codes have been added, and more obscure points have surfaced. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Document version 1.0, release date: 15 September 1992. This document describes the structures of files created or provided with Microsoft Flight Simulator 4.0 and/or the Microsof Aircraft and Scenery Designer ver 1. The document is ideally addressed to developers and requires a good knowledge of hex notation and some familiarity with programming concepts. Conventions: ù The symbol "m" always means meters, while nautical miles are noted by "NM". ù Hex values are marked with an final 'h', non-marked values are decimal, the only exception being code dumps in examples which are in hex. ù Within scenery files, all multi-byte values follow the Intel convention: lower order bytes precede higher order bytes; they are always transcribed as a single value restoring the correct digit positions ("53h 07h" means a byte value 53h followed by a byte value 07h, while "FFFBh" means a word value FFFBh made of a first byte FBh and a second byte FFh). ù Record structure is given in columnar form: in the 1st column the offset within the record, in the 2nd the length of each field, in the 3rd the des- cription of the field. ù Unindentified or undeciphered (parts of) records are marked with "???". ù Records fields which have the same value xxxx in all the examples I saw are described as "always xxxx ??". ù Fields whose value, when arbitrarely changed by hand, does not affect object appearance or behaviour are declared "irrelevant". Additions, corrections or suggestions are welcome. I apologize for English language errors and inelegancies. ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿ ³ I would like express my debt to: ³ ³ Greg Pierson [72520,1775] ³ ³ whose program DCOD01.EXE is at the origin of my work and to ³ ³ John Blackie [100032,532], ³ ³ John Mechalas, ³ ³ Dan Samuel [70110,434], ³ ³ Andrew Tuline [70742,3176] and ³ ³ Steve Turley [71340,1562] ³ ³ for their additions, suggestions and friendly support. ³ ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ Maurizio M. Gavioli CompuServe: 100021,2335 (checked once a week) InterNet: "Maurizio M. Gavioli" (checked daily) -------------------------- DISCLAIMER -------------------------- The below information was derived from months of analysis of FS4/ASD files (often manually generated for this very purpose), during which I also had many occasions to appreciate the sophistication of FS scenery description language. The FS/ASD community as a whole has spent way too much time decod- ing this information in order to generate useful utilities. It would be nice if the original authors chose to publish an "official" documentation of FS data files. However, the below information is not distributed with an eye towards enabling anyone to rob the original authors of any rightful profits and should be used only for the common good of the FS community and to encourage availability and sales of FS and related products and utilities. ======================================== GENERAL CONCEPTS FS COORDINATES AND GEOGRAPHIC UNIT FS coordinate unit (thereafter "FSu") is very close to 256 meters. FS North and East coordinates are internally coded with code 49,152 (= C000h) representing coordinate 0; therefore codes from 49,152 to 65,535 (C000h to FFFFh) represent coordinates from 0 to 16,383 and codes from 0 to 49,151 (0000h to BFFFh) represent coordinates from 16,384 to 65,535. Within programs, internally coded coordinates can be convert to external FS coordinated by subtracting 49152 (C000h) from the value considered as unsigned. Manually, coded coordinates below 49,152 can be converted to FS coordinates by adding 16,384, and coded coordinates above 49,151 can be converted by sub- tracting 49,152. Coded coordinates can appear in object definitions in one of three ways: ù INTEGER (2 bytes): a word containing only an integer coordinate (indicated as "int FSu") ù FRACTIONARY (4 bytes): a double word made of a high order word (4th and 3rd bytes) containing the coordinate integer part and a low order word (2nd and 1st bytes) containing the fractionary part. Fractionary coordinates can also be interpreted as made by 3 high order bytes expressing a distance in meters from coordinate origin and a low order byte containing a fractionary part in 256th of meter; this is confirmed by altitude fields, because altitude is almost invariably indicated in this way (with the fractionary byte left often unfilled). Both interpretations are indicated as "fract FSu". ù DELTA (2 bytes): a word representing the difference from an actual reference coordinate given in a previous reference point record 24h. Delta coordinates have not a fixed magnitude, but depend on a scale factor set with byte 1 of record 24h: for scale factor 0, delta coordinates are aligned with the fractionary word of fract FSu, for scale factor 8, delta coordinates are aligned with the integer word of fract FSu, and for inter- mediate scale factors intermediate alignments are used; for a detailed dis- cussion, see below under record 24h description. Contrarily to the other two representations, which are always positive, this one is signed. This representation is indicated as "delta FSu". OBJECT ORIENTATION Some objects, like runways, buildings and aircraft positions, are oriented. The angle of this orientation is always given relatively to the North axis of the FS coordinate system. For some kind of cartographic compensation not dis- cussed here (but see var 02F2h and 02F4h below), this axis is not necessarily the same as the compass North. Directions displayed by FS and ASD are rela- tive to the compass North and, therefore, there can be a rotation between the directions as displayed by ASD and FS4 and as memorized in the files. Unless otherwise stated, orientation or heading fields, as well as "pitch" and "bank" fields, are 2 bytes long and are expressed in 1/182.04ø: 0000h = 0ø -> 10000h = 360ø RECORDS Many kinds of FS data files are made of "records", i.e. chunks whose struc- ture, contents and meaning are determined by the first record byte (there- after called "record code"); records may contain many values (thereafter called "fields"), and, with a few exceptions, each record has a fixed length. Records appear in the files one after the other; given the start point and the structure (or at least the length) corresponding to each record code, a file can be sequentially parsed and decoded. Record code meanings may change (and usually do) from file type to file type. Some file types (as .SC1 and .DY1) start with a non-record coded portion ("header") containing general information about the file. BYTE OFFSET Many of the records used in static sceneries contain an offset, pointing to another record. It is used to provide some forms of inter-record addressing for conditional (after variable test) or unconditional jumps. These offsets are indicates as "bytes offset" and are always relative to first byte (code byte) of the record which contains them. ====================================================================== FS4 INTERNAL VARIABLES FS maintains somewhere in memory a set of 16-byte variables, which affect the display engine and the flight simulation engine. These variables are accessed with a value which is actually a memory address and has been called "variable address". Variables can be set and tested from within a scenery file. Known variables: 0280 AGL altitude of current view point in m. 0282 "counter": its value seems to be a single bit which cycles from 0001h to 8000h in about 6 sec. Checked 45 times in F1, never writ- ten 0284 Crash flag: when this var is set to a non-0 value, the plane crashes; the displayed message depends on the value: 2 "mountain crash" 6 "building crash" 8 "splash" (see also var 02E6) Ah "crash - lower your gear next time" Any other value results in a simple "crash" message 0286 set to 0000 during 3D window drawing, to 0001 during map window drawing 0288 set to 0001 in SC1 fuel boxes; set 15 t. to 1 and once to 2 in F1 028A FS version number (0300h = 3, 0400h = 4, 040Bh = 4b), never accessed in F1 028C holds the daytime code (1 = day; 2 = dusk; 4 = night). 028E In F1, set 1 time to 1111h 0290 Low word of current view point East coord. 0292 High word of current view point East coord. 0294 Low word of current view point Alt. coord. 0296 High word of current view point Alt. coord. 0298 Low word of current view point North coord. 029A High word of current view point North coord. 029C Current view point delta East from last ref. point 029E Current view point delta Alt. from last ref. point 02A0 Current view point delta North from last ref. point 02A2 - 02AA Never accessed in F1 02AC View direction in 1/182.04ø; North = 0000 Many of the following vars contain colour codes (repeated in all the 4 nib- bles): "reference" colours are loaded by FS4 at start up and never reset; "current" colours are set by the scenery itself (often by copying the rele- vant "reference" value) and usually affect the screen appearance of an item. 02AE Reference day colour of ground 02B0 Reference day colour of sky 02B2 Reference for ?? (used in F1 as source for current colour vars) 02B4 Reference for ?? ( " " ) 02B6 Reference for ?? ( " " ) 02B8 Reference for ?? ( " " ) 02BA Reference for ?? ( " " ) 02BC Reference dusk colour of sky 02BE Reference for ?? ( " " ) 02C0 Reference for ?? ( " " ) 02C2 Reference day colour of water 02C4 Reference for ?? (used 9 t. as source for var 02E8) 02C6 - 02CA Never checked or set in F1. 02CC Reference for ?? (used 9 t. as source for var 02E8) 02CE Never checked or set in F1. 02D0 - 02DC These seem to be 'spare' vars, used here and there to hold temporary values or copies of other vars' values 02DE Current colour of sky (setting this var changes the colour in the display) 02E0 Current colour of ground ( " " ) 02E2 Surface fill colour. In F1, the var value is set very often to literal colour codes (with record 25h) or copied from other colour vars (with record 1Ah). 02E4 In F1 set 16 times to 5555h and 16 times to FFFFh 02E6 Current colour of water. Setting this var does not affect the dis- play in any way, because lakes, rivers, seas and water surfaces in general are just standard polygons whose colour is governed by var 02E2; however the value of this var is internally checked by FS, because when landing onto or entering a polygon with a fill colour equal to var 02E6, the plain "SPLASH"es. 02E8 Current colour of ??; in F1 it is set 16 t. to 0000, 14 times to AAAAh, 9 t. to the value of 02C4 and 9 t. to the value of 02CC; used 8 t. as source for var 02E2 value. 02EA Current colour of ??; in F1 it is set 16 t. to 0000 and 16 t. to the value of var 02C6; used twice as source for var 02E2 value. 02EC In F1 it is set once to 0023h, once to 0046h, once to 0089h 02EE Low word of MSL altitude of current area in m. 02F0 High word of MSL altitude of current area in m. 02F2 Cant in 1/182.04ø 02F4 Magnetic variation in 1/182.04ø. The heading actually displayed by FS is the absolute heading MINUS the sum of var 02F2 and var 02F4 values. 02F6 Set to 0001 for inner markers, never reset. 02F8 Set to 0001 for outer markers, never reset. 02FA Set to 0001 for middle markers, never reset. 02FC Set to ILS glideslope (source: Peter Burri). Set 9 t. in F1 where, however, the record 4Fh is also used 25 times 02FE Set to ILS approach course (source: Peter Burri). Set 9 t. in F1 where, however, the record 4Fh is also used 25 times 0300 In F1, set twice to 0004, twice to 0005, 7 t. to 0007. Never read 0302 Base of bottom clouds in m. 0304 Top of bottom clouds in m. 0306 Base of top clouds in m. 0308 Top of top clouds in m. 030A - 0310 Apparently never used in F1 or in SC1 files 0312 Set to 0001 by SEE before some lists of 1Fh subroutine calls. Used in F1 as a 'spare' var to hold temporary values or a copy of another var value (often a delta altitude) 0314 - 031C Used in F1 as 'spare' var 031E Set to 0000 and 0001 in SC1 mountains. Unused by F1 0320 'Spare' ?? 0322 - 034C Apparently never used in F1 or in SC1 files 034E In F1 tested once against -1; tested against -1 in SEE custom objects (with 23h records) and in SC1 buildings (with 28h 36h records). 0350 - 0360 Apparently never used in F1 or in SC1 files 0362 Current hour (LSB) and minute (MSB). Not used in F1, SCN or SC1. 0364 Scenery detail level (0 sparse, 1 medium, 2 complex). From .DYN files, the following variables can be added: 1AC6 Dynamic scenery detail level (0 sparse, 1 medium, 2 complex) 1AD0 Ait traffic (0 off, 1 on) 1AD2 Airport aircraft ground traffic (0 off, 1 on) 1AD4 Airport service traffic (0 off, 1 on) 1AD6 Misc. traffic (0 off, 1 on) More variable addresses are listed in the ADV section at the end of this document. ====================================================================== SCENERY DESCRIPTION LANGUAGE STATIC RECORD CODE REFERENCE Static records are used in three types of files, all related to static scenery descriptions: the default scenery (F1), add-on sceneries (.SCN) and ASD static sceneries (.SC1). SDL portion has been found also in .DYN and .APL files as well as in the FS4.EXE file itself. While static records are geared toward scenery display, they build up a real procedural programming language, which we call Scenery Description Language (SDL), with variable tests, conditional and unconditional jumps, subroutine calls and so on. Scenery files are made of several scenery procedures and, within FS4, an SDL processor 'executes' them to display the scenery. Procedure entry points are listed at fixed locations of .SC1 and F1 files; .SCN files contain a special- ized record (0Ah) which defines such a table. Given the procedural nature of SDL, scenery objects do not usually have a fixed structure, but are made of the SDL statements (records) required to 'build' them, with the notably exception of unenhanced .SC1 files, which objects, perhaps to make the job of the ASD editor easier, follow standard record patterns. In the following reference, all records found in F1, SD-EUR and unenhanced .SC1 files are listed; some records from SEE enhanced .SC1 files are also added; for some records, however, the meaning is unknown and only the length has been determined. Record are listed by code. Field at offset 0 always contains the record code and is 1 byte long. Records found only in SEE enhanced sceneries are marked with =SEE=, records found only in SC1 files are marked with =SC1=, while records found, even not exclusively, in the default scenery F1 and in SD-EUR are considered part of the 'basic' SDL and not marked. Record description contributed by Dan Samuel are marked with a DS. Other contributions are individually detailed. -- 00h ------------- Flashing light (7 bytes) 1 2 E coord (delta FSu) 3 2 A coord (delta FSu) 5 2 N coord (delta FSu) Places a flashing light at the delta point. Light colour is given by a previous record 12h. -- 01h ------------- Move pen to 3D point (7 bytes) -- 02h ------------- Draw to 3D point (7 bytes) 1 2 E coord (delta FSu) 3 2 A coord (delta FSu) 5 2 N coord (delta FSu) These records, resp., move the pen and draw a line to a 3D point given rela- tively to the current ref. point. -- 03h ------------- Simple runway (6 bytes) 1 1 heading 2 2 half-length in m 4 2 half-width in m Draws a simple black runway with a dashed line in the middle, centered at the current ref. point. -- 04h ------------- ???-point list (variable) This record is used in F1 (only 4 times) after some points are defined with 31h records and it contains, after the record code, only a list of points (indicated by their numbers); the list is of variable length and is terminated by a FFh byte. -- 05h ------------- NDB (11 bytes) 1 2 frequency; BCD coded (ex.: 327 kHZ -> 27h 03h) 3 4 E coord. (fract. FSu) 7 4 N coord. (fract. FSu) -- 07h ------------- ??? (1 byte) Used only once in SD-EUR -- 0Ah xxxx -------- Proc list (xxxx bytes) 1 2 record length After the record length, a 4-byte per entry table lists all the procedures in the scenery file. Each entry has the format: 0 1 Proc code 1 2 Proc file offset in kB 3 1 Proc length in kB Proc code is a conventional ID (IDs need not to be consecutive nor in any particular order) with which the proc could afterward be invoked with a 0F record. File offset and length are expressed in 1 kB units. Only the low byte of the file offset is taken into account by FS, then SCN sceneries CAN- NOT BE LONGER THAN 256 kB. This record is equivalent to the procedure table found at offset 0022h of F1- format sceneries and is used only in SCN-format sceneries. In FS sceneries, this record is typically used only once in the main proce- dure (which in SCN-format sceneries is located at file offset 010800h). -- 0Bh ------DS----- Unconditional jump (3 bytes) 1 2 byte offset This record tells FS to jump over a given amount of bytes, avoiding the execution of some SDL statements. It is also used in .SC1 to unconditionally skip over 2-byte "signatures" inserted by ASD, usually before building descriptions, and not intended to be executed: they are probably only a help for the editor in recognizing the kind of object; record 0Bh is used in SEE files to skip over embedded ASCII "comments" (source: Steve Turley). Even if these kinds of non-SDL embedded material have been found only in SC1 objects (possibly SEE-enhanced) which follow rigid record patterns, they make the life difficult for scenery parsing utilities; the only general way I found to deal with them is to keep track of referenced record addresses and to skip to the given byte offset if the address of the record after the 0Bh record is not referenced by any previous SDL statement, but caveat: some backward byte offsets have been detected in F1. -- 0Ch ------------- ??? (3 bytes) Used only twice (at offsets 00BBF1 and 00D8E5) in F1, always after a 2Eh record and always in the form: 2E 09 80 0C 05 50 -- 0E/8Eh ---------- Delayed subroutine call (3 bytes) 1 2 byte offset This record has been one of most difficult to understand. It is basically a subroutine call, but the referenced address, instead of being called immediately, is collected in some kind of stack; at some point, presumably during the execution of a 79h record, all the collected routines are sorted in order of decreasing distance of the object they draw from the view point and executed. For the sorting to be effective, referenced routines have to begin with a ref point record (24h); if a routine lacks this record, it is executed first. This record is extensively used in .SC1 (but less in F1) to collect groups of routines drawing buildings and other elevated objects and provides a simple way to draw them in a perspective correct fashion. While it requires little code overhead to achieve a quite complex goal, it has probably a significant performance overhead. Record 0Eh is consistently used in .SC1 files in a way that makes such a behaviour very unclear, because in .SC1 each 0Eh is followed by a 0Bh record which jumps over the routine referenced in the 0Eh record; sometime after the 0Bh record a 2-byte "signature" is embedded (see above, under 0Bh record). -- 0Fh ------------- Load procedure (6 bytes) 1 1 procedure number 2 1 class 3 2 loading address (as byte offset) 5 1 nesting level This record loads from disk (if not already loaded) at the given memory address the specified scenery procedure; the number refers to the scenery position in the scenery table at file offset 000020h (see F1 description below) or, for SCN's, to the conventional code attributed to the procedure by the 0Ah record. Class is a parameter which, in F1, varies from 1 to 8; its purpose is not clear but may related to memory management or other housekeeping tasks; when arbitrarely modified, no visible difference can be detected. The most common value seems to be 6. The loading address (expressed as a byte offset from the 0F record) is presumably the memory address at which the procedure has to be loaded from disk. In all the examples I have seen, it consistently points right after the last record of the procedure containing the 0F record (calling proce- dure); the loaded routine is then activated with a Jump record. Apparently, the loaded procedure must not overwrite the calling procedure, in order to not invalidate it. Procedure calling can be nested: the nesting level is 0 for the first nesting and increases by 1 each time a called procedure calls another one. -- 10h ------------- Hidden surface check (5 bytes) 1 2 byte offset 3 1 point number 4 1 control vector number This record is a conditional jump. The vector (previously defined with a record 27h) applied to the point (previously defined with a record 31h) defines a 3D plane (the plane perpendicular to the vector and passing through the point); the vector, by definition, protrudes into the "inside" side of the plane. The record jumps to the given offset if the current view point is also in the "inside" side of the plane. A practical (and recurrent) application of this record is the hidden surface check for buildings and mountains. Building walls and mountain slopes are planar and have an "inside" and an "outside" side; considering the plane passing through one of them, if the view point is in the "inside" side, the wall (or slope) cannot be seen, because it will be hidden by other walls (buildings and mountains are usually closed). In that case, the record 10h is used to jump over the code drawing that wall. See also discussion of record 27h. -- 11h ------------- ??? (2 bytes) 1 1 ?? This record has been found after the record 57h. Its purpose is not clear. A default value for the second byte seems to be 11h. -- 12h ------------- Line Colour (2 bytes) 1 1 colour code from the following table: 0 Black 1 Dark Green 2 Dark Blue 3 Dark Cyan 4 Orange 5 Light Grey 6 Light Blue 7 Cyan 8 Brown 9 Yellow Ah Dark Grey Bh Light Green Ch Red Dh Gold Eh (White*) Fh White -- 13h ------------- Line multi-colour (10 bytes) 1 1 line colour for day time 2 1 line colour for dusk time 3 1 line colour for night time 4 3 second colour triplet 7 3 third colour triplet This record applies to following lines different colours for different daytimes; its effect ceases with the next 12h record. The second and third colour triplets are filled with consistent patterns of colours and, probably, refer to colours for other kinds of display (monochrome...). -- 14h ------------- Surface multi-colour (10 bytes) 1 1 surface colour for day time 2 1 surface colour for dusk time 3 1 surface colour for night time 4 3 second colour triplet 7 3 third colour triplet All colour codes are repeated in both nibbles. This record applies to following surfaces different colours for different daytimes; its effect ceases when variable 02E2h is set again. The second and third colour triplets are filled with consistent patterns of colours and, probably, refer to colours for other kinds of display (monochrome...). -- 15h ------DS----- Axis roto-translation (15 bytes) =SEE= 1 2 angle around E axis (x) 3 2 angle around N axis (y) 5 2 angle around A axis (z) 7 2 delta E (delta FSu) 9 2 delta A (delta FSu) 11 2 delta N (delta FSu) 13 2 byte offset The same observations made below for record 16h apply to this record also. With it, local coordinate system is both rotated and translated. -- 16h ------------- Axis rotation (9 bytes) 1 2 angle around E axis (x) 3 2 angle around N axis (y) 5 2 angle around A axis (z) 7 2 byte offset This record is one of the most ingenuous: it applies to the local coordinate system (used for delta FSus, and by default centered in the ref. point and parallel to global axes) the described rotations, then it calls the referenced subroutine: anything (not only buildings) drawn by this routine with delta coords. will appear rotated; when the subroutine returns, the coordinate system is restored. The record can be used to display tilted objects with a very small code overhead. It is extensively used by .SC1 object, but only one in F1 and never in other SCN's; execution overhead is probably significant. -- 17h ------------- Return17 (1 byte) This single byte record returns from a subroutine; its difference from record 19h is not clear. In .SC1 it has been observed only in timing gate definitions, but in F1 it is used 26 times in various contexts. -- 18h ------------- Call18 (3 bytes) 1 2 byte offset (subroutine address) Calls a subroutine; its difference from record 1Fh is not clear. Used 624 times in F1. -- 19h ------------- Return19 (1 byte) This single byte record returns from a subroutine; its difference from record 17h is not clear. Used 276 times in F1. -- 1Ah ------------- Equ var (5 bytes) 1 2 var1 address 3 2 var2 address Sets var1 to the value of var2. -- 1Bh ------------- Line night colour on (1 byte) This record set the night and dusk colours of following lines to a standard colour (in FS4, light blue). Its effect ceases with the next record 12h. -- 1Ch ------------- Line night colour off (1 byte) Restores the night and dusk colours of following lines to the same colour used for day. -- 1Dh ------------- VOR (11 bytes) 1 2 frequency; BCD coded (ex.: 109.15 MHz -> 15h 09h) 3 4 E coord. (fract. FSu) 7 4 N coord. (fract. FSu) -- 1Eh xxxx -------- ATC message (xxxx bytes) 1 2 record length 3 2 frequency; BCD coded (ex.: 127.15 MHz -> 15h 27h) 5 1 recommended runway number for NE winds 6 1 recommended runway number for SE winds 7 1 recommended runway number for NW winds 8 1 recommended runway number for SW winds 9 4 ?? 13 var message text (0-terminated) The message text can include any character from ASCII 20h to ASCII 93h. Characters greater than 93h result in garbage being printed. When the message is played back, characters from 80h to 93h are expanded into the following strings (stored in ATC.FS4): 80h " Whether - " 81h " OBSERVATION " 82h " XX:00 ZULU " (where XX is replaced by the current hour time) 83h "" (empty string) 84h " TEMPERATURE 25 - " 85h " INFORMATION " 86h " LANDING AND DEPARTING RUNWAY XX - " (where XX is replaced by the runway number given at offset 5) 87h " ADVISE CONTROLLER " 88h " ALTIMETER 29.95 - " 89h " VISIBILITY 10 - " 8Ah " WIND XXX at YY - " (where XXX and YY are replaced by wind direction and speed defined by the wind menu or generated by the weather generator; if both are off, this character is ignored) 8Bh " MEASURED CEILING 00600 OVERCAST " 8Ch "" (empty string) 8Dh "" (empty string) 8Eh "Microsoft Flight Simulator" 8Fh " requesting " 90h "clearance " 91h ", your are cleared " 92h "... " 93h "7777 " -- 1Fh ------DS----- Call1F (3 bytes) 1 2 byte offset (subroutine address) Subroutine call; its difference from record 18h is not clear. Used 191 times in F1. -- 20h ------------- Jump if var outside (9 bytes) 1 2 byte offset 3 2 var address 5 2 value1 7 2 value2 This record jumps over the given amount of bytes, if the value of the given variable is outside the range value1 - value2. -- 21h ------------- Jump if 2 vars outside (15 bytes) 1 2 byte offset 3 2 var1 address 5 2 min1 value 7 2 max1 value 9 2 var2 address 11 2 min2 value 13 2 max2 value This record jumps over the given amount of bytes, if var1 is outside the range min1 - max1 OR var2 is outside the range min2 - max2. -- 22h ------------- Jump if 3 vars outside (21 bytes) 1 2 byte offset 3 2 var1 address 5 2 var1 min value 7 2 var1 max value 9 2 var2 address 11 2 var2 min value 13 2 var2 max offset 15 2 var3 address 17 2 var3 min value 19 2 var3 max offset This record is similar to the previous, but involves 3 variables. -- 23h ------------- NAND Jump (7 bytes) 1 2 byte offset 3 2 var address 5 2 value Jumps if the bitwise AND of the given var value and the given value is 0. -- 24h ------------- Reference point (14 bytes) 1 1 scale factor 2 4 E coord. (fract. FSu) 6 4 AGL alt. (fract. FSu) 10 4 N coord. (fract. FSu) A reference point record is a temporary coordinate origin for delta FSunits. It is extensively used to define a point in 3D; the points of following objects are then defined relatively to this one. In vars 029A, 029C, 02A0, FS maintains the coordinates of the current view point relative to the cur- rent reference point. If the point is defined in a subroutine, it is apparently lost when the subroutine returns. Byte 1 is a scale factor determining delta unit magnitude: Factor 1 delta unit is max absolute delta (32768 units) 00 1/256 m 128 m - 1/2 FSu 01 1/64 m 512 m - 2 FSu 02 1/16 m 2048 m - 8 FSu (AAF objects, Fuel box) 03 1/4 m 8192 m - 32 FSu 04 1 m 32.8 km - 128 FSu (Most ASD objects) 05 4 m 131 km - 512 FSu 06 16 m 524 km - 2048 FSu 07 64 m 210 km - 8192 FSu 08 256 m (= 1 FSu) 837 km - 32768 FSu Most ASD created objects use factor 04 (plus factor 02 in fuel boxes only); F1 uses factors 02, 04, 06, 08; AAF created object use a factor of 02, all other factors have been tested manually. -- 25h ------DS----- Set variable (5 bytes) 1 2 variable address 3 2 new variable value Sets the given variable to the given value. -- 27h ------------- Define control vector (8 bytes) 1 2 x component of vector 3 2 z component of vector 5 2 y component of vector 6 1 vector number Defines a control vector. This vector is usually perpendicular to a surface and is it used by record 10h tests to check the "insideness" of the current point of view with respect to the surface. The vector components are computed as follows: 1) chosen 3 points, P, Q, and R, of the surface (usually 3 vertices of a 3D polygon) in clockwise order when seeing the surface from the "outside", 2) vector a = Q-P and has as components: a(x) = Q(x)-P(x); a(z) = Q(z)-P(z); a(y) = Q(y)-P(y); 3) vector b = R-Q and has as components: b(x) = R(x)-Q(x); b(z) = R(z)-Q(z); b(y) = R(y)-Q(y); 4) the vectorial product c = a x b is computed: c(x) = a(y) b(z) - a(z) b(y) c(z) = a(x) b(y) - a(y) b(x) c(y) = a(z) b(x) - a(x) b(z) 5) These components are finally scaled in order they fit in a signed 16-bit value (actually, in F1, they are almost always scaled so none of them is greater of 0x4000 in modulus). This algorithm has been determined on the example of Dan Samuel's algorithm for record 5Ah. See also discussion of record 10h, for practical applications. -- 28 -------------- Compare vars (8 bytes) 1 1 value: condition: 02 var1 > var2 ? 04 var1 < var2 ? 2 2 byte offset 4 2 var1 6 2 var2 Jumps to the given byte offset if the condition is true. Var values are treated as unsigned (8000h > 7FFFh). In SC1 buildings, a record 28h in which condition value = 36h, var1 = 034Eh, var2 = FFFFh is often used; in this case, var2 is obviously a literal value, but the performed test is not clear. -- 29h ------------- Close path (1 byte) This record, made of the single byte 29h, is used to close a path being drawn with 01h, 02h, 32h, 33h, 40h and 41h records. A line is drawn from the cur- rent point to the starting point of the last executed MoveTo record (01h, 40h, 32h). If the path begun with the surface record (2Fh), the path is filled with the colour stored in var 02E2. -- 2Ah ------------- Dotted line (14 bytes) 1 2 P1 E coord. (delta FSu) 3 2 P1 A coord. (delta FSu) 5 2 P1 N coord. (delta FSu) 7 2 P2 E coord. (delta FSu) 9 2 P2 A coord. (delta FSu) 11 2 P2 N coord. (delta FSu) 13 1 Number of dots / 2 This record draws a dotted line from P1 to P2, containing twice the number of dots given at byte 13. -- 2Bh ------------- Dashed line (14 bytes) 1 2 P1 E coord. (delta FSu) 3 2 P1 A coord. (delta FSu) 5 2 P1 N coord. (delta FSu) 7 2 P2 E coord. (delta FSu) 9 2 P2 A coord. (delta FSu) 11 2 P2 N coord. (delta FSu) 13 1 Number of dashes This record draws a dashed line from P1 to P2, containing the number of dashes given at byte 13. Note that, as each dash has two end points, this record defines the same number of points as record 2Ah. -- 2Eh ------------- ??? (3 byte) Used only twice (at offsets 00BBEE and 00D8E2) in F1, always before a 0Ch record and always in the form: 2E 09 80 0C 05 50 -- 2Fh ------------- Surface (1 byte) This record, made of the single byte 2Fh, is used to start a surface perimeter. When the perimeter is closed with 29h record, the surface is filled with the colour stored in var 02E2. -- 31h ------------- 3D-point (8 bytes) 1 1 point number 2 2 E coord (delta FSu) 4 2 A coord (delta FSu) 6 2 N coord (delta FSu) Used to define a point in 3D; the record has no display effect but the point can be thereafter addressed by drawing records through its number. -- 32h ------DS----- Move to 3D point (2 bytes) 1 1 point number Moves the pen (without drawing) to the point. Point numbers have been set by a previous 31h record. -- 33h ------DS----- Draw to 3D point (2 bytes) 1 1 point number Draws to the point. Point numbers have been set by a previous 31h record. -- 34h ------------- ??? (2 bytes) This record has been found in James Shrubsall's SC1 files right after a record 57h. -- 35h ------------- Dot (2 bytes) 1 1 point number Draws a dot at the given 3D point, prev. defined with a 31h record. -- 36h ------------- ??? (2 bytes) 1 1 ?? This record occurs only once in F1 and in each SCN, each time at the end of the AUTOLOAD scenery procedure. Byte 1 contains either the scenery number or the scenery number + 1. -- 39h ------------- ??? (5 bytes, source: Enrico Schiratti) 1 2? ??? 3 2 byte offset This record has been found by Enrico Schiratti in SD-NL (F1-format) at off- sets 001A74h and 001AC5. -- 3Bh ------------- Set elevation (5 bytes) 1 4 elevation level (fract. FSu) Set an elevation level above current ground level. Used in F1 to make elevated 'solid' surfaces, like the carrier deck or the Golden Gate Bridge. -- 3Ch ------------- ??? (4 bytes) 1 1 ?? 2 1 Scenery number (SD-x = xxh, SD-EUR = 0Eh, F1 = FFh) 3 1 AUTOLOAD procedure length This record occurs only once in F1 and in each SCN, each time at the beginning of the AUTOLOAD scenery procedure. -- 3Dh ------------- Jump if outside area (19 bytes) 1 2 byte offset 3 4 min E (fract. FSu) 7 4 max E (fract. FSu) 11 4 min N (fract. FSu) 15 4 max N (fract. FSu) Jumps if current plane position (not the view point) is outside the delimited rectangular area. -- 3Eh ------------- Jump if outside rectangle (Area record) (9 bytes) 1 2 byte offset 3 2 N coord. (int FSu) 5 2 E coord. (int FSu) 7 2 area semi-side (int FSu) Jumps if current plane position (not the view point) is outside the delimited rectangular area. The record tests for a rectangular area not a circular one. A 3Eh record (used to be called "AREA record") starts the representation of each object in SC1 files and, in fact, is the easiest way to avoid rendering an object if the aircraft is too away from it; however, as for any SDL record, it is a procedural statement and does not define an object property, it is not even mandatory: many times, in F1, several related objects are grouped within a single 3Eh rec, or a complex object is broken in many inde- pendently displayed parts. Sometimes, it is totally absent and the visibility of the object is checked by others ways. -- 40/C0h ---------- Move to 2D point (5 bytes) -- 41h ------------- Draw to 2D point (5 bytes) 1 2 E coord. of the point (delta FSu) 3 2 N coord. of the point (delta FSu) Move and draw records are used to draw line segments. A move record moves to the point given in the record without drawing anything, a draw record draws a line segment from the previous point to the given point. As Alt. coordinate, the Alt. of current reference point is used. Within SC1 files, Move record code can be either 40h or C0h, without any visible difference. -- 42h ------------- Jump if outside area (11 bytes) 1 2 byte offset 3 2 min E (int. FSu) 5 2 max E (int. FSu) 7 2 min N (int. FSu) 9 2 max N (int. FSu) Jumps if current plane position (not the view point) is outside the delimited rectangular area. -- 43h ------------- ??? (29 byte) 1 2 byte offset 3 4 E coord (fract FSu) 7 4 A coord (fract FSu) 11 4 N coord (fract FSu) 15 14 ?? Used only 5 times in F1, 4 times after 00BF4C (around the Catalina I.) and 1 time at 01E1E1 (within Oakland Int'l). It seems to be a test based on some geometrical property of the given point. -- 44h ------------- Define array of points (15 bytes) 1 1 i, first point number 2 2 P1 E (delta FSu) 4 2 P1 A (delta FSu) 6 2 P1 N (delta FSu) 8 2 P2 E (delta FSu) 10 2 P2 A (delta FSu) 12 2 P2 N (delta FSu) 14 1 n, number of points Defines n points, consecutively numbered from i onward and evenly distributed across the 3D segment from P1 to P2. Used only 4 times in F1 to define the points for the 'net' on the side of the mountain in front of San Francisco. -- 45h xxxx -------- Thermal generator (xxxx bytes) 1 2 record length (0025h) 3 4 E coord of generator center (fract FSu) 7 4 altitude AGL of generator center ? 11 4 N coord of generator center (fract FSu) 15 2 orientation 17 1 ??? 18 2 generator width (in m) 20 2 ??? 22 2 thermal effect height (in feet) 24 2 ??? 26 2 generator length (in m) 28 9 ??? This record has been found only in thermal generators. Used 11 times in F1. -- 47h ------------- Conditional point list ??? (8 bytes) 1 2 byte offset 3 4 four point numbers 7 1 always FFh Seems to be a conditional jump. Bytes 3-6 contain point numbers (previously defined with records 31h). The test performed is not clear; as it used to jump over the rendition of entire buildings (not of individual walls), it seems more reasonable to think to a magnitude test, than to an orientation test. Found 11 times in F1: 006059 47 54 01 01 03 05 06 FF 0073DD 47 8F 00 01 02 05 06 FF 007EC1 47 66 00 00 00 00 00 FF 007F96 47 49 00 01 03 06 00 FF 007FF6 47 33 00 00 00 00 00 FF 0080B4 47 8D 01 01 04 08 0C FF 008289 47 59 00 00 01 02 03 FF 0083D3 47 B0 00 00 05 07 02 FF 0084AA 47 F3 00 03 09 0A 00 FF 009729 47 EE 00 03 09 0A 00 FF 01FC06 47 E9 05 01 02 03 04 FF -- 49h ------------- Runway end lights (20 bytes) 1 4 E coord (fract. FSu) 5 4 A coord (fract. FSu) 9 4 N coord (fract. FSu) 13 2 heading (in 1/182.04ø) 15 1 light bits: 0 end lights 1 MALSR 2 REIL 3 VASI 4 moving strobes 5 ?? (irrelevant?) 6 ?? (irrelevant?) 7 ?? (irrelevant?) 16 1 moving strobe length (in ??) 17 2 VASI glide slope (in 1/10ø) 19 1 ?? Places a runway end light system. The given point is the end of the runway to which this record is always ideally applied. -- 4Ah ------------- Surface4A ?? (1 byte) This single byte record is used to start a surface path; the difference with record 2Fh is not clear. Used 8 times in F1. -- 4Bh ------------- Jump4B ?? (3 bytes) 1 2 byte offset This record, used only once in F1, seems to be another jump instruction. Its difference with record 0Bh is not apparent. -- 4Ch ------DS----- ??? (2 bytes) =SEE= -- 4Dh xxxx--DS----- Thermal generator (xxxx bytes) 1 2 record length 3 4 E coord (fract FSu) 7 4 A coord (fract FSu) 11 4 N coord (fract FSu) 15 ?? ?? Another thermal generator defining record. Used 7 times in F1. -- 4Eh ------DS----- ??? (4 bytes) =SEE= -- 4Fh ------------- ILS (15 bytes) 1 2 frequency; BCD coded (ex.: 109.15 MHz -> 15h 09h) 3 4 E coord. (fract. FSu) 7 4 N coord. (fract. FSu) 11 2 Approach course in 1/3ø (0 -> 0, 359 -> 0435h) 13 2 Glide slope in 1/9100ø (0 -> 0, 7.20 -> FFFFh) ----- The following records, up to 79h excluded, are never used in F1 but only in SC1 files, either standard or SEE enhanced; they seem not to be recognized by FS4 and are probably an ASD extension. ----- -- 50/D0h ---------- Runway (35 bytes) =SC1= See below under runway description for details. -- 51h ------------- Side list end (used in mountains, 1 byte) =SC1= -- 52h ------DS----- ??? (2 bytes) =SEE= -- 53h ------------- Building (variable) =SC1= The building record defines the aspect of a building; its length and struc- ture varies according to the building type. Here a summary is given, see below, under building descriptions, for details. byte 1 building type and length 01 Rectangular building record (18 [flat] and 19 [peaked] bytes) 02 L building record (24 [flat] and 27 [peaked] bytes) 03 T building record (28 [flat] and 32 [peaked] bytes) 04 U building record (28 [flat] and 33 [peaked] bytes) 05 H building record (34 [flat] and 41 [peaked] bytes) 06 Reversed L build. record (24 [flat] and 27 [peaked] bytes) 07 Control tower record (20 bytes) 29 Tower record (6 bytes) 33 Suspended bridge record (10 bytes) 34 Bridge record (10 bytes) 3D Timing gate record (17 bytes) 42 Coniferous tree record (7 bytes) 43 Deciduous tree record (7 bytes) 47 Auto record (3 bytes) 4C Multi-sided building record (13 bytes) -- 57h ------------- Exec 8088 code (3 bytes, source: James Shrubsall) =SC1= 2 2 8088 routine offset This record executes the 8088 code routine at offset. The routine must end with a RETF instruction and may access the SDL code in the SC1 addressing the CS: segment, the offset 0 of this segment is at the beginning of the SC1. -- 58h ------DS----- 3D text (variable) =SEE= 1 8 ??? 9 1 text size 10 xx text, 0-terminated -- 59h ------------- ??? (3 bytes) =ATP= 1 2 ?? This record has been found only the ATP (NOT FS4) default scenery F1. -- 5Ah ------DS----- 3D-triangle (10 bytes) =SC1= 1 2 E component of the "triangle vector" (see below) 3 2 A component 5 2 N component 7 3 numbers of the 3 points, listed in anti-clockwise order looking to the triangle from outside This record is used in .SC1 mountains to draw 3D triangles with hidden sur- face removing. The "triangle vector" is the cross product of the vectors for the P2-P1 and the P3-P1 edges of the tiangle, the cross product is then scaled so that no coord value is > 16767 (see also record 27h for examples). Point numbers at offset 7-9 correspond to mountain vertices defined by previous 31h records. -- 62h ------------- ??? (10 bytes) =SC1= -- 6Fh ------DS----- ??? (11 bytes) =SEE= -- 79h ------------- SDL End (1 byte) Exits the SDL processor. Used in SC1 only at the end of each section, within F1 it occurs even in the middle of procedure with a complex execution flow and multiple exit points (SDL is not structured, after all!); it cannot be used within subroutines, otherwise FS4 crashes. ====================================================================== NOTES ON FILES STRUCTURES GENERAL CONSIDERATIONS At least two scenery disk formats exist: one is the format of the default scenery F1 and of some of the new add-on sceneries (at least the MS-x.SCN series is in this format); the other is the format of the older .SCN files. These two formats have been conventionally called "F1" and "SCN" formats. To these base scenery format, the format of .SC1 additional sceneries can be added. Sceneries are made of "procedures", each procedure being a single piece of SDL code individually executed. Procedures do not contain absolute references to other procedures, the only inter-procedural link known so far being the 0Fh record. Procedure entry points are listed in the headers of SC1 files and of F1; SCN files contain a 0Ah record defining the procedure list in the main procedure (see below). One of the procedures is the main scenery entry point, henceforth called "procedure 00"; it is directly called by FS and it activates (through the 0Fh record) other procedures according to the current view point position, which it checks with appropriate tests (generally on the view point coordinate vars 0292h to 029Ah). In the F1 format, the main procedure is the first listed in the procedure table at offset 000022h; in the SCN format, the main procedure starts at the fixed offset 010800h. In SCN-format sceneries for ATP, however, proc 00 address is declared at file offset 000204h. Interaction between the base scenery and SC1 is complex: the nine SC1 layers are not executed together AFTER base scenery procedures, because at least base scenery buildings are drawn after some of the SC1 additions: one can imagine that ASD, after selecting the SC1 file appropriate to the current plane position, intercepts FS4 calls to the SDL processor and intermixes calls to it passing the SC1 layers. ==================================== SOME NOTES ON F1 CONTENTS F1 HEADER F1 begins with a header made of the elements listed below; given values come from ver. 4.0b's F1. 0000 02DD F1 format signature 0002 00000106 0081 offset and length of the dialogue descriptor 0008 00000187 0028 offset and length of the AUTOLOAD procedure 000E 00000000 0000 offset and length of RESERVED1 0014 00000000 0000 offset and length of RESERVED2 001A 00000000 0000 offset and length of RESERVED3 0020 0026 number of scenery procedures Then, a 6-byte entry table is given with, for each scenery procedure: oooooooo llll file offset and length of each procedure This table is used to locate the procedures activated with the 0F record; procedures are implicitly numbered from 0. A descriptor of the dialogue window displayed when the scenery is selected follows, each text line is described by: 01 xxxx yyyy 00 "line text " 00 00 xxxx and yyyy being the video coordinates of the line starting point, in some sort of device independent unit of measure. A record: 00 may mark the end of the descriptor; the surest clue to detect the end is, however, the length of the descriptor stated at offset 0006h. Also, the dialogue appears right after the table in F1 and Microscene's F1-format sceneries; in other F1-format sceneries, it appears at other positions; again, the surest clue is the dialogue descriptor offset stated at offset 000002h. The dialogue is followed by the AUTOLOAD procedure (its nature has been dis- covered by John Blackie): 0187 3C 00 FF 28 ??? 018B 21 0012 Jump to 019D if 0000 F470 FD80 var 0000 outside F470-FD80 or 0000 D972 E312 var 0000 outside D972-E312 019A 0B 0012 Jump to 01AC 019D 21 0012 Jump to 01AF (addr. of the 1st procedure) if 0000 EFEC FB8C var 0000 outside EFEC-FB8C or 0000 E312 EBEC var 0000 outside E312-EBEC 01AC 36 00 ??? 01AE 79 END SDL Processor where, in each 21h test, the first instance of var 0000 stand for a North range and the second for an East range. Actually, in F1 this procedure does not make much sense, but in other sceneries its tests match the populated areas; moreover FS, at startup, scans all *.SCN files for this procedure. Practically, this procedure implements the Scenery Automatic Loading option found in the Scenery Selection Menu. It is worth noting that in some F1-format files (like the MS-x.SCN series), the AUTOLOAD procedure is made only a 79h record, with a copryright notice embedded after it. After that, at 01AF, the first scenery procedure (procedure 00) begins. ---------- F1 PROCEDURES F1 contains 38 procedures. PROCEDURE 00 Procedure 00 is the main procedure and is made of a big "switch"-like series of tests which activates the appropriate procedure, according to the current view point position. This is a rendition of F1 procedure 00 in a C-like pseudo-code: 01AF if(East in 16884-17884 && North in 21884-22884) 01B8 END; 01B9 if(East in 15884-16884 && North in 21884-22884) 01C2 { 0F(07, 06, 0177, 00); // Walls in the sky 01C8 goto 0339; } 01CB if( (var0286 && 0x0001) // if drawing in the map window 01D2 & (Alt && 0xFF00)) // AND Alt > 65536 m 01D9 goto 0333; // draw world map 01DC if(East in 15884-16884 && North in 16950-17584) // MICHIGAN AREA 01EB { 0F(25, 06, 014E, 00); 01F1 goto 0339; } 01F4 if(East in 15884-16884 && North in 15950-16950) // ILLINOIS AREA 01FD { 0F(02, 06, 013C, 00); 0203 goto 0339; } 0206 if(East in 5384-6384 && North in 14501-16301) // SOUTH CALIF. AREA 0215 if(North in 15301-16301) 021E { 0F(0A, 06, 011B, 00); // Los Angeles area 0224 goto 0339; } else 0227 { 0F(09, 06, 0112, 00); // San Diego area 022D goto 0339; } 0230 if(East in 5534-7084 && North in 20384-22164) // WASHINGTON AREA 023F if(North in 21384-22164) 0248 { 0F(0E, 06, 00F1, 00); 024E goto 0339; } else 0251 { 0F(0F, 05, 00E8, 00); 0257 goto 0339; } 025A if(East in 20413-21414 && North in 16814-17884) // NEW YORK AREA 0269 { 0F(16, 05, 00D0, 00); 026F goto 0339; } 0272 if(East in 21403-22603 && North in 17034-18234) // BOSTON AREA 027B { 0F(15, 06, 00BE, 00); 0281 goto 0339; } 0284 if(East in 6884-7884 && North in 16884-17884) // WORLD WAR I AREA 028D { 0F(08, 04, 00AC, 00); 0293 goto 0339; } 0296 if(East in 4784-6244 && North in 16210-18584) // N. CALIF. AREA 02A5 { if(East in 4944-5444 && North in 17084-17584) 02B4 { if(var02AC & 0x8000) // if looking westward (?) 02BB if(East in 5098-5151 && North in 17391-17484) 02CA goto 02EE; else goto 02DF; 02CD if(East in 5098-5126 && North in 17391-17484) 02DC goto 02EE; 02DF if(East in 4974-5098 && North in 17366-17534) 02EE { 0F(1B, 08, 004B, 00); 02F4 goto 0339; } 02F7 if(East in 4384-5251 && North in 17291-17583) 0306 { if(East in 5174-5274 && North in 17279-17329) 0315 goto 0321; 0318 0F(23, 05, 0021, 00); 031E goto 0339; } else 0321 { 0F(1E, 05, 0018, 00); 0327 goto 0339; } } 032A 0F(24, 07, 000F, 00); 0330 goto 0339; } 0333 0F(01, 06, 0006, 00); // word map 0339 END Procedure 01 is the continent map. It is activated by proc 00 if the window being drawn is the map window (testing var 0286) and the view point is above 65537 m AGL or if no other procedure applies. It is worth noting that, as with any other scenery, the seas are drawn over the ground with blue polygons and not viceversa. As John Blackie pointed to me, one important reason for that is the possibility to add tests before sea polygon drawing, in order to avoid drawing them if the view point is sufficiently inland, thus simulating the Earth surface curvature. The procedure is quite complex and directly contains the more detailed local variants. Procedures 2 to 37 draw the 7 populated areas (New York-Boston, Chicago, Seattle, San Francisco, Los Angeles, WW1 area and Wall in the Sky area). Simpler areas are rendered by just one procedure, the most complex by many procedures either adjacent (as the Los Angeles and the San Diego procedures) or layered one above the other; in the latter case, layering is obtained with nested 0Fh record calls. This is a summary of procedure properties. no length area called with by calling -- ------ ---- --------------- -- ------- 00 395 selector -- -- 01, 02, 07, 08, 09, 0A, 0E, 0F, 15, 16, 1B, 1E, 23, 24, 25 01 4620 map 0F 01 06 0006 00 00 02 11969 IL 0F 02 06 013C 00 00 03 7607 MI 0F 03 06 000A 01 25 06 04 4783 MI 0F 04 06 0031 01 25 05 7070 MI 0F 05 06 0013 01 25 06 2203 MI 0F 06 06 0006 02 03 07 3799 WItS 0F 07 06 0177 00 00 08 4003 WWI 0F 08 04 00AC 00 00 09 7372 SD 0F 09 06 0112 00 00 0A 5639 LA 0F 0A 06 011B 00 00 0B, 0C, 0D 0B 1149 LA 0F 0B 02 0C36 01 0A 0F 0B 02 0CF6 01 0A 0C 775 LA 0F 0C 01 0785 01 0A 0F 0C 01 084A 01 0A 0D 557 LA 0F 0D 01 08CA 01 0A 0F 0D 01 099E 01 0A 0F 0D 01 0D7E 01 0A 0F 0D 01 0E09 01 0A 0E 8674 WA 0F 0E 06 00F1 00 00 10, 11 0F 5824 WA 0F 0F 05 00E8 00 00 12, 13, 14 10 791 0F 10 01 11D1 01 0B 0F 10 01 12AF 01 0B 11 407 WA 0F 11 01 1390 01 0E 0F 11 01 145C 01 0E 12 770 0F 12 01 08AC 01 0F 0F 12 01 0972 01 0F 13 554 0F 13 01 0C6E 01 0F 0F 13 01 0D25 01 0F 14 413 0F 14 01 09F1 01 0F 0F 14 01 0AB6 01 0F 15 6597 MA 0F 15 06 00BE 00 00 16 4634 NY 0F 16 05 00D0 00 00 17, 18, 19 17 1202 NY 0F 17 02 0972 01 16 0F 17 02 0A14 01 16 18 597 NY 0F 18 01 082F 01 16 0F 18 01 08B5 01 16 19 2422 NY 0F 19 02 018F 01 16 1A 699 CA 0F 1A 02 10F7 01 23 1B 9806 CA 0F 1B 08 004B 00 00 1C 421 CA 0F 1C 01 0523 02 21 1D 3900 CA 0F 1D 04 0009 01 1E 1E 3347 CA 0F 1E 05 0018 00 00 1D, 21 1F 1970 CA 0F 1F 02 12B1 01 23 20 1562 CA 0F 20 02 1307 01 23 21 3370 CA 0F 21 03 0012 01 1E 1C, 22 22 1504 CA 0F 22 02 0686 02 21 23 9733 CA 0F 23 05 0021 00 00 1A, 1F, 20 24 6404 CA 0F 24 07 000F 00 00 25 1516 MI 0F 25 06 014E 00 00 03, 04, 05 RECORD 0Fh OCCURRENCES IN CALLING HIERACHY 0F 01 06 0006 00 0F 02 06 013C 00 0F 07 06 0177 00 0F 08 04 00AC 00 0F 09 06 0112 00 0F 0A 06 011B 00 ÄÂÄ> 0F 0D 01 0E09 01 ÃÄ> 0F 0D 01 0D7E 01 ÃÄ> 0F 0B 02 0CF6 01 ÃÄ> 0F 0B 02 0C36 01 ÃÄ> 0F 0D 01 099E 01 ÃÄ> 0F 0D 01 08CA 01 ÃÄ> 0F 0C 01 084A 01 ÀÄ> 0F 0C 01 0785 01 0F 0E 06 00F1 00 ÄÂÄ> 0F 11 01 145C 01 ÃÄ> 0F 11 01 1390 01 ÃÄ> 0F 10 01 12AF 01 ÀÄ> 0F 10 01 11D1 01 0F 0F 05 00E8 00 ÄÂÄ> 0F 13 01 0D25 01 ÃÄ> 0F 13 01 0C6E 01 ÃÄ> 0F 14 01 0AB6 01 ÃÄ> 0F 14 01 09F1 01 ÃÄ> 0F 12 01 0972 01 ÀÄ> 0F 12 01 08AC 01 0F 15 06 00BE 00 0F 16 05 00D0 00 ÄÂÄ> 0F 17 02 0A14 01 ÃÄ> 0F 17 02 0972 01 ÃÄ> 0F 18 01 08B5 01 ÃÄ> 0F 18 01 082F 01 ÀÄ> 0F 19 02 018F 01 0F 1B 08 004B 00 0F 1E 05 0018 00 ÄÂÄ> 0F 21 03 0012 01 ÄÂÄ> 0F 22 02 0686 02 ³ ÀÄ> 0F 1C 01 0523 02 ÀÄ> 0F 1D 04 0009 01 0F 23 05 0021 00 ÄÂÄ> 0F 20 02 1307 01 ÃÄ> 0F 1F 02 12B1 01 ÀÄ> 0F 1A 02 10F7 01 0F 24 07 000F 00 0F 25 06 014E 00 ÄÂÄ> 0F 04 06 0031 01 ÃÄ> 0F 05 06 0013 01 ÀÄ> 0F 03 06 000A 01 ÄÄÄ> 0F 06 06 0006 02 ---------- F1 RECORD COUNTS record times record times record times 0(00): 43 28(1C): 411 53(35): 19 1(01): 137 29(1D): 173 54(36): 1 2(02): 449 30(1E): 45 59(3B): 9 3(03): 178 31(1F): 191 60(3C): 1 4(04): 4 32(20): 158 61(3D): 7 5(05): 68 33(21): 416 62(3E): 917 11(0B): 408 34(22): 235 64(40): 1746 12(0C): 2 35(23): 417 65(41): 8157 14(0E): 39 36(24): 783 66(42): 78 15(0F): 49 37(25): 849 67(43): 5 16(10): 99 39(27): 121 68(44): 4 18(12): 270 40(28): 161 71(47): 11 19(13): 63 41(29): 1298 73(49): 32 20(14): 81 42(2A): 117 74(4A): 8 22(16): 1 43(2B): 62 75(4B): 1 23(17): 26 46(2E): 19 77(4D): 7 24(18): 624 47(2F): 832 79(4F): 25 25(19): 276 49(31): 1405 121(79): 123 26(1A): 314 50(32): 771 27(1B): 454 51(33): 2107 ---------- NOTE ON SCN FILES SCN files have a very different structure than F1. Generally speaking, the SCN structure seems to be an old leftover of the time when sceneries were loaded from floppy disks without a secure DOS aid (FS was an auto-booting protected program). Now, the only reason for implementing such a format seems to be a possible compatibility with the SubLogic's ATP program. The general structure of SCN files can be outlined as follows: 000000-0002FF Only garbage: some files contain a boot-strap sector, other just a lot of 79h records. 000300-0003FF The first bytes contain the AUTOLOAD procedure. The remaining part of this area does not have any apparent sense. 000400-00E7FF Available for scenery procedures. 00E800-00EBFF Dialogue descriptor area 00EC00-0107FF Available for scenery procedures. 010800-010BFF Procedure 0 010C00-end Available for scenery procedures. SCN file space is allocated in 1 kB "clusters" or blocks. If the length of a procedure is not an exact multiple of 1 kB, the portion from its end to the next kB boundary is left uninitialized. Procedure 00 is at the fixed file offset 010800h and, judging from FS file activity during SCN loading, seems to be limited to 1 kB (see below for info on ATP's F1 proc 00). SCN format does not contain a procedure table, as F1 format does; it uses instead a record 0A in procedure 00 to define the code, file offset and length of other procedures. Because only the hight byte of procedure offset fields in record 0A is actually ingored, SCN format scenery cannot be longer than 256 kB. DIALOGUE DESCRIPTOR SCN-format dialogue descriptor has a different structure than F1-format's. In particular, it does not include screen coordinates of text lines; a rudimentary layout formatting is obtained through blank lines (which however always contain at least a white space). Dialogue text lines begin at offset 00E832 and have the following structure: 01 00 "line text" 00 the dialogue text end is marked by: 00 00 Sections 00E800-00E831 and from the end of the text to 00EBFF contain machine code and replicate the structure of a .DRV (see below); they are probably useless, now. It is worth noting that a file may have an .SCN extension and still use the F1 structure, as the MS-x.SCN scenery series does. ---------- ATP SCN FORMAT ATP sceneries are in the same SCN format, with some notable exceptions: At file offset 000200h, there is a sort of header (from an indirect (!) com- munication of Simon Hradezky): 000200 1 01 (ATP flag, differentiates ATP SCNs from FS SCNs) 000201 1 Reserved 000202 2 required RAM in paragraphs (16 bytes) 000204 2 offset of Proc 00 in kB units 000206 2 length of Proc 00 in kB units 000208 2 Reference number (identifies the scenery?) ATP sceneries contain at least one record unattested in FS SCN (record 59h). In ATP sceneries, the main entry proc is not fixed at file offset 0010800h and to 1 kB length, but is parametrized in the header. ====================================================================== ASD STATIC SCENERY FILES (.SC1) (Beyond its specific contents, this section can also be seen as a sort of tutorial in interpreting SDL records, because of the commented examples it contains.) .SC1 GENERAL STRUCTURE .SC1 files are made of: ù a header containing a lookup table for the various file sections, the scenery boundaries, and the scenery name; this header is 73 bytes long; ù 9 sections, containing definitions of Navaids, Polygon, Rivers, Roads, Lines, Runways, Mountains, Timing gates, and Buildings respectively. Each section is terminated by a 79h record. In SC1 files, some record codes can have the most significant bit set or reset, without any apparent difference. ==================== HEADER STRUCTURE - length: 73 bytes 0 2 file size 2 2 0003h (a kind of signature?) 4 2 002Ah (= 42, pointer to scenery name) 6 2 0049h (= 73, header length) 8 2 pointer to Navaid section (always 73) 10 2 pointer to Polygon section 12 2 pointer to River section 14 2 pointer to Road section 16 2 pointer to Line section 18 2 pointer to Runway section 20 2 pointer to Mountain section 22 2 pointer to Timing gate section 24 2 pointer to Building section 26 4 E coord. of scenery center (fract. FSu) 30 4 N coord. of scenery center (fract. FSu) 34 2 scenery radius (int. FSu) 36 6 always 0 ?? 42 31 scenery names: up to 30 characters (padded with space, if shorter) plus a 0 ending byte ==================== OBJECT DETAILED DESCRIPTIONS The following section contains a detailed description of structure of all the objects found in standard .SC1 files, with examples of decoding. With the exception of ATC messages, SEE extensions are not included. One must not assume that the following structures are THE object structures, because base sceneries (either in F1 or SCN format) are not bound to them and, given the procedural nature of SDL, any succession of records yielding the same, or similar, result could work. I found that even ASD is not bound to them and can correctly execute SC1 files containing other record succes- sions, while it may no longer able to edit them. In SC1, there is a 3Eh record at the beginning of each object, skipping it if it cannot be seen (or tuned) from the current plane position; under the spe- cial SC1 conditions, I keep the previous name of "AREA record" and the byte offset in it as "object length". ==================== NAV AIDS Like all .SC1 object, navaids begin with an area record; to the area record, NDB, VOR, and ILS add a specific record (05h, 1Dh, 4Fh, resp.); Markers add a 25h record setting var 02F6h (inner marker), 02F8h (outer marker) or 02FAh (middle marker) to 0001. Adding the 9 bytes of the area record, the total length of each kind of Nav aids is (in parenthesis, the default area radius set by ASD): NDB 20 bytes (500 FSu = 128 Km = 69 NM) VOR 20 bytes (500 FSu = 128 Km = 69 NM) ILS 24 bytes (250 FSu = 64 Km = 34.6 NM) OM 14 bytes (2 FSu = 512 m) MM 14 bytes (2 FSu = 512 m) IM 14 bytes (1 FSu = 256 m) Example: 3E 18 00 92 03 8C 04 FA 00 4F 25 09 00 06 8C 04 00 00 92 03 2C 01 FF 6A is interpreted as: 3Eh Area record 0018h object is 24 bytes long 0392h N coord of visib. area is [0392h =] 914 + 16384 = 17298 048Ch E coord of visib. area is [048Ch =] 1164 + 16384 = 17548 00FA area radius is [FAh =] 500 FSu 4Fh ILS record 0925h frequency is 109.25 MHz 048C0600h E coord is [0485.06h =] 1164+6/256 + 16384 = 17548.0234 03920000h N coord is [0392.00h =] 914+0/256 + 16384 = 17298.0000 012Ch approach course is [012Ch =] 300 / 3 = 100ø 6AFFh glide slope is [6AFFh = ] 27391 / 9100 = 3.01ø ==================== ATC MESSAGES ASD cannot add ATC messages to sceneries. However, messages added to .SC1 files with other programs (or manually!) are correctly played by FS4 and do not interfere with ASD ability to manipulate the modified .SC1. The following structure has been determined from SEE4-modified sceneries. ATC messages are made by: ù an area record ù a 0B jump record with 2-byte embedded code: 0Bh 0005h 41h 43h (where 41h 43h, "AC", is probably an ID meaning "ATC") ù an ATC message record (1Eh) ==================== POLYGONS Polygon descriptions are made of an area record, a ref. point record, a sur- face colour record and a 2Fh, 40h, 41h, [41h...] 29h record sequence (there- after called "perimeter") describing the polygon perimeter. As for any object of variable size, area radius is not fixed, like in nav aids, but depends on the polygon size. Triangles are special, because, after the polygon proper, they add a 3-point line corresponding to two of the three sides of the triangle; this line has the same colour of the triangle and cannot be seen. Example: 3E 3E 00 92 03 8D 04 03 00 24 04 00 4D 8D 04 00 0A 00 00 00 B9 92 03 25 E2 02 99 99 2F 40 F2 FF 08 00 41 0D 00 0B 00 41 0F 00 F6 FF 29 12 09 40 F2 FF 08 00 41 0D 00 0B 00 41 0F 00 F6 FF is interpreted as: 3Eh Area record 003Eh object is 62 bytes long 0392h N coord of visib. area is 17298 048Dh E coord of visib. area is 17549 0003 area radius is 3 FSu 24h 04h Ref. point record, scale factor = 4 048D4D00h E coord is [048D.4Dh =] 1165+77/256 + 16384 = 17549.0273 00000A00h altitude above ground level is [00000Ah =] 10 m 0392B900h N coord is [0392.B9h =] 914+185/256 + 16384 = 17298.7227 25h Set variable record 02E2h variable at 02E2 (surface colour) 9999h set to colour 9 (yellow) 2Fh Path 40h Move record FFF2h E coord of P1: [FF.F2h =] -14/256 + 17549.0273 = 17548.9726 0008h N coord of P1: [00.08h =] 8/256 + 17298.7227 = 17298.7540 41h Draw record 000Dh E coord of P2: [00.0Dh =] 13/256 + 17549.0273 = 17549.0781 000Bh N coord of P2: [00.0Bh =] 11/256 + 17298.7227 = 17298.7657 41h Draw record 000Fh E coord of P3: [00.0Fh =] 15/256 + 17549.0273 = 17549.0859 FFF6h N coord of P3: [FF.F6h =] -10/256 + 17298.7227 = 17298.6836 29h Close path (polygons with 4 or more points, would stop there) 12h 09h Line colour is 9 (yellow) 40h FFF2h 0008h same move record as above 41h 000Dh 000Bh same draw record as above 41h 000Fh FFF6h same draw record as above ==================== RIVERS Even if they are created in ASD by stretching and bending rectangular strips of colour, rivers are actually memorized in scenery files as polygons, and follow the same format described in the previous section. The reason for keeping them in a specific section resides probably in the order in which scenery object are drawn. Rivers can also contain skips: in this case, the river description contains a single area record and a single ref. point record followed by a surface colour record and a perimeter for each polygon created by skipping. ==================== ROADS Roads also are memorized as polygons, and follow the polygon format. For skippings, the same observation made about rivers, holds also for roads. Country roads and city streets require no observations. 4-lane roads contain, after the perimeter describing the road perimeter, a line colour record and a multi-line describing the road middle line. Divided highways, after the area and ref. point records, contain a single surface colour record (25h) with two perimeters to describe the two road ways, then a line colour record, a conditional jump record (23h) on var 028Ch value and another line colour record to change colour line according to day time, and a multi-line with 4 jumps to describe the 4 borders of the ways. ==================== LINES Line descriptions are made of an area record, a ref. point record, a line colour record and a 40h, 41h, [41h...] record sequence ("multi-line") des- cribing the line shape. If the line contains skips, a new line colour record and a new multi-line are generated for each line section. ==================== RUNWAYS Runway descriptions are made of 2 area records referring to the same point (one spanning the entire object and the other covering only the altitude set- ting), a 25h record to set area altitude and the specialized runway record: Runway record - code: 50h/D0h length: 35 bytes 0 1 50h or D0h: record code 1 4 E coord of center (fract. FSu) 5 4 Altitude of center (fract. FSu) 9 4 N coord of center (fract. FSu) 13 1 Design elements (bit is 1 if the element is present): bit 7: always 1 6: always 1 5: Numbers 4: Dashes 3: Fixed distance markers 2: Touchdown markers 1: Threshold markers 0: Edges 14 1 Runway colour (repeated in each nibble) 15 1 Edge colour (") 16 1 Threshold marker colour (") 17 1 Touchdown marker colour (") 18 1 Fixed distance mrkr colour (") 19 1 Dash colour (") 20 1 Number colour (") 21 1 Runway number (down side) as hex number 22 1 Designator: 0: none 1: LEFT/RIGHT 2: RIGHT/LEFT 3: CENTER/CENTER 23 1 Down side lights: bit 0: End light 1: always 0? 2: REIL 3: VASI high nibble value: 0: none 1: MASLR 2: MASLR with strobes 3: SSALR 4: SSALR with strobes 5: MALSF 6: MALSF with strobes 7: SSALF 8: SSALF with strobes 9: ALSF-I A: ALSF-II 24 2 Down side VASI slope in 1/10ø 26 1 Up side lights (as in byte 23) 27 2 Up side VASI slope in 1/10ø 29 2 Up side direction in 1/182.04ø 31 2 Runway width in m 33 2 Runway length in m Note: up side refers to the runway end located up when placing it, down side is the other end. Example: 3E 3A 00 2B F9 2D 05 32 00 3E 0E 00 2B F9 2D 05 15 00 25 EF 02 0F 00 D0 00 4C 2D 05 00 00 00 00 00 21 2B F9 FF 00 88 DD 88 99 FF FF 04 00 01 1C 00 39 1E 00 5C 15 2D 00 52 08 is interpreted as: 3Eh Area record 003Ah object is 58 bytes long (includes the entire object) F92Bh N coord is [F92Bh =] 63787 - 49152 = 14635 052Dh E coord is [052Dh =] 1325 + 16384 = 17709 0032h area radius is 50 FSu (12.8 Km) 3Eh Area record 000Eh 14 bytes (includes only this record and the following) F92Bh N coord is 14635 again 052Dh E coord is 17709 again 0015h inner area radius is 21 FSu (5.4 Km) 25h Set var 02EFh at 02EFh (area altitude) 000Fh to 15 m above sea level D0h Runway record 052D4C00h E coord. of runway is 17709.2969 00000000h Altitude is 0 F92B2100h N coord. of runway is 14635.8711 FFh runway has all design elements 00h runway colour is Black 88h edge colour is Brown DDh threshold mkr colour is Gold 88h touchdown mkr colour is Brown 99h fix. dist.mkr colour is Yellow FFh dash colour is White FFh number colour is White 04h runway number is 4 00h no designator 01h down side has end lights 001Ch down side VASI slope is [1Ch =] 28 / 10 = 2.8ø * 39h up side has VASI and end light (9) of type SSALR (3) 001Eh up side VASI slope is [1Eh =] 30 / 10 = 3.0ø 155Ch runway direction is [155Ch =] 5468 / 182.04 = 30.04ø 002Dh runway is [002Dh =] 45 meter wide 0852h runway is [0852h =] 2130 meter long Note: down side VASI slope is actually undefined because down side has no VASI. ==================== MOUNTAINS Mountains are among the most complex ASD objects. These are the records used to define a mountain: ù an area record, ù a delayed call (0Eh) calling the actually drawing routine ù a jump record (0Bh) skipping the entire mountain definition The drawing routine follows, made of: ù a ref. point record. for each peak and each point of the base there is: ù a 3D-point record (31h) ù a 25h 031Eh 0000h constant record ù a 22h record with a byte offset of 001Ah and checking values of vars at 029Ch (delta E coord.), 029Eh (delta A coord.), and 02A0h (delta N coord.) ù a 25h 031Eh 0001h constant record Then, for each side of the mountain, two records are given: ù an area colour record (25h 02E2h xxxxh) ù a 3D-triangle record (5Ah) ù a 51h record ù a RET from subroutine (19h) Example: This example describes a square mountain, with sides 2 FSu long and parallel to the coordinate axes. 3E 00A2 0393 048C 0040 Center: 17299, 17548; radius: 64 FSu 8E 0006 Call the subroutine 0B 0096 Jump over [0096h =] 150 bytes ; the drawing routine: 24 04 048C0000 00000000 03930000 Ref. point: 17548 E, 0 AGL, 17299 N 31 01 0080 0098 0080 1st peak: +0.5 E,+152 m, +0.5 N from ref. point 31 21 FF00 0000 0100 1st point:-1.0 E, + 0 m, +1.0 N from ref. point 31 22 0100 0000 0100 2nd point:+1.0 E, + 0 m, +1.0 N from ref. point 31 23 0100 0000 FF00 3rd point:+1.0 E, + 0 m, -1.0 N from ref. point 31 24 FF00 0000 FF00 4th point:-1.0 E, + 0 m, -1.0 N from ref. point 25 031E 0000 Set var at 031Eh to 0 (fixed) 22 001A 3-var rec.: byte offs. 26 (skips over next 25h rec) 029C FF00 0100 var 029Ch (E range): -1.0 to +1.0 around ref. point 029E 0000 0198 var 029Eh (A range): 0 to [0198h - 0100h =] 152 m 02A0 FF00 0100 var 02A0h (N range): -1.0 to +1.0 around ref. point 25 031E 0001 set var at 031Eh to 1 (fixed) 25 02E2 5555 Surface colour: Light Grey 5A 1300 D000 0000 01 21 24 Triangle thru 1st peak, 1st and 4th points 25 02E2 8888 Surface colour: Brown 5A 0000 D000 1300 01 24 23 Triangle thru 1st peak, 4th and 3rd points 25 02E2 AAAA Surface colour: Dark Grey 5A DA00 E000 0000 01 23 22 Triangle thru 1st peak, 3rd and 2nd points 25 02E2 5555 Surface colour: Light Grey 5A 0000 E000 DA00 01 22 21 Triangle thru 1st peak, 2nd and 1st points 51 End of triangle list 19 RETurn ==================== TIMING GATES Timing gate description is not fully deciphered. It is made of: ù an area record ù a delayed call (0Eh) calling the drawing routine ù a jump record (0B) skipping over the drawing routine Then the drawing routine follows, made of: ù a reference point record ù an orientation record calling a tilt-drawing sub-routine ù a RET from subroutine (17h) (return from delayed call) The tilt-drawing sub-routine follows, made of: ù a specialized timing gate record (53h 3Dh) ù a RET from subroutine (19h) (return from the orientation call). -- 53h 3Dh --------- Timing gate (17 bytes) 0 0 53h: object record code 1 1 3Dh: timing gate sub-code 2 2 gate width in m 4 2 gate height in m 6 1 front colour (code in both nibbles) 7 1 back colour (code in both nibbles) 8 2 always 0 ?? 10 1 gate number from 0 onward; last gate number has msb set 11 2 ?? 13 2 ?? 15 2 ?? Note: the last 3 field values vary from gate to gate of the same amounts of which E coord., alt. and N coord. vary; they are perhaps connected with the distance from gate to gate. ==================== BUILDINGS All real buildings share the same structure (poles, bridges, trees, autos, fuel boxes and thermal generators depart somewhat from this structure): ù an area record ù a delayed call (0Eh) calling the actually drawing routine ù a jump record (0Bh) skipping over the entire object ù a 2-byte embedded code related to building type and detailed below ; drawing routine: ù a reference point record ù an orientation record calling a tilt-drawing sub-routine ù a RET (19h) returning from the delayed call ; titl-drawing sub-routine: ù a 53h variable record depending on the object ù a RET (19h) returning from the orientation call. Towers, wind socks and trees lack a separated tilt-drawing sub-routine and have the following structure: ù an area record ù a delayed call (0Eh) calling the actually drawing routine ù a jump record (0Bh) skipping over the drawing routine ù a 2-byte embedded code related to building type and detailed below ; drawing routine: ù a reference point record ù a 53h variable record depending on the object ù a RET (19h) returning from the orientation call. For buildings, the 53h record contains: ù the record code 53h in the 1st byte ù a sub-code related to the building type in byte 1 ù a series of 2-bytes fields defining wall distances from ref. point (first horizontal positions from left [negative] to right [positive], then verti- cal positions from top [positive] to bottom [negative]) ù a 2-bytes field with base height ù a single byte field with peak height (0 for flat roofs) ù a series of single byte fields with wall colours and roof pitches colours (just one if the roof is flat). All distances are in meters, and colour codes are repeated in both nibbles. In the following sketches, for each kind of building, code and sub-code of 53h record as well as the build. type in the enbedded code are given; numbers and letters show the order in which wall positions and colour codes respec- tively appear within the 53h record. Rectangular building (53h 01h) flat roof (type 0003h) peaked roof (type 0005h) 1 2 1 2 ³ a ³ ³ a ³ ÚÄÄÄÄÄÄÄÄÄÄÄ¿Ä 3 ÚÄÄÄÄÄÄÄÄÄÄÄ¿Ä 3 ³ ³ ³ f ³ d ³ e ³ b d ÃÄÄÄÄÄÄÄÄÄÄÄ´ b ³ ³ ³ g ³ ÀÄÄÄÄÄÄÄÄÄÄÄÙÄ 4 ÀÄÄÄÄÄÄÄÄÄÄÄÙÄ 4 c c L building (53h 02h) flat roof (type 0007h) peaked roof (type 0009h) 1 2 3 1 2 3 ³ a ³ ³ ³ a ³ ³ ÚÄÄÄÄÄÄÄ¿ Ä 4 ÚÄÄÄÂÄÄÄ¿ Ä 4 ³ ³b ³ ³ ³ b ³ ³ c ³ ³ h ³ c ³ ÀÄÄÄÄÄÄ¿Ä 5 ³ g ³ /ÀÄÄÄÄÄÄ¿Ä 5 f ³ g ³ f ³ ³/ i ³ ³ ³ d ³ /ÀÄÄÄÄÄÄÄÄÄÄ´ d ³ ³ ³/ l ³ ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙÄ 6 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙÄ 6 e e Reversed L building (53h 06h) flat roof (type 000Bh) peaked roof (type 000Dh) 1 2 3 1 2 3 ³ ³ c ³ ³ ³ c ³ ÚÄÄÄÄÄÄ¿Ä 4 ÚÄÄÄÂÄÄÄ¿Ä 4 b ³ ³ b ³ ³ ³ a ³ ³ a ³ h ³ ³ ÚÄÄÄÄÄÄÄÙ ³Ä 5 ÚÄÄÄÄÄÄÄÙ\ ³ g ³Ä 5 ³ g ³ d ³ i \³ ³ d f ³ ³ f ÃÄÄÄÄÄÄÄÄÄÄÄÙ\ ³ ³ ³ ³ j \³ ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙÄ 6 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙÄ 6 e e T building (53h 03h) flat roof (type 000Fh) peaked roof (type 0011h) 1 2 3 4 1 2 3 4 ³ ³ a ³ ³ ³ ³ a ³ ³ ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿Ä 5 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿Ä 5 ³ ³ ³ i ³ h ³ ³ b h ÃÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄ´ b ³ i ³ ³ j /³\ m ³ ÀÄÄÄÄÄÄÄ¿ ÚÄÄÄÄÄÄÄÙÄ 6 ÀÄÄÄÄÄÄÄ¿/ ³ \ÚÄÄÄÄÄÄÄÙÄ 6 g ³ ³ c g ³ ³ ³ c f ³ ³ d f ³ k ³ l ³ d ³ ³ ³ ³ ³ ÀÄÄÄÄÄÄÄÙ Ä 7 ÀÄÄÄÁÄÄÄÙ Ä 7 e e U building (53h 04h) flat roof (type 0013h) peaked roof (type 0015h) 1 2 3 4 1 2 3 4 ³ a ³ ³ e ³ ³ a ³ ³ e ³ ÚÄÄÄÄÄÄÄ¿ ÚÄÄÄÄÄÄÄ¿Ä 5 ÚÄÄÄÂÄÄÄ¿ ÚÄÄÄÂÄÄÄ¿Ä 5 ³ ³b d³ ³ ³ ³ ³b d³ ³ ³ ³ ³ c ³ ³ ³ ³ j ³ c ³ m ³ ³ h ³ ÀÄÄÄÄÄÄÄÙ ³Ä 6 h ³ i ³ /ÀÄÄÄÄÄÄÄÙ\ ³ n ³Ä 6 ³ ³ f ³ ³/ k \³ ³ f ³ i ³ ³ /ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ\ ³ ³ ³ ³/ l \³ ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙÄ 7 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙÄ 7 g g H building (53h 05h) flat roof (type 0017h) peaked roof (type 0019h) 1 2 3 4 1 2 3 4 ³ a ³ ³ e ³ ³ a ³ ³ e ³ ÚÄÄÄÄÄÄÄ¿ ÚÄÄÄÄÄÄÄ¿Ä 5 ÚÄÄÄÂÄÄÄ¿ ÚÄÄÄÂÄÄÄ¿Ä 5 ³ ³b d³ ³ ³ ³ ³b d³ ³ ³ ³ ³ c ³ ³ ³ ³ n ³ c ³ r ³ ³ ³ ÀÄÄÄÄÄÄÄÙ ³Ä 6 ³ ³ /ÀÄÄÄÄÄÄÄÙ\ ³ ³Ä 6 ³ ³ ³ ³/ p \³ ³ l ³ m ³ f l ³ m ÃÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ´ t ³ f ³ ³ ³ ³\ q /³ ³ ³ ÚÄÄÄÄÄÄÄ¿ ³Ä 7 ³ ³ \ÚÄÄÄÄÄÄÄ¿/ ³ ³Ä 7 ³ ³ i ³ ³ ³ ³ o ³ i ³ s ³ ³ ³ ³j h³ ³ ³ ³ ³j h³ ³ ³ ÀÄÄÄÄÄÄÄÙ ÀÄÄÄÄÄÄÄÙÄ 8 ÀÄÄÄÁÄÄÄÙ ÀÄÄÄÁÄÄÄÙÄ 8 k g k g Example of a peaked L building: 3E 0045 0391 048C 0003 Area record 8E 0008 Call the drawing routine 0B 0039 Jump over the entire object 0009 Embedded code: object type is 9 ; the drawing routine: 24 04 048C0A00 00000000 03918700 Ref. point record (center of the object) 16 0000 0000 FC6E 000A Orient. record: 0ø pitch, 0ø bank, [FC6E =] -914 / 182.04 = -5.02ø; call the tilt-drawing sub-routine 19 RET from delayed call ; the tilt-drawing sub-routine: 53 02 L building record FFF6 FFFF 000A Ascisses of walls are -10, -1, 10 0007 0001 FFF9 Ordinates of walls are 7, 1, -7 0004 02 base heigh is 4 m, peak height is 2 m 66 88 99 66 88 99 wall colours are L.Blue, Brown, Yellow, L.Blue, Brown, Yellow 55 AA 55 AA roof colours are L.Grey, D.Grey, L.Grey, D.Grey 19 RET from orientation record call Multi-sided building (53h 4Ch) flat roof (type 001Bh) and peaked roof (type 001D) have the same contents: 0 1 53h: record code 1 1 4Ch: record sub-code 2 1 number of sides 3 2 length in m 5 2 width in m 7 2 height in m 9 2 two alternating colours for sides 11 2 two alternating colours for roof pitches 12 1 peak height in m Control tower (type 001Fh; codes 53h 07h) 0 1 53h: record code 1 1 07h: record sub-code 2 8 four wall positions as for rectangular buildings 10 2 base height 12 2 always 0Ah ?? (irrelevant) 14 4 four side colours as for rectangular buildings 18 1 roof colour 19 1 always 00h ?? (irrelevant) Bridge (type 0025h; codes 53h 34h): 0 1 53h: record code 1 1 34h: record sub-code 2 2 length 4 2 width 6 1 suspension colour (0 for non-suspended bridge) 7 1 bridge colour 8 2 suspension height The following 4 object types lack the orientation record: Tower (type 0020h; codes 53h 29h) and wind sock (type 0022h; codes 53h 2Eh) have the same structure: 0 1 53h: record code 1 2 29h / 2Eh: record sub-code 2 1 always 0 ?? (irrelevant) 3 2 height Coniferous (type 0028h; codes 53h 42h) and deciduous tree (type 002Bh; codes 53h 43h) have the same structure: 0 1 53h: record code 1 1 42h / 43h: record sub-code 2 1 total height 3 1 width 4 1 trunk height 5 1 leave colour 6 1 trunk colour Suspended bridges (type 0027h; codes 53h 33h) and autos (type 002Dh; codes 53h 47h) add a 28h 36h record right before the 53h record. Suspended bridges have the same 53h record as standard bridges (of course, sub-code is 33h instead of 34h). Autos have a 3-byte 53h record containing, after code and sub-code, only a byte with the auto colour. -------------------- Fuel box (type 002Fh). Fuel box descriptions are complex, but the great part is fixed because fuel boxes have a fixed size and are always oriented toward the North. Below a template is given: 3E 0076 xxxx xxxx 0007 Area record (coords may vary, length [118 bytes] and radius [7 FSu=ca 1 NM] are constant) 8E 0008 Delayed call to the actually drawing routine 0B 006A Jump over 106 bytes skipping the entire object 002F Embedded code: object type 2Fh ; the drawing routine: 24 02 xxxxxxxx xxxxxxxx xxxxxxxx Ref. point record (coords and alt. may vary); note the reduced scale factor (02) 16 0000 0000 0000 000A Orientation is always flat and North; call the tilt-drawing sub-routine 19 RET from delayed call ; the tilt-drawing sub-routine: 28 36 004C 034E FFFF Jump over 004Ch bytes (to the end of the sub- routine) if var 034E tests in some way against value -1 12 99 yellow line 40 FF80 FF44 the "F", described with normal lines: 41 FF80 0098 leg 41 0080 0098 upper arm 40 007A FFF4 jump to 41 FF80 FFF4 lower arm 40 FEFB FEFB the box: 41 00F9 FEFB lower side 41 00F9 0101 right side 41 FEFB 0101 upper side 29 close the box 21 0014 Skip 20 bytes (to rec 19h) if: 029C FEFB 00FF var 029Ch (delta E) outside -260 - 255 02A0 FEFB 0101 var 02A0h (delta N) outside -260 - 257 25 0288 0001 Set var 0288 to 1 19 RET from orientation record call -------------------- Thermal generator (type 0031h) Thermal generators also have a very special description including some gen- eral records. Again, a template is given. 3E 006A xxxx xxxx xxxx Area record (106 bytes long, coords may vary, as well as radius, which depend on size) 8E 0008 Delayed call to drawing routine 0B 005E Jump over 94 bytes skipping the entire object 0031 Embedded code: object type is 0031 ; the drawing routine: 24 04 xxxxxxxx xxxxxxxx xxxxxxxx Ref. point record 16 xxxx xxxx xxxx 000A Orientation record; call tilt-dr. sub-routine 19 RET from delayed call ; tilt-drawing sub-routine: 25 02E2 xxxx Surface colour record 2F Polygon begin 40 xxxx xxxx generator area as a polygon 41 xxxx xxxx 41 xxxx xxxx 41 xxxx xxxx 29 close area and fill 4D 0025 a 4Dh record, 0025h bytes long, follow: xxxxxxxx E coord of generator center ???????? ??? (4 bytes) xxxxxxxx N coord of generator center xxxx orientation ?? ??? (1 byte) xxxx generator width (in m) ???? ??? (2 bytes) xxxx thermal effect height (in feet) ???? ??? (2 bytes) xxxx generator length ?????????????????? ??? (9 bytes) 19 RET from orientation record call ====================================================================== NOTE ON .SC0 and .ELE SEE04 DATA FILES .SC0 FILES .SC0 files begin with a word containg the length of the following SDL code. The SDL code actually used to draw the object follows; it basically follows .SC1 structures, but may include more records to achieve the special SEE effects. It always starts with a 3Eh record, but its coordinates are zeroed, because the actual object coordinates are supposed to be filled in by SEE itself when the object is inserted in an SC1. After the SDL code, a table of SEE control codes is appended After the table, an ASCII text portion describing the object and its intended usage may appear. SEE CONTROL CODES (by John Blackie) The codes are needed to allow SEE to place an object at a desired location and orientation. To do this a series of 3 byte codes are used following the object information. The control sequence is terminated by FF FF FF. Control codes are 3 bytes long and have the structure: xx yy yy dump contents of SEE Register xx to file offset yyyy. The following table summarises the characteristics of each of the known SEE Registers. REGISTER LENGTH USE Hex Dec Bytes 01 1 1 Custom 02 2 1 Custom 03 3 1 Custom 04 4 1 Custom (Night colour) 05 5 1 Custom (Dusk colour) 06 6 1 Custom (Day colour) 07 8 1 Custom 09 9 1 Custom 0A 10 1 Custom 0B 11 1 Custom 0C 12 1 Custom 41 65 4 ALTITUDE 45 69 4 NORTH (long) 49 73 1 Control Code (substitution??) 4E 78 4 EAST (long) 54 84 32 TEXT (for signs) 62 98 2 BANK 65 101 2 EAST (short) 68 104 2 HEADING 6E 110 2 NORTH (short) 70 112 2 PITCH 72 114 1 RANGE 73 115 2 SCALE 78 120 2 Delta East 79 121 2 Delta North 7A 122 2 Delta Altitude (HEIGHT) Many of the above SEE variables are Custom variables which can be used as 1 byte register to dump any user specified information. Uninitialized Custom variables have a default 0 value and can be used to extend 1-byte registers into 2-byte file words. SEE code 49H appears to set one variable equal to another. The sequence 49 41 7A is often used and appears to transfer the contents of the ALTITUDE variable 41 into the Delta Altitude variable 7A. Variable 41 is zeroed after the operation. This command appears to keep the object with a zero altitude ground reference. The object is raised by Delta Altitude. SEE can make either polygon or line .sc0s, each of which is limited to one object. The default object position/orientation and control codes are con- tained in two binary files in SEE. The standard control codes are found in P_STD.SEE (for polygons) and L_STD.SEE for lines. The only difference between these two files is the presence of the orientation control record for the polygons. Both these files are decodable using FSDECODE. SEE only creates .sc0s from a line or a poly, other kinds of objects were hand coded. Perhaps SEE will be later updated to allow any object to be con- verted to .sc0 format. For more complex .sc0s requiring more than one line or poly, use Aircraft and Adventure factory. Be careful, however, as the scale setting of 2 used for these files only allows the objects to be viewed up to 8 FS units. If you set the range higher than this, the object will "repeat". The solution is to make the object to 1/4 or 1/16 scale and then use the X4 or X16 command on the .sc0 file in SEE to return it to full size. The inbuilt range of the object will then be extended to 32 or 128 FS units. .ELE FILES .ELE files contain just the SDL portion of .SC0 files. ====================================================================== DYNAMIC SCENERIES (.DY1) GENERAL STRUCTURE Dynamic scenery files are made of: ù a header containing various pointers ù a pattern definition section containing the definitions of all the patterns in the file ù a pattern code section containing the actual description of the patterns. ==================== HEADER STRUCTURE; length: 43 bytes 0 2 file length 2 2 0002h (a kind of signature?) 4 2 000Ch (= 12; pointer to scenery name) 6 2 002Bh (= 43; header length) 8 2 number to be assigned to the next pattern that will be defined 10 2 pointer to pattern code section 12 31 scenery names: up to 30 characters (padded with space, if shorter) plus a 0 ending byte ==================== PATTERN DEFINITION SECTION The pattern definition section contains a 48-byte block for each pattern of the scenery. 0 2 pattern number (see note) 2 2 model: 0065h Cessna R182 0066h Boeing 747 0067h Gates Learjet 0068h F14 0069h Schweizer SGS 012Dh Fuel truck 0137h Red car 0138h Blue car 0139h White car 0191h Sail boat Any other model code is rendered by ASD as a Cessna R182. 4 2 pointer to the corresponding pattern code 6 2 length of the corresponding pattern code 8 2 number of the pattern after which this pattern will start, zero if patter starts immediately 10 1 begin code: 0 immediately 1 after other pattern starts 2 after other pattern takes off 3 after other pattern lands 4 after other pattern parks 11 1 status code: 0 - inactive, 1 - active 12 1 end action code: 0 start over 1 park 2 disappear 13 1 display before start: 0 - yes, 1 - no (sic!!) 14 4 ??? (irrelevant) 18 30 pattern name, padded with spaces, no ending zero Note: to each new pattern is assigned the number contained at byte 8 of file header which is then increased; when a pattern is deleted, its record is removed and other patterns are shifted but its number is not made available, nor other pattern numbers are modified to fill a possible gap, as a con- sequence patterns can have numbers greater than the total number of patterns present in the file. ==================== PATTERN CODE SECTION This section contains all the definitions of the scenery patterns, one after the other. Pattern definitions are made of 5 kinds of records: 00h Initial record 20 bytes FFh Position record 21 bytes 02h Look record 5 bytes 06h Take off/Land record 2 bytes 04h End of pattern record 1 byte -- 00h ------------- Initial record (20 bytes) Used to set the initial position of the object at the beginning of the pat- tern. 1 4 E coord (fract. FSu; all 4 bytes used) 5 4 alt. AGL (fract. FSu; all 4 bytes used) 9 4 N coord (fract. FSu; all 4 bytes used) 13 2 pitch (noze down is positive, noze up is negative) 15 2 bank (left is positive, right is negative) 17 2 heading 19 1 always 03 ?? Note: Pitch variation is somewhat special: if the object rotates more than 90ø up or down, it is reversed up side down and pitch sign is changed! -- 02h ------------- Look record (5 bytes) Look record defines some visual detail of the object. To my knowledge, a look record may have 3 sub-codes, related to 3 visual aspect; patterns always begin defining the initial values of these aspects with 3 look records, one for each sub-code. 1 2 FFFEh: shadow is visible or not FFFDh: object is flying or landed FFFBh: gear is lowered or not 3 2 value: for FFFEh: 1 = shadow on, 0 = shadow off for FFFDh: 2 = landed, 0 = flying for FFFBh: 4 = gear down, any other value = up Notes: Shadow is switched off by ASD when the object raises above ca. 100 m from ground level. Sub-code FFFDh probably triggers patterns starting after another pattern's landing or taking off. -- 04h ------------- End of pattern (1 byte) End of pattern record Used to mark the end of a pattern. It is made of the single byte 04h. -- 06h ------------- Teake off/land record (2 bytes) A take off (land) record is inserted after the movement that caused the model to rise over (to sink at) the ground level. Each of them is always followed by the corresponding 02h FFFDh record. 1 1 02h: take off (always followed by a 02 FFFD 0000 record) 03h: landing (always followed by a 02 FFFD 0002 record) -- FFh ------------- Position record (21 bytes) Position record is identical to initial record, excepted the record code and the last field. It is used through the entire pattern description to mark successive positions and orientations of the object. 1 4 E coord (fract. FSu) 5 4 alt. AGL (fract. FSu) 9 4 N coord (fract. FSu) 13 2 pitch (noze down is positive, noze up is negative) 15 2 bank (left is positive, right is negative) 17 2 direction 19 2 time between the previous (or initial) position and this one Note: The time interval between positions is apparently measured in ticks, 1 tick every 0.008 sec (or 126 ticks per sec). Time intervals are not constant but shorter when the position (or orientation) variation is greater and longer when it is smaller. It seems never to exceed ca 1500 ticks (12 sec). About other fields, the same observations made for the initial record apply. ==================== Patterns usually begin with: record 02 FFFE to define initial conditions record 02 FFFB " record 02 FFFD " record 00 to define initial point and orientation Then enough FFh records follow to define successive positions and orienta- tions of the object. Change in visual aspects and flying condition are marked by appropriate records. The pattern is closed by the record 04 ======================================== DEMO FILES (.DEM) Demo files, like dynamic sceneries, have a relatively simple structure and record set. Basically, demo files describe successive positions (and orienta- tions) of the aircraft with a flow of position records; these records, however, are intermixed with single byte codes that correspond to the keys pressed by the user during demo recording. Contrarily to dynamic sceneries, aircraft position is sampled at a fixed rate (either 1 or 5 sec) and all the codes for keys pressed between two samples are grouped and inserted between the two corresponding position records. KEY CODES Key codes correspond, in almost all cases, to the hardware press scan codes generated by the keyboard and are, therefore, less than 80h. Some kind of tanslation is, however, carried out by the demo recorder: ù on all keyboards, some key codes are ignored and some other are converted to 00h ù on 101-key keyboards, function keys are converted to their functional equi- valent of the 83-key keyboard and the corresponding scan code is used ù some keys of the numeric pad have the same function in the 101-key keyboard (like Gray /, Gray * and ScrollLock, or Gray + and Gray Enter) and their scan code are merged ù scan code prefixes used by 101-key keyboards to differentiate among dupli- cated keys (left and right Alt and Ctrl, white and gray cursor keys...) are thrown away. ù release scan code are ignored. Excepted for a few special keys (like Shift, Ctrl and Alt), all key presses are recorded, even if they do nothing. Key presses are executed as soon as they are met during demo play back: they affect the instrument panel, the display and outer world simulation in the same way as during normal flight; apparently, however they do not affect flight simulation which is based on the position records. Subsequent position records are interpolated to simulate a continuous flight. The following table lists all the key codes generated by the demo recorder with their corresponding key; function key codes have two corresponding keys, the first is for 83-key keyboards, the second for 101-key keyboards. All codes are in hex. Alphanumeric keys 01 Esc 0F Tab [1D ù] [2A ù] [38 ù] 02 '1' 10 'Q' 1E 'A' [2B ù] 39 Space 03 '2' 11 'W' 1F 'S' 2C 'Z' 3A CapsLk 04 '3' 12 'E' 20 'D' 2D 'X' 05 '4' 13 'R' 21 'F' 2E 'C' 06 '5' 14 'T' 22 'G' 2F 'V' 07 '6' 15 'Y' 23 'H' 30 'B' 08 '7' 16 'U' 24 'J' 31 'N' 09 '8' 17 'I' 25 'K' 32 'M' 0A '9' 18 'O' 26 'L' 33 ',' 0B '0' 19 'P' 27 ';' 34 '.' 0C '-' 1A '[' 28 ''' 35 '/' 0D '+' 1B ']' 29 '`' [36 ù] 0E BkSp 1C Enter 37 '*'-PrtSc Function keys Numeric pad keys 3B F1/F5 3C F2/F4 45 NumLk 46 Gr /|*|ScrollLk 3D F3/F6 3E F4/F3 47 Home 48 Up 49 PgUp 4A Gr - 3F F5/ùù 40 F6/ùù 4B Left 4C Pad 5 4D Right 4E Gr +|<ÄÙ 41 F7/F7 42 F8/F2 4F End 50 Down 51 PgDn 43 F9/F8 44 F10/F1 52 Ins 53 Del 56 '<'ùùù Notes: ù Scan codes 1D, 2A, 2B, 36, 38 would correspond to Ctrl, Left Shift, '\', Right Shift, Alt respectively; but within demos, Shift and '\' keys do not generate any code, while Ctrl and Alt keys generate a 00 code. ùù No F key of 101-key keyboard correspond to F5 and F6 of 83-key keyboard: therefore those codes are never recorded with a 101-key keyboard ùùù Code 56 is generated (and recorded) only with 102-key European keyboards. RECORDS All records have a code >= 80h and are therefore easily differentiated from key codes. Only 8 kinds of records have been recognized and are listed below. The first four of them are actually found in demo files generated by the demo recorder; the other four have been found in the demo supplied with the program (the default demo as well as the instructor flights of the flight school and the lead plane flights of the formation entertainement which are all regular demo files), but are correctly played back if manually inserted in a recorded demo. A recorded demo has a very simple structure: it is made of sample rate records (either 80h or 81h) followed by long position records; between a position record and the next sample rate record, the codes for key pressed by the user are inserted. The file is not divided in sections (like, for instance, scenery files) nor its end is marked in any way. -- 80h ------------- 1 sec (1 byte) This single byte record marks a sample rate of 1 sec and is usually followed by a long position record. -- 81h ------------- 5 sec (1 byte) This single byte record marks a sample rate of 5 sec and is usually followed by a long position record. -- 82h ------------- Long position record (19 bytes) 1 4 E coord. (fract. FSu) 5 4 Alt. AGL (fract. FSu) 9 4 N coord. (fract. FSu) 13 2 pitch (noze down is positive, noze up is negative) 15 2 bank (left is positive, right is negative) 17 2 heading This record is usually preceded by a 1 sec or a 5 sec record. --84h -------------- Message (mess.length+2 bytes) 1 xx Message text 1+xx 1 00h ==================== Supplied demos contain four more kinds of record, allowing for adding a major feature (mode record) and for saving some bytes. They usually begin with a mode record which sets the initial conditions; a 1 sec position record follows giving the aircraft initial position, then a flow of short position records describes subsequent aircraft positions. As usual, key codes are inserted among position records to interact with the simulator. -- 8Ah ------------- Mode record (528 bytes) 1 526 Mode 527 1 8Bh: end of mode This record embeds a full mode, with exactly the same structure of a .MOD mode file; this allows specifying all the display, environment and flight conditions within a demo. Mode records are usually inserted at the beginnig of a demo to prepare the field; other mode records can however appear any- where in a .DEM to change simulation parameters. -- 90h ------------- 1 sec/position (19 bytes) 1 4 E coord. (fract. FSu) 5 4 Alt. AGL (fract. FSu) 9 4 N coord. (fract. FSu) 13 2 pitch (noze down is positive, noze up is negative) 15 2 bank (left is positive, right is negative) 17 2 heading This record has the same structure of the 82h record, but contains also a 1 sec sample rate information. -- 91h ------------- 5 sec/position (19 bytes) 1 4 E coord. (fract. FSu) 5 4 Alt. AGL (fract. FSu) 9 4 N coord. (fract. FSu) 13 2 pitch (noze down is positive, noze up is negative) 15 2 bank (left is positive, right is negative) 17 2 heading This record has the same structure of the 82h record, but contains also a 5 sec sample rate information. -- 94h ------------- Short position record (7 bytes) This record describes the variations of the 6 position parameters relatives to a previous position record (either a 90h record or another 94h record). It can be used also after an 82h record, even if MS demos never do so. The record includes also 1 sec of sample rate. 1 1 E coord. delta 2 1 Alt. delta 3 1 N coord. delta 4 1 Pitch delta 5 1 Bank delta 6 1 Heading delta Linear parameters are in m, angular parameters in 1.4ø (= 360ø / 256); all 6 parameters are signed: the max linear delta is therefore 127 m, and the max angular delta is 180ø. Short position records save 12 bytes each over long position records. Apparently, there is no short position record for 5 sec interval. ====================================================================== MODE FILES (.MOD) Mode files still have many obcure points, but almost all the parameters the can be set from FS menu are decoded. Exceptions are mouse sensitivity para- meters, because I do not use a mouse with FS (it seems to me like driving a car with the foots), and joystick parameters because I do not have one (I am a serious person, I don't play games!). There are several undecoded 1-byte fields; they are probably unused and maybe are only the MSBytes of word fields which never exceed an 8-bit value. Screen coordinates (for window positions) are apparently device-independent (I tried on a VGA and a Hercules): ascissae span from 0032h to 1FD6h and ordinates from 0032h to 17D4h; origin is in the upper left corner. The following listing follows the same format used above, but, given the length of the mode "record", a column with hex offset has been added. Key labels (as ) refer to the 101-key keyboard. 0 0000 2 020Eh: file length 2 0002 2 0017h: pointer to mode name 4 0004 1 01h: mode file signature 5 0005 4 Initial E coord. (fract. FSu) 9 0009 4 Initial AGL alt. (fract. FSu) 13 000D 4 Initial N coord. (fract. FSu) 17 0011 2 Initial pitch 19 0013 2 Initial bank 21 0015 2 Initial heading 23 0017 31 Mode name (padded with spaces and 0-terminated) FIRST 3D WINDOW 54 0036 2 Left border position 56 0038 2 Top border position 58 003A 2 Width 60 003C 2 Height 62 003E 1 View: 00h Cockpit 01h Tower 02h Track 03h Spot plane 63 003F 1 Cockpit view direction: counterclockwise 00h front -> 07h front left 64 0040 2 Cockpit view zoom: 0010h .16 x 0020h .33 x 0040h 1 x 0081h 2 x 0103h 4 x 0207h 8 x 040Fh 16 x 081Fh 32 x 103Fh 64 x 207Fh 129 x 40FFh 256 x 7FFFh 511 x 66 0042 2 Tower view zoom (as above) 68 0044 2 Track view zoom (as above) 70 0046 2 Spot plane view zoom (as above) 72 0048 1 73 0049 1 Spot view direction: counterclockwise 00h front -> E0h front left (01h = 1.4ø) 74 004A 2 Spot plane distance (in 1/256 m) 76 004C 2 78 004E 1 Spot plane preference: 00h roll - 01h loop 79 004F 1 Spot plane transition: 00h slow - 01h fast 80 0050 2 Spot plane altitude (in 1/256 m) 82 0052 28 ?? (these bytes change when the cockpit view direction changes, but without any clear pattern) SECOND 3D WINDOW 110 006E 2 Left border position 112 0070 2 Top border position 114 0072 2 Width 116 0074 2 Height 118 0076 1 View: 00h Cockpit 01h Tower 02h Track 03h Spot plane 119 0077 1 Cockpit view direction: counterclockwise 00h front -> 07h front left 120 0078 2 Cockpit view zoom (see byte 64) 122 007A 2 Tower view zoom (as above) 124 007C 2 Track view zoom (as above) 126 007E 2 Spot plane view zoon (as above) 128 0080 1 129 0081 1 Spot view direction: counterclockwise 00h front -> E0h front left (01h = 1.4ø) 130 0082 2 Spot plane distance (in 1/256 m) 132 0084 2 134 0086 1 Spot plane preference: 00h roll - 01h loop 135 0087 1 Spot plane transition: 00h slow - 01h fast 136 0088 2 Spot plane altitude (in 1/256 m) 138 008A 28 ?? (these bytes change when the cockpit view direction changes, but without any clear pattern) 166 00A6 2 Map window left border position 168 00A8 2 Map window top border position 170 00AA 2 Map window width 172 00AC 2 Map window height 174 00AE 1 Current window: 00h first 3D 01h second 3D 02h map 175 00AF 1 First 3D: 00h off - 01h on 176 00B0 1 Second 3D: 00h off - 01h on 177 00B1 1 Map: 00h off - 01h on 178 00B2 1 Position indic.: 00h off - 01h on 179 00B3 1 Instr. panel: 00h off - 01h on 180 00B4 2 Full external view: 00h off - 01h on 182 00B6 2 Titles on windows: 00h off - 01h on 184 00B8 2 Shader: 00h off - 01h on 186 00BA 2 Stars: 00h off - 01h on 188 00BC 1 Ground text.: 00h off, 01h dots, 02h small rect, 03h big rect 189 00BD 1 Crash: 00h off, 01h detect, 02h detect and analyse 190 00BE 1 Sound: 00h off - 01h on 191 00BF 1 Pause: 00h off - 01h on 192 00C0 1 Realism, bits (realism scale is at offset 299): 0 engine 1 elevator trim 2 gyro drift 3 light burn 4 fast throttle 5 instrument lights 6 barometer drift 7 [unused] 193 00C1 1 Axis indicator: 00h none 01h V-shaped 02h 4-dots 03h small V 194 00C2 2 Auto coordination: 00h off - 01h on 196 00C4 2 Smoke system: 00h off - 01h on 198 00C6 2 ATC comm: 00h off - 01h 0n 200 00C8 1 Slew: 00h off - 01h on 201 00C9 3 ?? 204 00CB 2 Rotat. slew: negative = right, positive = left (+- 80h each or ) 206 00CE 1 207 00CF 1 Altit. slew: 00h max up -> 40h stable -> 7Fh max down (+- 02h each or , -> 7Fh, -> 00h) 208 00D0 1 209 00D1 1 Longit. slew: negative = forward, positive = rear (+-01h each or ) 210 00D2 1 211 00D3 1 Side slew: negative = left, positive = right (+-01h each or ) 212 00D4 2 ?? 214 00D6 1 EFIS/CFPD: 00h off - 01h on (equal to byte 394) 215 00D7 3 ?? 218 00DA 3 Hours, min and sec as hex numbers 221 00DD 12 ?? Instrument panel display (instr. displayed when bit set): 233 00E9 1 bits: 0 airspeed 1 turn coordination 2 gyro heading 3 altimeter 4 attitude 5 VOR 1 6 tacheometer 7 vertical velocity 234 00EA 1 bits: 0 time 1 transponder 2 NAV 1 3 COM 4 compass 5 fuel 6 oil 7 AUX 2 235 00EB 1 bits: 0 gear and carb heat 1 NAV 2 2 DME 3 VOR 2 4 ADF 5 AUX 1 6 AUX 4 7 AUX 3 236 00EC 5 ?? WINDS 241 00F1 1 Layer 3 speed (in kt) 242 00F2 1 Layer 3 turbulence: 00h -> 0Ah 243 00F3 2 Layer 3 direction (in 1/182.04ø) 245 00F5 1 Layer 2 speed (in kt) 246 00F6 1 Layer 2 turbulence: 00h -> 0Ah 247 00F7 2 Layer 2 direction (in 1/182.04ø) 249 00F9 1 Layer 1 speed (in kt) 250 00FA 1 Layer 1 turbulence: 00h -> 0Ah 251 00FB 2 Layer 1 direction (in 1/182.04ø) 253 00FD 1 Surface speed (in kt) 254 00FE 1 Surface turbulence: 00h -> 0Ah 255 00FF 2 Surface direction (in 1/182.04ø) 257 0101 2 Layer 3 tops (in m) 259 0103 2 Layer 3 base (in m) 261 0105 2 Layer 2 tops (in m) 263 0107 2 Layer 2 base (in m) 265 0109 2 Layer 1 tops (in m) 267 010B 2 Layer 1 base (in m) 269 010D 2 Surface depth (in m) CLOUDS 271 010F 2 Top layer tops (in m) 273 0111 2 Top layer base (in m) 275 0113 2 Top layer coverage: 00h clear -> 08h overcast 277 0115 2 Top layer deviation (in m) 279 0117 2 Bottom layer tops (in m) 281 0119 2 Bottom layer base (in m) 283 011B 2 Bottom layer coverage: 00h clear -> 08h overcast 285 001D 2 Bottom layer deviation (in m) 287 011F 2 Thunderstorm tops (in m) 289 0121 2 Thunderstorm base (in m) 291 0123 2 Thunderstorm coverage: 00h widely scatt. -> 02h dense 293 0125 2 Thunderstorm speed (in 1/2 kt) 295 0127 2 Thunderstorm direction (in 1/182.04ø) 297 0129 1 Reliability: 00h -> 64h 298 012A 1 299 012B 1 Realism: 00h -> 64h 300 012C 1 301 012D 26 ?? this portion contains mouse and joystick parameters 327 0147 1 Keyboard aileron sensibility: 01h = 1 -> 7Fh = 8 328 0148 1 329 0149 1 Keyboard elevator sensibility: 01h = 1 -> 7Fh = 8 330 014A 1 331 014B 1 Keyboard rudder sensibility: 01h = 1 -> 7Fh = 8 332 014C 3 ?? 335 014F 2 Instrumental panel top border 337 0151 2 ?? 339 0153 1 Season: 00h winter -> 03h autumn 341 0155 6 COM freq as ASCII string of the form "120;30" 347 015B 1 always 0 ?? 348 015C 1 NAV1 active: 00h off - 01h on 349 015D 6 NAV1 freq as ASCII string of the form "120;30" 355 0163 1 always 0 ?? 356 0164 1 NAV2 active: 00h off - 01h on 357 0165 6 NAV2 freq as ASCII string of the form "120;30" 363 016B 3 OBI1 inbound course as ASCII string of the form "120" 366 016E 1 always 0 ?? 367 016F 1 VOR1 active: 00h off - 01h on 368 0170 3 OBI1 outbound course as ASCII string of the form "120" 371 0173 1 always 0 ?? 372 0174 1 VOR2 active: 00h off - 01h on 373 0175 3 OBI2 inbound course as ASCII string of the form "120" 376 0178 1 always 0 ?? 377 0179 1 VOR2 active: 00h off - 01h on 378 017A 3 OBI2 outbound course as ASCII string of the form "120" 381 017D 1 always 0 ?? 382 017E 1 Transponder active: 00h off - 01h on 383 017F 4 Transponder freq as ASCII string of the form "1200" 387 0183 1 always 0 ?? 388 0184 1 ADF active: 00h off - 01h on 389 0185 3 ADF freq as ASCII string of the form "120" EFIS/CFPD 392 0188 2 00h none 01h lock to ILS for landing approach 02h lock to navaid and alt. tracking 394 018A 2 00h off - 01h on (equal to byte 214) 396 018C 2 type: 00h rect, 01h bricks, 02h poles 398 018E 2 density: 00h thick, 01h medium, 02h thin 400 0190 2 range: 00h short, 01h medium, 02h long 402 0192 2 navaid: 00h NAV1, 01h NAV2 404 0194 2 tracking altitude (in m) 406 0196 66 ???? (this portion apparently contains, among other things, the dynamic parameters (velocity vector, angular velocities...), but no clear relation has emerged) 472 01D8 1 Elevator 'carry': 01h when full pushed, FFh when full pulled, 00h otherwise 473 01D9 1 Elevator: C0h full pushed -> 3F full pulled; +-01h each or 474 01DA 1 Aileron 'carry': 01h when at full left, FFh when at full right, 00h otherwise 475 01DB 1 Ailerons: C0h full left -> 3Fh full right; +- 04h each or 476 01DC 1 Rudder 'carry': 01h when at full left, FFh when at full right, 00h otherwise 477 01DD 1 Rudder: C0h full left -> 3Fh full right; +- 04h each or 478 01DE 1 Throttle 'carry': FFh when full, 00h otherwise 479 01DF 1 Throttle: 00h cut -> 3Fh full; +-02h each or 480 01E0 1 Trim 'carry': 01h when full down, FFh when full up, 00h otherwise 481 01E1 1 Trim: C0h full down -> 3F full up; +-01h each or 482 01E2 10 ?? 492 01EC 2 Position indic. window left border 494 01EE 2 Position indic. window top border 496 01F0 4 Tower E coord (fract FSu) 500 01F4 4 Tower AGL alt (fract FSu) 504 01F8 4 Tower N coord (fract FSu) 508 01FC 2 ?? 510 01FE 1 Flap 'carry': FFh when flap down, 00h otherwise 511 01FF 1 Flap: 00h 0ø 20h 10ø 40h 20ø 60h 30ø 7Fh 40ø 512 0200 1 Gear: 00h up - FFh down 513 0201 1 Lights: 00h off - FFh on 514 0202 1 Mags: 00h off 01h left 02h right 03h both 04h start 05h lean 515 0203 1 516 0204 1 Carb heat: 00h off - FFh on 517 0205 1 Strobe: 00h off - 01h on 518 0206 8 .SIM file name. .SIM files define the visual appearance of the aircraft; the name is padded with space if shorter than 8 chars. No path nor extension are allowed (a standard .SIM extension is apparently supplied by the program) FS4 .SIMs: SIM1.SIM Cessna R182 SIM2.SIM Gates Learjet 25G * SIM3.SIM Schweizer 2-32 Sailplane SIM4.SIM Sopwith Camel SIM5.SIM Experimental aircraft ASD .SIMs: SIM7.SIM Experimental jet aircraft SIM8.SIM Experimental sailplane SIM9.SIM Boeing 747-400 SIMA.SIM Beechcraft Starship SIMB.SIM Piper Cherokee Archer II SIMC.SIM Cessna 182 seaplane ====================================================================== NOTE ON .DRV FILE FORMAT .DRV file format applies to executable code resources installable in FS and/or callable by it. Even if the format has been called .DRV format, it is shared by other file types; among them, all the .APL files supplied with FS4 are in .DRV format, as well as *.GRA, *.KBD, *.DYN, ATC.FS4 and DYNAMIC.FS4. .DRV are basically in 80x86 machine language, even if some of them may con- tain portions in SDL. .DRV has a 31-byte 'header' with the following contents: 0000 2 file length 0002 3 1st entry point: E9 xxxx or EB xx 90: long JMP or short JMP NOP 0005 3 same as above; the addresses (relative) point to two routines in the body of the file 0008 5 ??? 000D 7 0 in all the examples I saw 0014 2 0000 or FS reference version (040B = ver 4b) 0016 2 1234h; a kind of signature 0018 2 memory required by the DRV, often equal to file length 001A 3 3rd entry point; same as 1st entry point 001D 2 check sum Bytes 001D-001E contain a cheksum of the file; the checksum algorithm can be determined from the following routine, directly excerpted from the FS4.EXE disassembly: CheckLoop: lodsb add dl,al adc dh,0 push cx mov cl,al and cl,7 xor cl,5 rol dx,cl pop cx loop CheckLoop At start DI points to the beginning of the DRV, AX and DX contain 0, CX con- tains the length of the DRV and bytes 001A-001B contain 0; at the end, DX contains the required checksum. A data section for the use of the program may be inserted after the header and is followed by the actual machine code. .DRV programs are called by FS4 with the DS segment register loaded with the data segment of FS, so that they can access the FS variables with the same addresses used by SDL sceneries; the CS register is set so that the program header starts at offset 0. .DRV code uses the small memory model, with a single segment for the code and one for the data. When disassembling .DRV with DEBUG, you have to subctract 0100h from memory addresses displayed by DEBUG itself to derive the CS: off- set at which each instruction or datum will be actually located during execu- tion within FS. .DRV files can access the FS variables and use an FS API through indirect calls to FS routines whose addresses are stored in a portion of the data seg- ment spanning at least 0B00-1C00. Clear details about this API have yet to emerge. Some of these calls pass as parameters absolute memory addresses (segment:offset) of code and/or data contained in the .DRV itself. ====================================================================== DYN FILE FORMAT by John Mechalas and MMG Because we know of only two .DYN files (F1.DYN and SD-9.DYN), the following description is not complete. I'm indebted to John Mechalas, who discovered the majority of the following material and allowed me to include it in this document. .DYN files are made of three major parts: ù a .DRV header ù a DDL (Dynamic Description Language) section with the dynamic patterns ù an SDL section with the model shapes. THE HEADER DYN header is a standard DRV header, with only two differences: ù the three entry points may point nowhere, because there is no 8088 code to be executed ù the word at offset 0A probably points to the beginning of the DDL section. THE DDL SECTION This section is made of two parts: an initial "list" of patterns and then the definitions of these patterns. However, because DDL, like SDL, is a fully procedural language, this distinction is only convenient from a logical per- spective and not inforced by any structural reason; in fact, DDL records have their own meaning, independently of their position. It may be deducted, from the two existing examples, that each pattern is given a memory area (always no more than 40h byte long and allocated right after the end of the DYN file image), which will be called "pattern memory" in the following. Given than DDL records - unlike SDL - last in the time and may occurr simultaneously, this area is probably where intermediate steps are stored. THE SDL SECTION This section contains SDL records required to draw the dynamic models. It contains three special records (45h, 46h, 48h), not found in static sceneries (or, like record 45h, found with a different structure and meaning), which probably are the link between DDL and SDL. -- 45h ----- ??? (4 bytes) 1 1 value 2 2 absolute address Probably, places the given value at the given address. The address is usually the address of a pattern memory. -- 46h ----- ??? (5 bytes) 1 2 absolute address 3 2 ??? -- 48h ----- ??? (5 bytes) 1 2 ??? 3 2 ??? ====================================================================== DYNAMIC DESCRIPTION LANGUAGE DYNAMIC RECORD CODE REFERENCE Notes Time fields are presumably in seconds, they are 2-byte fields but their values cannot be larger than 255. All addresses are absolute file locations and not relative offset as for SDL records. -- 01h ----- Rotate model to pitch attitude (5 bytes) 1 2 Pitch angle 3 2 Speed This record rotates the model about its lateral axis to the desired pitch angle. It displays the rotation process, and the speed of rotation is defined by the bytes 3-4. This is a signed value with the sign determining the direction of rotation (clockwise or counterclockwise, etc..). Fastest rotation rate is 0000h, and slowest rotation is 7FFFh. If the record is fol- lowed by a move record (12h-18h), the rotation is performed during the move and not before. -- 02h ----- Rotate model to bank attitude (5 bytes) 1 2 Bank angle 3 2 Speed Same as record 01, but for bank attitude. -- 03h ----- Rotate model to yaw attitude (5 bytes) 1 2 Yaw angle 3 2 Speed Same as record 01, but for yaw attitude. -- 04h ----- Gear up/down (2 bytes) 1 1 0 = gear up, 1 = gear down, FFh = ?? This record changes the apparence of the model. It is probably related with the three SDL entry points each model has. -- 07h ----- Set heading (3 bytes) 1 2 New heading Instantaneously sets the heading of the model. Final heading is a CANTED value, not a geographical heading. -- 08h ----- ??? (7 Bytes??) -- 09h ----- ??? (7 Bytes??) -- 0Dh ----- ??? (6 Bytes) 1 1 ?? 2 2 ?? 4 2 ?? -- 12h ----- Move East (5 bytes) 1 2 Time in seconds 3 2 East coord (delta FSu) This record moves the object from its current position to the delta position in the defined number of seconds. -- 13h ----- Move Alt (UNATTESTED, 5 bytes) 1 2 Time in seconds 3 2 Delta Alt. (delta FSu = m) Same as record 12h, but for altitude. The record has not been actually found, it has been inferred from the general pattern of record codes. -- 14h ----- Move North (5 bytes) 1 2 Time in seconds 3 2 Delta Alt. Same as record 12h, but for North coordinate. -- 15h ----- Move East / North (7 bytes) 1 2 Time in seconds 3 2 E coord (delta FSu) 5 2 N coord (delta FSu) Same as record 12h, but for East and North coordinates. -- 16h ----- Move East / Alt (7 bytes) 1 2 Time in seconds 3 2 E coord (delta FSu) 5 2 A coord (delta FSu) Same as record 12h, but for East and Alt. coordinates. -- 17h ----- Move Alt. / North (7 bytes) 1 2 Time in seconds 3 2 A coord (delta FSu) 5 2 N coord (delta FSu) Same as record 12h, but for Alt. and North coordinates. -- 18h ----- Move 3D (9 bytes) 1 2 Time in seconds 3 2 E coord (delta FSu) 5 2 A coord (delta FSu) 7 2 N coord (delta FSu) Same as record 12h, but for East, Alt. and North coordinates. -- 19h ----- Accelerate East (7 bytes) 1 2 Time in second 3 2 Rate 5 2 E coord (delta FSu) This record accelerates object motion from it's current position to the delta position in the defined number of seconds. The Rate parameter influences the acceleration rate in a yet unclear way. -- 1Ah ----- Accelerate Alt (UNATTESTED, 7 bytes) 1 2 Time in second 3 2 Rate 5 2 A coord (delta FSu = m) Same as record 19h, but for altitude. The record has not been actually found, it has been inferred from the general pattern of record codes. -- 1Bh ----- Accelerate North (7 bytes) 1 2 Time in second 3 2 Rate 5 2 N coord (delta FSu) Same as record 19h, but for the North coordinate. -- 1Ch ----- Accelerate East / North (7 bytes) 1 2 Time in second 3 2 Rate 5 2 E coord (delta FSu) 7 2 N coord (delta FSu) Same as record 19h, but for the East and North coordinates. -- 1Dh ----- Accelerate East / Alt (9 bytes) 1 2 Time in second 3 2 Rate 5 2 E coord (delta FSu) 7 2 A coord (delta FSu) Same as record 19h, but for the East and Alt. coordinates. -- 1Eh ----- Accelerate Alt. / North (UNATTESTED, 9 bytes) 1 2 Time in second 3 2 Rate 5 2 A coord (delta FSu) 7 2 N coord (delta FSu) Same as record 19h, but for the Alt. and North coordinates. The record has not been actually found, it has been inferred from the general pattern of record codes. -- 1Fh ----- Accelerate 3D (11 bytes) 1 2 Time in second 3 2 Rate 5 2 E coord (delta FSu) 7 2 A coord (delta FSu) 9 2 N coord (delta FSu) Same as record 19h, but for the East, Alt. and North coordinates. -- 20h ----- Turn left/right about point (7 bytes) 1 2 Time in seconds 3 2 Final heading 5 2 Turning radius (delta FSu) Turns the model to the new heading in the given amount of time. The center of the turning circle is defined in delta FSu from the current position along the lateral axis. Left/right turns are performed depending on the current and final heading so that no turn is greater than 180 degrees. Final heading is a CANTED value, not a geographical heading. -- 24h ----- Jump (3 bytes) 1 2 Address to jump to The record jumps to another file location. -- 25h ----- Call subroutine (3 bytes) 1 2 Subroutine absolute address -- 26h----- Return from subroutine (1 byte) -- 27h ----- Hold position (3 bytes) 1 2 Wait time in seconds This freezes the model at its current position for the given number of sec- onds. -- 28h ----- Define initial position (13 bytes) 1 4 E coord (fract FSu) 1 4 A coord (fract FSu) 1 4 N coord (fract FSu) Defines the "starting point" for the patter, used at the very beginning of the pattern definition. -- 29h ----- Sleep (1 byte) Puts the pattern in sleep; the model remains at the current position until awakened by another pattern. -- 2Ah ----- Awaken (3 bytes) 1 2 Pattern memory address of the pattern to awaken Awaken the pattern owning the given pattern memory. -- 2Ch ----- Test FS variable (7 bytes) 1 2 Jump absolute address 3 2 FS variable 5 2 value Jumps to the given address, if the given variable is equal to the given value. Used in F1.DYN to test the contents of variables 1AD2 (Airport air- craft ground traffic), 1AD4 (Airport service traffic) and 1AD6 (Misc. traf- fic). -- 2Eh ----- Test FS variable (7 bytes) 1 2 Jump absolute address 3 2 FS variable 5 2 value Jumps to the given address, if the given variable is equal to the given value. Used in F1.DYN to test the contents of variables 1AC6 (dynamic scenery detail: 0 = sparse, 1 = medium, 2 = complex). It is not clear how this record is different from record 2Ch; one may note that var 1AC6 may have three different values, while variables tested with record 2Ch may have only two. -- 2Fh ----- Branch on area (11 bytes) 1 2 Jump absolute address 3 2 East min (int FSu) 5 2 East max (int FSu) 7 2 North min (int FSu) 9 2 North max (int FSu) Jumps to the given address if outside the given coordinate ranges. Used in F1.DYN to avoid rendering dynamic patterns of non current areas. -- 31h ---- Pattern Declaration (13 bytes) 1 2 Pattern number 3 2 pattern memory absolute address 5 2 pattern DDL definition absolute address 7 2 pattern first SDL entry point 9 2 pattern second SDL entry point 11 2 pattern third SDL entry point Declares (or perhaps executes) a pattern. This record is used once for each pattern, associating to it a pattern memory area, a DDL routine and 3 (?) SDL routines to draw the model. -- FFh ----- Exit (1 byte) Exits the DDL processor. ====================================================================== ADV FILE FORMAT by John Mechalas .ADV files have a very simple structure, being only a successions of ADV records, without header or sections of any kind. ADV records, compared with SDL's, have the following peculiarities: ù record codes are 2-byte long; however, since the second byte is always 0, they may considered made of one code byte plus one 0 byte; ù addresses are always absolute, not relative to the current record as in SDL ù many records have, right after the code, a 2-byte field with the address of the next record; it as been labelled with "Next" in the reference below. ù records map quite well to ADV commands; whenever possible ADV commands have been retained as record names. ù All decimal values are truncated to integer, and are not modified anymore (for instance, FS East and North coordinates are memorized as integer but not shifted by the 4000h factor; degrees are stored in degrees, not in the 1/182.04 FS unit, and so on). Each value is stored in the high word of a 4-byte field, possibly to allow future inclusion of real decimal values. ADV RECORD CODE REFERENCE -- 00h ----- EOF (4 bytes) 2 2 Next -- 01h ----- IF (length varies according to the condition) 2 2 Address to jump to if condition TRUE 4 2 Address to jump to if condition FALSE The condition is determined by the next word (at offset 6) and may have the following structures: 6 2 00 KEY 8 2 key code 6 2 01 BUBBLE 8 2 0000 10 2 north 12 2 0000 14 2 east 16 2 0000 18 2 min 20 2 0000 22 2 to 6 2 02 ALTITUDE 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 03 DME 8 2 0000 10 2 max distance (min distance is ignored) 6 2 04 COM 8 2 frequency in MHz BCD less 100 (as in SDL frequencies) 6 2 05 NAV1 8 2 frequency in MHz BCD less 100 (as in SDL frequencies) 6 2 06 NAV2 8 2 frequency in MHz BCD less 100 (as in SDL frequencies) 6 2 07 PITCH 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 08 BANK 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 09 HEADING 8 2 0000 10 2 min 12 2 0000 14 2 max 6 2 0A AIRSPEED 8 2 0000 10 2 min 12 2 0000 14 2 max 6 2 0B GROUNDSPEED 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 0C FLAPS 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 0D POWER 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 0F GEARUP 6 2 10 GEARDOWN 6 2 11 JETENGINE 6 2 12 PROPENGINE 6 2 13 VARTEST 8 2 variable 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 14 VARMASK 8 2 variable 10 2 bit mask 6 2 15 RADIAL 8 2 0000 10 2 north 12 2 0000 14 2 east 16 2 0000 18 2 min 20 2 0000 22 2 to 6 2 16 GSLOPE 8 2 0000 10 2 north 12 2 0000 14 2 east 16 2 0000 18 2 min 20 2 0000 22 2 to 6 2 17 COURSE 8 2 0000 10 2 min 12 2 0000 14 2 to 6 2 18 CYLINDER 8 2 0000 10 2 north 12 2 0000 14 2 east 16 2 0000 18 2 min 20 2 0000 22 2 to 6 2 19 XPNDR 8 4 4 digit frequency as text string 6 2 1A ADF 8 4 4 digit frequency as text string 6 2 1B ALTAGL 8 2 0000 10 2 min 12 2 0000 14 2 to -- 02h ----- GOTO (4 bytes) 2 2 Address to jump to -- 03h ----- PLAY (5 bytes + file name length) 2 2 Next 4 xx File name (0-terminated) -- 04h ----- PRINT (5 bytes + text length) 2 2 Next 4 xx Text string (0-terminated) -- 05h ----- SETPOSITION (16 bytes) 2 2 Next 4 2 0000 6 2 North coord (int FSu) 8 2 0000 10 2 East coord (int FSu) 12 2 0000 14 2 Alt. coord (int FSu) -- 06h ----- WAIT (8 bytes) 2 2 Next 4 2 0000 6 2 Time in seconds -- 07h ----- ONCRASH (6 bytes) 2 2 Next 4 2 Address to jump to on crash -- 08h ----- GOSUB (6 bytes) 2 2 Next 4 2 Address of subroutine -- 09h ----- RETURN (4 bytes) 2 2 Next -- 0Ah ----- SETVAR (8 bytes) 2 2 Next 4 2 Variable (see below for a variable reference) 6 2 Value -- 0Bh ----- ADDVAR (8 bytes) 2 2 Next 4 2 Variable 6 2 Value to add -- 0Dh ----- PRINTVAR (7 bytes + text length) 2 2 Next 4 2 Variable to print 6 xx Text to print (0-terminated) -- 0Eh ----- MOVEVAR (8 bytes) 2 2 Next 4 2 Destination variable 6 2 Source variable -- 0Fh ----- RESET (4 bytes) 2 2 Next -- 10h ----- VIEW (9 bytes + file name length) 2 2 Next 4 2 0000 6 2 Time in seconds 8 xx file name (0-terminated) -- 11h ----- ONSTALL (6 bytes) 2 2 Next 4 2 Address to go to on stall -- 12h ----- RETURN2 (4 bytes) 2 2 Next -- 13h ----- Variable arithmetics (12 bytes + 4 bytes for each operation) 2 2 Next 4 2 Destination variable Operations are described alternating a source variable and an operator: 2 Source variable 2 Operator: 1 + 2 - 3 * 4 / 5 logical AND 6 logical OR 7 logical XOR The last variable has 0000h as 'operator', and the calculation is ended by: 4 0013h 0000h Example: 13 00 6E 00 42 04 10 04 01 00 12 04 03 00 14 04 02 00 16 04 04 00 18 04 06 00 1A 04 05 00 1C 04 07 00 1E 04 00 00 13 00 00 00 is analysed: 0013 006E 0442 Math, Next statement at 006E, dest var Z 0410 0001 var A, oper. + 0412 0003 var B, oper. * 0414 0002 var C, oper. - 0416 0004 var D, oper. / 0418 0006 var E, oper. logical OR 041A 0005 var F, oper. logical AND 041C 0007 var G, oper. logical XOR 041E 0000 var H, no oper. 0013 0000 Math end and corresponds to the AAF statement: Z := A + B * C - D / E | F & G ^ H ---------- ADV VARIABLES Please note that, as clearly stated in AAF documentation, the following vari- ables are by no mean reserved or documented; their usage may be subject to change in future FS releases. 0000 remainder - result 0DA4 rudped_ind 0410 A 0DA6 throtl_ind 0412 B 0DA8 elvtrm_ind 0414 C 0DAA brake_ind 0416 D 0DB2 elev_pos 0418 E 0DC9 ailer_pos 041A F 0DE0 rudder_pos 041C G 0DF7 fuellf 041E H 0DFA fuelrt 0420 I 0DFD oiltmp 0422 J 0DFF oilprs 0424 K 0E01 dmefrc 0426 L 0E02 dmemil 0428 M 0E03 dmedist 042A N 0E05 dmespeed 042C O 0E06 dmeblk 042E P 0E07 dmesource 0430 Q 0E08 dme_update 0432 R 0E09 ils_dmedist 0434 S 0E0B vornew 0436 T 0E0C pornew 0438 U 0E0D gsnew 043A V 0E0E iomact 043C W 0E0F tfflag 043E X 0E10 pfflag 0440 Y 0E11 omiold 0442 Z 0E12 nfvor 0E14 efvor 0280 altmsl 0E22 date_year 028C tod 0E24 date_month_day 0362 hour 0E26 time_hours_min 0363 minute 0E28 time_seconds 04C6 menu_level 0E2C cloud_dev_fract 0534 fulltower 0E2E cloud2top 0536 titles 0E30 cloud2bot 0538 shadflg 0E32 cloud2cover 053C sysmode 0E48 cloud2dev 053E sndflg 0E4A cloud1top 0542 sound2 0E4C cloud1bot 0544 pauflg 0E4E cloud1cover 0548 auto_coord 0E64 cloud1dev 054A smoke_enable 0E66 cloud3top 054C atc_com 0E68 cloud3bot 054E smoke_now 0E6A cloud3cover 055C smoke_plane_ptr 0E74 cloud3spd 0568 random 0E76 cloud3dir 07AA season_cycl 0E78 w9vel 07B6 cfpd 0E79 w9turb 07BE efis_type_cycl 0E7A w9dir 098E scenery_cycl 0E7C w6vel 09C8 cmfreq 0E7D w6turb 09CC hederr 0E7E w6dir 09D0 barom 0E80 w3vel 09D2 trans_ident_flg 0E81 w3turb 09D6 nvfreq 0E82 w3dir 09D8 nav1_vorrad 0E84 w0vel 09DC pvfreq 0E85 w0turb 09E2 aerflg 0E86 w0dir 09E4 hedlsb 0E88 w9top 09E5 bpupdt 0E8A w9bot 09E6 sound_rpm 0E8C w6top 09E7 emrgcy 0E8E w6bot 09E9 ground 0E90 w3top 09EA stlwrn 0E92 w3bot 09EB spdwrn 0E94 w0depth 09F6 plane_height 0E96 tmpvar 0B47 gndbias 0E97 in_the_clouds 0B5D vely 0FEF pause 0B60 vel_x 105C mouse 0B62 vel_y 105D mouse_mode 0B64 vel_z 105E mouse_button 0B66 vel_p 105F curs_x 0B68 vel_b 1061 curs_y 0B6A vel_h 106E mouse_brake 0CAB magcom 11F8 autop_master 0CAD obi 11FA wing_leveler 0CAE oldrpm 11FC nav1_lock 0CAF pbi 11FE heading_lock 0CEA tod_master 1200 head_lock_var 0D1A gen_model 1202 altit_lock 0D58 flaps 1204 altit_lock_var 0D5A gear 1B32 wind_up_vel 0D5B lights 1B33 weather_turb 0D5C magno 1B34 weather_clouds 0D5E carbh 1B36 weather_fronts 0D5F strobes 1B38 weather_winds 0D60 strobe_flash 1B3A weather_turbulence 0D7E pan_active 1B46 mixture_pos 0D80 pan_gen 1B48 fuel_flow 0D81 lear_airspeed 1B4A displace 0D82 engine_type 1B4C prop_leng 0D83 retractable 1B4E oilamt 0D84 adf_flag 1B50 nrpm 0D86 ail_rud_lock 1B52 bhp 0D87 cntr_ail_5key 1B54 thp 0D88 cntr_rud_5key 1C82 gear_smoke 0D89 cntr_elv_5key 1C84 smoke_cntr 0DA0 yoke_ind_y 1C86 crash_protector 0DA2 yoke_ind_x ==================== FSSTRUCT END ====================================