Much of a DWG file from R13 on is read bit by bit, not byte by byte. The header variables, classes and objects are bit streams in which common values such as 0, 1.0 and 256 take only two bits. This page lists every data type the specification uses and how each is coded. It follows chapter 2 of the Open Design Alliance’s Open Design Specification for .dwg files, version 5.4.1. Unless stated, data is little-endian, least significant byte first. Within a byte, bits are read from the most significant end, as the examples show.
- Data type codes
- 3B, BS, BL, BLL, BD
- Modular chars (MC), modular shorts (MS)
- BE, DD, BT
- Colours (CMC, ENC, TC)
- Object type (OT)
- Handle references (H)
- Strings (T, TU, TV)
- 8-bit CRC and 32-bit CRC
- What changes by version
Data type codes
| Code | Name | Meaning |
|---|---|---|
| B | bit | One bit, 1 or 0 |
| BB | 2-bit code | A special 2-bit value, such as the entity mode of an entity |
| 3B | bit triplet | 1 to 3 bits (below); R2010 and later |
| BS | bitshort | 16-bit value, compressed |
| BL | bitlong | 32-bit value, compressed |
| BLL | bitlonglong | 64-bit value, compressed; R2010 and later |
| BD | bitdouble | Double, compressed |
| 2BD | 2D point | Two bitdoubles |
| 3BD | 3D point | Three bitdoubles |
| RC | raw char | One byte, not compressed |
| RS | raw short | Two bytes, not compressed |
| RD | raw double | Eight-byte IEEE double, not compressed |
| RL | raw long | Four bytes, not compressed |
| 2RD | – | Two raw doubles |
| 3RD | – | Three raw doubles |
| MC | modular char | Variable-length integer in bytes |
| MS | modular short | Variable-length integer in 16-bit units |
| H | handle reference | Below |
| T | text | Bitshort length, then the string |
| TU | Unicode text | Bitshort character count, then UTF-16 characters, 2 bytes each; read from the string stream |
| TV | variable text | T in R2004 and earlier, TU in R2007 and later |
| X | special form | Described where it is used |
| U | unknown | – |
| SN | sentinel | 16 bytes used for file recovery |
| BE | bit extrusion | Below |
| DD | bitdouble with default | Below |
| BT | bit thickness | Below |
| 3DD | – | 3D point as three DD, needing three default values |
| CMC | CmColor | Colour value |
| TC | true colour | The same format as CMC in R2004 and later |
| OT | object type | Below |
A seeker is an RL holding an absolute file address or an offset from a known address. Some prescriptions also use EC (for vertex flags), S, L and D, which chapter 2 does not define; see Not confirmed.
3B: bit triplet
Read bits until a 0 bit is read or three bits have been read, whichever comes first. Each time a bit is read, shift the bits already read one place left. The result is 0 to 7.
BS: bitshort
| First 2 bits | Meaning |
|---|---|
| 00 | A short (2 bytes, least significant first) follows |
| 01 | An unsigned char (1 byte) follows |
| 10 | The value is 0 |
| 11 | The value is 256 |
The one-byte form is for positive values below 256; negative values use the
short form, so −1 is 00 11111111 11111111, not
01 11111111.
0000000001000000011011010000111110
00 00000001 00000001 short 257
10 0
11 256
01 00001111 15
10 0
BL: bitlong
| First 2 bits | Meaning |
|---|---|
| 00 | A long (4 bytes, least significant first) follows |
| 01 | An unsigned char (1 byte) follows |
| 10 | The value is 0 |
| 11 | Not used |
As with BS, negative values use the full form.
000000000100000001000000000000000010010000111110
00 00000001 00000001 00000000 00000000 long 257
10 0
01 00001111 15
10 0
BLL: bitlonglong
A 3B gives a length l, then l bytes follow, least significant first.
BD: bitdouble
| First 2 bits | Meaning |
|---|---|
| 00 | An 8-byte IEEE double follows |
| 01 | The value is 1.0 |
| 10 | The value is 0.0 |
| 11 | Not used |
MC: modular char
A run of bytes ending at the first byte whose high bit is 0. In each byte the high bit means “another byte follows” and the other seven bits are data, least significant group first. If the final byte also has bit 0x40 set, that bit is cleared and the number is negative. In the object map, modular chars hold handle offsets, which are never negative.
| Bytes | Working | Value |
|---|---|---|
82 24 | 0x02 + (0x24 << 7) = 2 + 18 × 256 | 4610 |
E9 97 E6 35 | 0x69 + (0x17 << 7) + (0x66 << 14) + (0x35 << 21) = 233 + 139 × 256 + 185 × 256² + 6 × 256³ | 112823273 |
85 4B | 0x4B has 0x40 set: negative; 0x05 + (0x0B << 7) = 133 + 5 × 256 | −1413 |
MS: modular short
Like a modular char, but in 16-bit little-endian units: the high bit of each short means another follows, and the other 15 bits are data. Modular shorts hold object sizes, so in practice there are one or two units.
| Bytes | Working | Value |
|---|---|---|
31 F4 8D 00 | Shorts 0xF431 (continue) and 0x008D; 0x7431 + (0x8D << 15) = 62513 + 70 × 65536 | 4650033 |
BE: bit extrusion
In R13 and R14, a 3BD. From R2000, one bit: 1 means the extrusion is (0, 0, 1) and nothing more is stored; 0 means a 3BD follows.
DD: bitdouble with default
A 2-bit code, then data, applied to a default value that the field’s description names (often the previous value):
| Code | Meaning |
|---|---|
| 00 | No data: use the default |
| 01 | 4 bytes follow; they replace the first 4 bytes of the default (little-endian) |
| 10 | 6 bytes follow; the first 2 replace bytes 5 and 6 of the default and the last 4 replace its first 4 bytes |
| 11 | A full RD follows |
BT: bit thickness
In R13 and R14, a BD. From R2000, one bit: 1 means the thickness is 0.0; 0 means a BD follows.
Colours: CMC, ENC and TC
In R2000 and earlier a colour is a BS colour index. From R2004 there are two forms. CMC, used by objects:
| Type | Meaning |
|---|---|
| BS | Colour index, always 0 |
| BL | RGB value |
| RC | Colour byte: & 1, a colour name follows (TV); & 2, a book name follows (TV) |
ENC, used by entities, may refer to a DBCOLOR object and carry a transparency. It starts with a BS whose high byte holds flags and whose low bits hold the colour index:
| Flag | Meaning |
|---|---|
| 0x8000 | Complex (RGB) colour: a BS with the RGB value in its low 24 bits follows |
| 0x4000 | Has an AcDbColor reference (0x8000 is also set); the handle is in the handle stream |
| 0x2000 | A transparency BL follows. Its first byte is the type: 0 by layer, 1 by block, 3 the transparency value is in the last byte |
| none | The colour is the AutoCAD colour index (ACI) given by the colour number |
TC (true colour) is the same as CMC in R2004 and later.
OT: object type
Up to R2007 the object type is a BS. From R2010 it is a 2-bit code followed by one or two bytes:
| Bit pair | Meaning |
|---|---|
| 0 | Read the next byte |
| 1 | Read the next byte and add 0x1F0 |
| 2 | Read the next two bytes (a raw short) |
| 3 | Should never occur; read as 2 |
The type numbers are listed on Objects and entities.
H: handle references
Every object in an R13 or later file has a handle, and objects refer to each other
by handle. A reference is stored as |CODE (4 bits)|COUNTER (4 bits)|HANDLE or
OFFSET|: COUNTER is the number of handle bytes that follow, most significant
first. The specification writes a reference as CODE.COUNTER.BYTE…, for example
5.1.0F, the usual reference to layer 0 (handle F) in drawings made by
R13.
Where the reference expresses ownership, CODE gives its kind (TYPEDOBJHANDLE):
| Code | Meaning |
|---|---|
| 2 | Soft ownership: the owner does not need the owned object, which cannot exist by itself |
| 3 | Hard ownership: the owner needs the owned object, which cannot exist by itself |
| 4 | Soft pointer: neither object needs the other |
| 5 | Hard pointer: the referencing object needs the referenced one, but both are owned by another object |
Elsewhere the handle is an offset from a reference handle, always a soft pointer (OFFSETOBJHANDLE):
| Code | Result |
|---|---|
| 0x2, 0x3, 0x4, 0x5 | The value read is the handle |
| 0x6 | Reference handle + 1 (length 0) |
| 0x8 | Reference handle − 1 (length 0) |
| 0xA | Reference handle + offset |
| 0xC | Reference handle − offset |
5 2 05 E7
0101 0010 00000101 11100111
Strings: T, TU and TV
Up to R2004, text (T) is a BS length followed by that many bytes in the drawing’s code page. From R2007, text is Unicode (TU): a BS character count and UTF-16 characters, 2 bytes each. Field lists write TV for “T before R2007, TU from R2007”.
In R2007 and later, an object’s Unicode strings are not where the field list puts them: they are gathered in a string stream at the end of the object’s data, and the handles in a separate handle stream after that. How to find the string stream is described on Objects and entities. The header variables and classes sections use the same arrangement in R2007 and later.
Extended entity data and XRECORD use other string forms: in R13 to R2004 a 1-byte length, a 2-byte code page and the bytes; in R2007 and later a 2-byte length and that many UTF-16 characters (see Extended entity data).
8-bit CRC
Despite its name this CRC is 2 bytes long: a byte-at-a-time CRC with a 256-entry table of 16-bit values. CRCs are always on byte boundaries and never bit coded, so an object may end with unused bits before its CRC. AutoCAD uses a non-zero starting value in places, and sometimes XORs the result with a “magic number” (in R13 and later, only in the file header).
unsigned short crc8(unsigned short dx, const unsigned char *p, long n)
{
while (n-- > 0) {
unsigned char al = (unsigned char)(*p ^ (dx & 0xFF));
dx = (dx >> 8) & 0xFF;
dx = dx ^ crctable[al];
p++;
}
return dx;
}
To accumulate a CRC, call it with 0 (or the starting value for that kind of data) and then with the last result. Starting values used: 0xC0C1 for the header variables; 0 with an XOR for the file header.
01000000 11100000 01010101 01010101
01 bitshort with one byte
00000011 value 3
100000 unused bits
01010101 01010101 the CRC
32-bit CRC
From R2004 a 32-bit CRC is also used, with a 256-entry table of 32-bit values that starts 0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA:
uint32_t crc32(const uint8_t *p, uint32_t n, uint32_t seed)
{
uint32_t inverted = ~seed;
while (n--) {
uint8_t byte = *p++;
inverted = (inverted >> 8) ^ crc32Table[(inverted ^ byte) & 0xff];
}
return ~inverted;
}
R2007 adds two 64-bit CRCs, described on File structure.
What changes by version
| Item | R13–R14 | R2000 | R2004 | R2007 | R2010 and later |
|---|---|---|---|---|---|
| Extrusion (BE) | 3BD | Bit, then 3BD if not (0, 0, 1) | |||
| Thickness (BT) | BD | Bit, then BD if not 0.0 | |||
| Colour | BS index | CMC, or ENC in entities | |||
| Text (TV) | T, code page bytes | TU, UTF-16 in a string stream | |||
| Object type (OT) | BS | Bit pair and 1 or 2 bytes | |||
| 3B, BLL | – | Used | |||
Not confirmed
- The codes EC, S, L and D appear in some prescriptions (for example the vertex flags and the DICTIONARY item count) but are not defined in chapter 2.
- Section 2.11 says colours are a BS index in R15 (R2000) and earlier, but the common entity format in section 20.2 lists an ENC entity colour for “R2000+”. The table above follows section 2.11.
Sources
- Open Design Specification for .dwg files, version 5.4.1 – Open Design Alliance; chapter 2 (bit codes and data definitions), and the string forms in chapters 20 and 28