The header is 12 bytes and all its numbers are little-endian. It says which bytecode the file holds and records the date and size of the source file. The code object starts at offset 12.
| Offset | Size | Field | Meaning |
|---|---|---|---|
| 0 | 2 | magic | Which bytecode the file holds |
| 2 | 2 | 0D 0A | A carriage return and a line feed |
| 4 | 4 | source_mtime | The source’s modification time |
| 8 | 4 | source_size | The source’s size in bytes |
Magic number
A 16-bit number, then the bytes 0D 0A. CPython changes the number
whenever its bytecode changes, and only loads a file whose number is its own. The
carriage return and line feed mean that a file copied in text mode, which alters line
endings, no longer has the right magic number.
3379 is the final number of CPython 3.6, and the others belong to alpha, beta and release-candidate builds. The descriptions are those of the list in CPython’s source.
| Magic | Bytes | Release | What changed |
|---|---|---|---|
| 3360 | 20 0D | 3.6a0 | Added FORMAT_VALUE |
| 3361 | 21 0D | 3.6a1 | The line step in co_lnotab became signed |
| 3370 | 2A 0D | 3.6a2 | 16-bit wordcode: every instruction became two bytes |
| 3371 | 2B 0D | 3.6a2 | Added BUILD_CONST_KEY_MAP |
| 3372 | 2C 0D | 3.6a2 | MAKE_FUNCTION simplified, MAKE_CLOSURE removed |
| 3373 | 2D 0D | 3.6b1 | Added BUILD_STRING |
| 3375 | 2F 0D | 3.6b1 | Added SETUP_ANNOTATIONS and STORE_ANNOTATION |
| 3376 | 30 0D | 3.6b1 | Simplified the CALL_FUNCTION family and BUILD_MAP_UNPACK_WITH_CALL |
| 3377 | 31 0D | 3.6b1 | The __class__ cell is set from type.__new__ |
| 3378 | 32 0D | 3.6b2 | Added BUILD_TUPLE_UNPACK_WITH_CALL |
| 3379 | 33 0D | 3.6 (from 3.6rc1) | More thorough __class__ validation |
Source modification time
At offset 4: the source file’s modification time when it was compiled, as a 32-bit count of seconds since 1 January 1970. Python compares it with the source, and recompiles if the two differ.
Source size
At offset 8: the size of the source file in bytes, modulo 232. Python compares this too, so a file edited within the same second is still caught if its size changed.
File names
Python writes these files to a __pycache__ folder next to the source
and puts the interpreter’s name and version in the file name.
| Source | Compiled by | File |
|---|---|---|
spam.py | CPython 3.6 | __pycache__/spam.cpython-36.pyc |
spam.py | CPython 3.6 with -O | __pycache__/spam.cpython-36.opt-1.pyc |
spam.py | CPython 3.6 with -OO | __pycache__/spam.cpython-36.opt-2.pyc |
A spam.pyc placed in a folder by itself, with no source file beside it,
can also be imported.