Protocol
This page presents a dissection of the new Minecraft Alpha protocol by aera (Andrew Godwin), ylt (Joe Carter) and TkTech (Tyler Kennedy). Additionally, credit goes to the citizens of #mcdevs who helped by providing packet dumps and insight. If you're having trouble, check out the FAQ.
Note: While you may use the contents of this page without restriction to create servers, clients, bots, etc… you still need to provide the attribution above if you copy any of the contents of this page for publication elsewhere.
Contents
- 1 Data Types
- 2 Terminology
- 3 Units of Measurement
- 4 Packets
- 4.1 Keep Alive (0x00)
- 4.2 Login Request (0x01)
- 4.3 Handshake (0x02)
- 4.4 Chat Message (0x03)
- 4.5 Time Update (0x04)
- 4.6 Player Inventory (0x05)
- 4.7 Spawn Position (0x06)
- 4.8 Use Entity? (0x07)
- 4.9 Update Health (0x08)
- 4.10 Respawn (0x09)
- 4.11 Player (0x0A)
- 4.12 Player Position (0x0B)
- 4.13 Player Look (0x0C)
- 4.14 Player Position & Look (0x0D)
- 4.15 Player Digging (0x0E)
- 4.16 Player Block Placement (0x0F)
- 4.17 Holding Change (0x10)
- 4.18 Animation (0x12)
- 4.19 Named Entity Spawn (0x14)
- 4.20 Pickup Spawn (0x15)
- 4.21 Collect Item (0x16)
- 4.22 Add Object/Vehicle (0x17)
- 4.23 Mob Spawn (0x18)
- 4.24 Entity Velocity? (0x1C)
- 4.25 Destroy Entity (0x1D)
- 4.26 Entity (0x1E)
- 4.27 Entity Relative Move (0x1F)
- 4.28 Entity Look (0x20)
- 4.29 Entity Look and Relative Move (0x21)
- 4.30 Entity Teleport (0x22)
- 4.31 Entity Status? (0x26)
- 4.32 Attach Entity? (0x27)
- 4.33 Pre-Chunk (0x32)
- 4.34 Map Chunk (0x33)
- 4.35 Multi Block Change (0x34)
- 4.36 Block Change (0x35)
- 4.37 Explosion (0x3C)
- 4.38 Open Inventory (0x64)
- 4.39 Inventory Close (0x65)
- 4.40 Inventory Click (0x66)
- 4.41 Inventory Update (0x67)
- 4.42 ??? (0x69)
- 4.43 ??? (0x6A)
- 4.44 Update Sign (0x82)
- 4.45 Disconnect/Kick (0xFF)
- 5 Protocol History
Data Types
All types in Java (and as such Minecraft) are big-endian, that is, the most significant byte comes first. The majority of everyday computers are little endian, and using most programming languages will require converting big endian values to little endian.
Size | Range | Notes | |
---|---|---|---|
byte | 1 | -128 to 127 | Signed, two's complement |
short | 2 | -32768 to 32767 | Signed, two's complement |
int | 4 | -2147483648 to 2147483647 | Signed, two's complement |
long | 8 | -9223372036854775808 to 9223372036854775807 | Signed, two's complement |
float | 4 |
See this |
Single-precision 32-bit IEEE 754 floating point |
double | 8 |
See this |
Double-precision 64-bit IEEE 754 floating point |
string | … | N/A | UTF-8 string. Prefixed by a short containing the length of the string |
bool | 1 | 0 or 1 | Value can be either True (0x01) or False (0x00) |
Terminology
This is a fairly lengthy page, and to make it more readable certain terminology must be understood. Terms used on this page and their definition are provided below.
Definition | |
---|---|
Player | When used in in the singular, Player always refers to the client connected to the server |
Entity | Entity refers to any item, player or mob in the world. This definition is subject to change as Notch extends the protocol |
EID | An EID - or Entity ID - is a unique 4-byte integer used to identify a specific entity |
XYZ | In this document, the axis names are the same as those used by Notch. Y is always the upwards coordinate, while X and Z are parallel to the ground |
MOTD | Message Of The Day |
Units of Measurement
There are several different units of measurement used in the protocol depending on what is being described. For example, it wouldn't make much sense to send the position of a block (which is a constant multiple of 32) in a floating point double.
Type | Represents | |
---|---|---|
Absolute | double | Represents an objects exact location in the world, specified in block coordinates. |
Absolute Integer | int | Represents an objects approximate location in the world, specified in pixels. This is the Absolute position cast to an integer, thus losing precision. |
Block | int or byte | Represents a blocks exact location in the world. Block = Absolute / 32. |
Chunk | int or short | Represents the exact position of a chunk. Chunk = Block / 16. |
Packets
Keep Alive (0x00)
This packet may be sent to keep the connection alive, or may be a relic of UDP testing. No one is really sure. What we do know is that the Alpha server will disconnect a client if it doesn't receive at least one packet before 1200 in-game ticks, and the Alpha client will time out the connection under the same conditions.
Packet ID |
---|
0x00 |
Login Request (0x01)
Client to Server
Sent by the client after the handshake to finish logging in. If the version is outdated or any field is invalid, the server will disconnect the client with a kick. If the client is started in offline mode, the player's username will default to Player
, making LAN play with more than one player impossible (without authenticating) as the server will prevent multiple users with the same name.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x01 | Protocol Version | int | 7
|
The latest version of the protocol is 7 |
Username | string | TkTech
|
The name of the user attempting to login | |
Password | string | Password
|
Used to login to password-protected servers | |
Map Seed | long | 0
|
This value is not required for the client | |
Dimension | byte | 0
|
This value is not required for the client | |
Total Size: | 18 bytes + length of strings |
Server to Client
Sent by the server if it accepts the clients login request. If it didn't, it'll send a kick instead.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x01 | Entity ID | int | 1298
|
The Players Entity ID |
Unknown | string | n/a | Not yet used (Possibly the server name?) | |
Unknown | string | n/a | Not yet used (Possibly the MOTD? ) | |
Map Seed | long | 971768181197178410
|
Used for map generation | |
Dimension | byte | 0
|
Used for specifying the players dimension -1 for hell, 0 otherwise | |
Total Size: | 18 bytes + length of strings |
Handshake (0x02)
Client to Server
This is the first packet sent when the client connects and is used for Authentication.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x02 | Username | string | TkTech
|
The username of the player attempting to connect |
Total Size: | 3 bytes + length of strings |
Server to Client
This is the first packet sent when the client connects and is used for Authentication. If the hash is '-', then the client continues without doing name authentication. If the hash is a '+', the client sends the server password in the login request.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x02 | Connection Hash | string | 2e66f1dc032ab5f0
|
A unique, per-connection hash, or '-', or '+' |
Total Size: | 3 bytes + length of strings |
Chat Message (0x03)
A message from the client to the server, or the server to the client. The actual handling of chat messages is variable and depends on the server and client; there are no de facto standards yet.
The Alpha server will check the message to see if it begins with a '/'. If it doesn't, the username of the sender is prepended and sent to all other clients (including the original sender). If it does, the server assumes it to be a command and attempts to process it. A message longer than 100 characters will cause the server to kick the client. This limits the chat message packet length to 103 bytes. Note that this limit does not apply to incoming chat messages as the server may have prepended other information, not limited to, but usually including, a username.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x03 | Message | string | <Bob> Hello World!
|
User input must be sanitized server-side |
Total Size: | 3 bytes + length of strings |
Time Update (0x04)
The default SMP server increments the time by 20
every second.
The current time ranges from 0 to 24000.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x04 | Time | long |
|
The world (or region) time in minutes |
Total Size: | 9 bytes |
Player Inventory (0x05)
Sent by the server to set or reset a players inventory. This includes the main inventory, equipped armour and crafting slots. Packets for all three types are sent to initialize the players inventory before spawning them. Clients send this packet to the server to indicate the contents of their inventory.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x05 | Type | int | -1
|
The “type” of inventory being sent (see below) |
Count | short | 4
|
The number of inventory items (see below) | |
Payload | … |
|
The payload (see below) | |
Total Size: | 7 bytes + size of payload |
Type can (currently) be one of three values:
Inventory Type | Value | Count |
---|---|---|
Main inventory | -1 | 36 |
Equipped armour | -2 | 4 |
Crafting slots | -3 | 4 |
This packet is a bit more tricky to parse than most others because the size of its payload is variable. The payload is an array of shorts (item ID) optionally followed by a byte-short pair (count and uses) as long as the item ID does not equal -1
, which signifies an empty slot.
Uses is the number of times an item has been used (the value starts at 0 and counts up.) Note that an invalid use of an item may count as 2 uses.
offset = 0
for slot in count:
item_id = payload[offset] as short
offset += 2
if item_id is not equal to -1:
count = payload[offset] as byte
offset += 1
uses = payload[offset] as short
offset += 2
inventory[slot] = new item(item_id, count, uses)
else:
inventory[slot] = None
Spawn Position (0x06)
Sent by the server after login to specify the players starting location and to initialize compasses. It can be sent at any time afterwords to update the point compasses are focused on.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x06 | X | int | 117
|
Spawn X in block coordinates |
Y | int | 70
|
Spawn Y in block coordinates | |
Z | int | -46
|
Spawn Z in block coordinates | |
Total Size: | 13 bytes |
Use Entity? (0x07)
This packet is new to version 4 of the protocol, and is believed to be Use Entity.
(This packet data values are not fully verified)
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x07 | User | int | 1298
|
The entity of the player (ignored by the server) |
Target | int | 1805
|
The entity the player is interacting with | |
Left-click? | bool | true
|
Seems to be | |
Total Size: | 10 bytes |
Update Health (0x08)
Sent by the server to update/set the health of the player it is sent to. Added in protocol version 5.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x08 | Health | short | 20 | 0 = dead, 20 = full HP |
Total Size: | 3 bytes |
Respawn (0x09)
Sent by the client when the player presses the "Respawn" button after dying. The server then drops the player's inventory, teleports the user to the spawn point, and sends a respawn packet in response.The client will not leave the respawn screen until it receives a respawn packet.
Packet ID |
---|
0x09 |
Total Size: 1 bytes |
Player (0x0A)
This packet is used to identify the state of the client, with the idea being to send one each game-tick to detect speed hackers. Notch will be optimizing/removing this in the future. This packet was previously referred to as Flying
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x0A | On Ground | bool | 1
|
True if the client is on the ground, False otherwise
|
Total Size: | 2 bytes |
Player Position (0x0B)
Updates the players XYZ position on the server. If Stance - Y
is less than 0.1
or greater than 1.65
, the stance is illegal and the client will be kicked with the message “Illegal Stance”.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x0B | X | double | 102.809
|
Absolute position |
Y | double | 70.00
|
Absolute position | |
Stance | double | 71.62
|
Used to modify the players bounding box when going up stairs, crouching, etc… | |
Z | double | 68.30
|
Absolute position | |
On Ground | bool | 1
|
Derived from packet 0x0A | |
Total Size: | 34 bytes |
Player Look (0x0C)
Updates the direction the player is looking in.
Yaw is measured in degrees, and does not follow classical trigonometry rules. The unit circle of yaw on the xz-plane starts at (0, 1) and turns backwards towards (-1, 0).
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x0C | Yaw | float | 0.00
|
Absolute rotation on the X Axis |
Pitch | float | 0.00
|
Absolute rotation on the Y Axis | |
On Ground | bool | 1
|
Derived from packet 0x0A | |
Total Size: | 10 bytes |
Player Position & Look (0x0D)
A combination of Player Look and Player position.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x0D | X | double | 6.5
|
Absolute position |
Stance | double | 67.240000009536743
|
Used to modify the players bounding box when going up stairs, crouching, etc… | |
Y | double | 65.620000004768372
|
Absolute position | |
Z | double | 7.5
|
Absolute position | |
Yaw | float | 0.0
|
Absolute rotation on the X Axis | |
Pitch | float | 0.0
|
Absolute rotation on the Y Axis | |
On Ground | bool | 0
|
Derived from packet 0x0A | |
Total Size: | 42 bytes |
This packet differs from client Player Position & Look packet, the Stance and Y are sent in a different order, however because of the different order this is sent the client will actually use the X,Y,Stance,Z client layout.
Player Digging (0x0E)
Sent repeatedly as the player mines a block.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x0E | Status | byte | 1
|
The action the player is taking against the block (see below) |
X | int | 32
|
Block position | |
Y | byte | 64
|
Block position | |
Z | int | 32
|
Block position | |
Face | byte | 3
|
The face being hit (see below) | |
Total Size: | 12 bytes |
Status can (currently) be one of four values:
Meaning | Value |
---|---|
Started digging | 0
|
Digging | 1
|
Stopped digging | 2
|
Block broken | 3
|
Drop item | 4
|
When the Status value is 4 (Drop item), the coordinates and Face are 0.
The face can be one of six values, representing the face being hit:
Value | 0 | 1 | 2 | 3 | 4 | 5 |
---|---|---|---|---|---|---|
Offset | -Y | +Y | -Z | +Z | -X | +X |
Player Block Placement (0x0F)
Sent when the player places a block or (probably) an item. The coordinates sent in this packet are actually the block being built against, which combined with the direction offset tell you where the block should be placed. This is required to correctly position furnaces, torches, etc…
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x0F | Block or Item ID | short | 1
|
The block or item to be placed |
X | int | 32
|
Block position | |
Y | byte | 64
|
Block position | |
Z | int | 32
|
Block position | |
Direction | byte | 3
|
The offset to use for block/item placement (see below) | |
Total Size: | 13 bytes |
The direction can be one of six values, representing the face the block/item is being placed against:
Value | 0 | 1 | 2 | 3 | 4 | 5 |
---|---|---|---|---|---|---|
Offset | -Y | +Y | -Z | +Z | -X | +X |
This packet has a special case where X, Y, Z, and Direction are all -1. This special packet indicates that the currently held item for the player should have its state updated.
The block or item ID corresponds to whatever the client is currently holding, and the Alpha client sends one of these packets any time a right-click is issued on a surface, so no assumptions can be made about the safety of the ID.
Holding Change (0x10)
Sent when the player changes the item or block currently being held.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x10 | Block or Item ID | short | 1
|
The block/item to be equipped |
Total Size: | 7 bytes |
Animation (0x12)
Sent whenever an entity should change animation.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x12 | EID | int | 55534
|
Player ID |
Animate | byte | 1
|
Can be 0 (no animation), 1 (swing arm) or 2 (death animation?). Getting 102 somewhat often, too.
| |
Total Size: | 6 bytes |
Named Entity Spawn (0x14)
The only named entities (at the moment) are players (either real or NPC/Bot). This packet is sent by the server when a player comes into visible range, not when a player joins.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x14 | EID | int | 94453
|
Player ID |
Player Name | string | Twdtwd
|
||
X | int | 784
|
Player X as Absolute Integer | |
Y | int | 2131
|
Player Y as Absolute Integer | |
Z | int | -752
|
Player Z as Absolute Integer | |
Rotation | byte | 0
|
Player rotation as a packed byte | |
Pitch | byte | 0
|
Player rotation as a packed byte | |
Current Item | short | 0
|
The item the player is currently holding | |
Total Size: | 23 bytes + length of strings |
Pickup Spawn (0x15)
A pickup spawn is sent by the server whenever an item on the ground (say a pickaxe thrown on the ground) comes into range of the player. It is also sent by the client when an item is dropped from a tile (chest or furnace) or from inventory.
It is completely acceptable for servers to ignore the EID issued by the client in this packet and instead create a new packet with a server-controlled EID when sending this packet out to clients.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x15 | EID | int | 157617
|
Unique entity ID |
Item | short | 4
|
The item ID | |
Count | byte | 1
|
The number of items | |
X | int | 133
|
Item X as Absolute Integer | |
Y | int | 913
|
Item Y as Absolute Integer | |
Z | int | 63552
|
Item Z as Absolute Integer | |
Rotation | byte | 252
|
Item rotation as a packed byte | |
Pitch | byte | 25
|
Item pitch as a packed byte | |
Roll | byte | 12
|
Item roll as a packed byte | |
Total Size: | 23 bytes |
Collect Item (0x16)
Sent by the server when someone picks up an item lying on the ground - its sole purpose appears to be the animation of the item flying towards you. It doesn't destroy the entity in the client memory (0x1D does that), and it doesn't add it to your inventory (0x11 does that).
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x16 | Collected EID | int | 38
|
|
Collector EID | int | 20
|
||
Total Size: | 9 bytes |
Add Object/Vehicle (0x17)
Sent by the server when an Object/Vehicle is created.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x17 | EID | int | 62
|
Entity ID of the Object |
Type | byte | 11
|
The type of object (see below) | |
X | int | 16080
|
The Absolute Integer X Position of the object | |
Y | int | 2299
|
The Absolute Integer Y Position of the object | |
Z | int | 592
|
The Absolute Integer Z Position of the object | |
Total Size: | 18 bytes |
Object Types
Type ID | Type Name |
---|---|
1 | Boats |
10 | Minecart |
11 | Storage Cart |
12 | Powered Cart |
Mob Spawn (0x18)
Sent by the server when a Mob Entity is Spawned
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x18 | EID | int | 446
|
Entity ID |
Type | byte | 91
|
The type of Mob Entity Type | |
X | int | 13366
|
The Absolute Integer X Position of the object | |
Y | int | 2176
|
The Absolute Integer Y Position of the object | |
Z | int | 1680
|
The Absolute Integer Z Position of the object | |
Yaw | byte | -27
|
The X Axis rotation as a fraction of 360 | |
Pitch | byte | 0
|
The Y Axis rotation as a fraction of 360 | |
Total Size: | 20 bytes |
Mob Types (Incomplete)
Type ID | Type Name |
---|---|
90 | Pig |
91 | Sheep |
92 | Cow |
93 | Hen |
Entity Velocity? (0x1C)
This packet is new to version 4 of the protocol, and is believed to be Entity Velocity/Motion.
Velocity is believed to in block velocity * 32000 with regards to the speed being server ticks, 200ms
e.g. -1343 would move (-1343 / 32000) = -0.04196875 blocks per tick (or -0.20984375 blocks per second)
Each axis Velocity is capped between -0.9 and 0.9 blocks per tick (Velocity -28800 to 28800)
(This packet data values are not fully verified)
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x1C | Entity ID | int | 1805
|
The entity ID |
Velocity X | short | -1343
|
Velocity on the X axis | |
Velocity Y | short | 0
|
Velocity on the Y axis | |
Velocity Z | short | 0
|
Velocity on the Z axis | |
Total Size: | 11 bytes |
Destroy Entity (0x1D)
Sent by the server when an Entity is to be destroyed on the client.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x1D | EID | int | 446
|
Entity ID |
Total Size: | 5 bytes |
Entity (0x1E)
Most entity-related packets are subclasses of this packet. When sent from the server to the client, it may initialize the entry.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x1E | EID | int | 446
|
Entity ID |
Total Size: | 5 bytes |
Entity Relative Move (0x1F)
This packet is sent by the server when an entity moves less then 4 blocks, if an entity moves more then 4 blocks Entity Teleport should be sent instead.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x1F | EID | int | 459
|
Entity ID |
X | byte | 1
|
X axis Relative movement as an Absolute Integer | |
Y | byte | -7
|
Y axis Relative movement as an Absolute Integer | |
Z | byte | 5
|
Z axis Relative movement as an Absolute Integer | |
Total Size: | 8 bytes |
Entity Look (0x20)
This packet is sent by the server when an entity rotates.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x20 | EID | int | 459
|
Entity ID |
Yaw | byte | 126
|
The X Axis rotation as a fraction of 360 | |
Pitch | byte | 0
|
The Y Axis rotation as a fraction of 360 | |
Total Size: | 7 bytes |
Entity Look and Relative Move (0x21)
This packet is sent by the server when an entity rotates and moves.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x21 | EID | int | 459
|
Entity ID |
X | byte | 1
|
X axis Relative movement as an Absolute Integer | |
Y | byte | -7
|
Y axis Relative movement as an Absolute Integer | |
Z | byte | 5
|
Z axis Relative movement as an Absolute Integer | |
Yaw | byte | 126
|
The X Axis rotation as a fraction of 360 | |
Pitch | byte | 0
|
The Y Axis rotation as a fraction of 360 | |
Total Size: | 10 bytes |
Entity Teleport (0x22)
This packet is sent by the server when an entity moves more then 4 blocks.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x22 | EID | int | 459
|
Entity ID |
X | int | 14162
|
X axis position as an Absolute Integer | |
Y | int | 2176
|
Y axis position as an Absolute Integer | |
Z | int | 1111
|
Z axis position as an Absolute Integer | |
Yaw | byte | 126
|
The X Axis rotation as a fraction of 360 | |
Pitch | byte | 0
|
The Y Axis rotation as a fraction of 360 | |
Total Size: | 19 bytes |
Entity Status? (0x26)
This command is not fully understood.
This packet is new in version 6 of the protocol, and is believed to be indication of entity damage, death and explosion
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x26 | Entity ID | Int | 34353 | |
Entity Status? | Byte | 0x03 | Possible values: 2, 3 (entity dead?), 4, 5 | |
Total Size: | 6 bytes |
Attach Entity? (0x27)
This packet is new to version 4 of the protocol, and is believed to be Attach Entity.
This packet is sent when a player has been attached to an entity (e.g. Minecart)
(This packet data values are not fully verified)
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x27 | Entity ID | int | 1298
|
The player entity ID being attached |
Vehicle ID | int | 1805
|
The vehicle entity ID attached to (-1 for unattaching) | |
Total Size: | 9 bytes |
Pre-Chunk (0x32)
This packet is sent by the server to notify the client to initialize (Mode=1) or unload (Mode=0) a chunk. The client is expected to allocate space for a full chunk (currently 16 x 128 x 16 blocks). One or more 0x33 packets will follow, specifying actual data to fill the chunk with.
Whenever you send this packet the client will clear any previous chunk at that spot if one has previously been sent. Clients don't like being in or next to an unloaded chunk, so try not to unload it if players are nearby. If the player appears to be twitching and stuck in place after joining the world, there is probably an unloaded chunk too close to them.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x32 | X | int | -9
|
Chunk X Coordinate |
Z | int | 12
|
Chunk Z Coordinate | |
Mode | bool | 1
|
If mode is 0 the client will unload the chunk, otherwise the client will initialize the chunk | |
Total Size: | 10 bytes |
Map Chunk (0x33)
The client will overwrite all or part of a chunk using the region of data contained in this packet. The server specifies the region to write using a block position and size in X,Y,Z. Note that this region will always be inside a single chunk. (At least using the vanilla server. Unknown if the client has this limitation.)
A server can send a 0x32 packet prior, allowing the client to initialize the chunk. However this doesn't always happen in practice. Thus the client should initialize the chunk on-demand.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x33 | X | int | 128
|
Block X Coordinate |
Y | short | 0
|
Block Y Coordinate | |
Z | int | -192
|
Block Z Coordinate | |
Size_X | byte | 15
|
Size_X is Actual X Size -1 | |
Size_Y | byte | 127
|
Size_Y is Actual Y Size -1 | |
Size_Z | byte | 15
|
Size_Z is Actual Z Size -1 | |
Compressed size | int | 3663
|
Size of compressed region data | |
Compressed data | byte array | …
|
The region data is compressed using ZLib Deflate function. | |
Total Size: | 18 bytes + Compressed chunk size |
X, Y, Z
This is the start position of the region, in world block coordinates.
To find which chunk is affected, in the same coordinates given by packet 0x32:
ChunkX = X >> 4 ChunkY = Y >> 7 ChunkZ = Z >> 4
And conversely, which local block in the chunk to start at:
StartX = X & 15 StartY = Y & 127 (not always 0!) StartZ = Z & 15
SizeX, SizeY, SizeZ
This is the size of the region, in blocks. The server will subtract one from the sizes and then cast them to a byte before sending. This is so that chunks as large as 256 are possible (the maximum size of a byte is 255; 256 - 1 = 255).
Compressed data
The data is compressed using the deflate() function in zlib. After uncompressing, the data consists of four sections, in order:
- Block type array (1 byte per block)
- Block metadata array (half byte/nibble per block)
- Block Light array (half byte/nibble per block)
- Sky Light array (half byte/nibble per block)
The data is exactly (Size_X+1) * (Size_Y+1) * (Size_Z+1) * 2.5
bytes long.
In other words, there are Size_X number of x planes, each plane made up of Size_Z number of z rows, each row made up of Size_Y blocks indexed by y coordinate in order.
The block type array is indexed with:
index = y + (z * (Size_Y+1)) + (x * (Size_Y+1) * (Size_Z+1))
The other arrays are similar but you need to divide the index by two after calculating the above. Then each byte contains data for two blocks.
Multi Block Change (0x34)
Further investigation shows that this is a multiple-block-change command; if you take the three arrays, and put together elements with the same index, and then decompose the short into coordinates (top 4 bits is X, next 4 bits is Z, bottom 8 bits is Y), you get things like [((8, 7, 4), 11, 0), ((7, 13, 6), 11, 0), ((13, 1, 8), 11, 0), ((7, 6, 6), 11, 0)].
See the Block Change command for description of the general format of a block change.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x34 | Chunk X | int | -9
|
Chunk X Coordinate |
Chunk Z | int | 12
|
Chunk Z Coordinate | |
Array size | short | 2
|
The total number of elements per array | |
Coordinate array | short array | …
|
The coordinates of the blocks to change | |
Type array | byte array | …
|
The type for each block change | |
Metadata array | byte array | …
|
The Metadata for each block changed | |
Total Size: | 11 bytes + Arrays |
Block Change (0x35)
Block metadata varies by block type - it should be 0x00
for most blocks with a few exceptions, shown in the table below.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x35 | X | int | 502
|
Block X Coordinate |
Y | byte | 71
|
Block Y Coordinate | |
Z | int | 18
|
Block Z Coordinate | |
Block Type | byte | 78
|
The new block type for the block | |
Block Metadata | byte | 0
|
The new Metadata for the block | |
Total Size: | 12 bytes |
Explosion (0x3C)
This command is not fully understood.
Seems to be sent when an explosion occurs (both creepers and TNT).
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x3C | X | double | ||
Y | double | |||
Z | double | |||
Unknown | float | 3.0 | radius? | |
Record count | int | This is the count, not the size. The size is 3 times this value. | ||
Records | byte array | Each record is 3 bytes, which seem to be XYZ offsets of affected blocks. | ||
Total Size: | 33 bytes + 3*(Record count) bytes |
Open Inventory (0x64)
This command is not fully understood.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x64 | Inventory ID | byte | 123 | ID which identifies this opened inventory |
Inventory Type | byte | 2 | Check below | |
Inventory Name | string | Chest
|
Name shown in the open inventory | |
Number of Slots | byte | 54 | Number of slots in the opening inventory screen (multiple of 9) | |
Total Size: | 4 bytes + 1 string |
Inventory types: 0 = basic, 1 = crafting table, 2 = furnace
Inventory Close (0x65)
This packet is sent by the client when closing inventory screen.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x65 | Inventory ID | byte | 0 | this is the inventory ID the player closes (or server wants player to close?) |
Total Size: | 2 bytes |
Inventory Click (0x66)
This command is not fully understood.
This packet is sent by the player when it clicks on a slot in the inventory
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x66 | Inventory ID | byte | 0
|
0 for player inventory |
Slot ID | short | 36
|
ID of clicked slot | |
Right-click? | byte | 1
|
Seems to be 1 when rightclicking and otherwise 0 | |
Num clicks | short | 12
|
Number of total inventory clicks | |
Item ID | short | 3
|
ID of Item that was in the slot | |
Item count | byte | 64
|
Number of items that were in the slot | |
Item uses | byte | 10
|
Number of times the item was used that was in the slot | |
Total Size: | 9 bytes (+2 for item ID != -1) |
Inventory Update (0x67)
This command is not fully understood.
Sent by the server when adding/removing item to/from inventory
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x67 | Inventory ID | byte | 0
|
0 for player inventory |
Slot ID | short | 36
|
ID of clicked slot | |
Item ID | short | -1
|
When -1, this is the last value in this packet | |
Item Count | byte | 64
|
Number of items in a stack | |
Item uses | byte | 3
|
||
Total Size: | 6 bytes (+2 for item ID != -1) |
Slots: [1]
??? (0x69)
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x69 | ??? | byte | ||
??? | short | |||
??? | short | |||
Total Size: | 6 bytes |
??? (0x6A)
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x6A | ??? | byte | ||
??? | short | |||
??? | boolean | |||
Total Size: | 5 bytes |
Update Sign (0x82)
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0x82 | X | int | 128 | Block X Coordinate |
Y | short | 0 | Block Y Coordinate | |
Z | int | -128 | Block Z Coordinate | |
Text1 | string | First line
|
First line of text in the sign | |
Text2 | string | Second line
|
Second line of text in the sign | |
Text3 | string | Third line
|
Third line of text in the sign | |
Text4 | string | Fourth line
|
Fourth line of text in the sign | |
Total Size: | 11 bytes + 4 strings |
Disconnect/Kick (0xFF)
Sent by the server before it disconnects a client, or by the client before it disconnects from the server. The receiver of this packet assumes that the sender has already closed the connection by the time the packet arrives.
Packet ID | Field Name | Field Type | Example | Notes |
---|---|---|---|---|
0xFF | Reason | string | The server is full!
|
Displayed to the client when the connection terminates |
Total Size: | 3 bytes + length of strings |
Protocol History
Provided below is a changelog of the server protocol starting on 2010-08-20. The wiki history feature may also be used to investigate changes.
2010-12-20
- Notch released Beta on time! Amazing! Refactored the page to be slightly smaller and easier to navigate.
- A whole host of packet changes. 0x08, 0x10, 0x11, 0x3b, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6a, and 0x82.
2010-12-01
- Protocol version changed to 6
- Packet 0x12 (Animation) got a lot more new values
- Packet 0x26 changed, now indicates entity damage, death and explosion (for creepers, TNT not tested)
- Packet 0x3B now being sent from client
- Packet 0x3C added
- (need info on other changes)
2010-11-24
- Protocol version changed to 5
- Packet 0x07 (Use Entity) got a new field (byte)
- Packet 0x08 (Update Health) added
- Packet 0x09 (Respawn) added
- Packet 0x12 (Animation) started getting non-boolean values for the Animation field
- Packet 0x26 (Entity Death) added
2010-11-10
- Protocol version changed to 4
- Packet 0x01 (login request) changed
- Packet 0x07 (Use Entity?) added
- Packet 0x1C (Entity Velocity?) added
- Packet 0x27 (Attach Entity?) added
2010-10-31
- Protocol version changed to 3
- Packet 0x01 (login request) changed
2010-09-10
- Protocol version changed to 2
- Packets 0x05, 0x06, 0x3B added
- Server-side inventory (no verification)
- Vanilla adds experimental monsters (only damaged by fire)
2010-08-20
- Protocol version reset from 14 to 1
- Packet 0x04 (time update) added