Skip to content

DarqlineMP Protocol ​

DarqlineMP runs over UDP. Every multi-byte value is little-endian, and every packet starts with packet_id: u8. The current wire revision is PROTOCOL_VERSION = 146 (u16). The server compares it only during the handshake, by strict equality: a ClientHello with any other revision gets no answer. The revision is unrelated to the release versions of the client and the server; those are not sent on the wire and do not decide compatibility. The envelope (revision check, per-connection session token, stale-packet protection and strict validation) is set out in ADR 0004.

This specification describes only the current format.

Golden examples of every packet live in ../fixtures/protocol/, one .bin file per packet (a few packets have extra variants). The server's codec writes them and its tests check that encoding still produces the same bytes; every other implementation can check itself against the same files. Each packet section links its examples.

Pages ​

  • Connection: handshake, server query, player IDs, disconnect, acks and keepalive, authentication.
  • Player: the player's own state and its relay, streaming, spawn and death, and the server-applied player state.
  • Combat: shots, projectiles, damage, health and armor, weapons, explosions and fire.
  • Vehicles: vehicle state relay, seats, damage, attachments, trains and the server-applied vehicle state.
  • World: pickups, clock and weather, garage doors, world markers, colshapes, objects and waypoints.
  • Chat, HUD and dialogs: chat and commands, nametags, the player list, actions, dialogs, menus, offers and HUD elements.
  • Resource files and views: resource client files and resource views.
  • Map editing: the in-game map editor.

Packet IDs ​

IDNameDirectionPage
0x01ClientHelloClient → ServerConnection
0x02ServerHelloServer → ClientConnection
0x03PlayerSyncClient → ServerPlayer
0x04RemotePlayerSyncServer → ClientPlayer
0x05ClientByeClient → ServerConnection
0x06PlayerLeaveServer → ClientConnection
0x07ClientChatClient → ServerChat, HUD and dialogs
0x08ChatMessageServer → ClientChat, HUD and dialogs
0x09WeaponShotClient → ServerCombat
0x0ARemoteWeaponShotServer → ClientCombat
0x0BDamageReportClient → ServerCombat
0x0CRespawnRequestClient → ServerPlayer
0x0DRespawnPlayerServer → ClientPlayer
0x0EClientAckClient → ServerConnection
0x0FServerAckServer → ClientConnection
0x10PlayerSkillsServer → ClientPlayer
0x11SetWantedServer → ClientPlayer
0x12PickupSyncServer → ClientWorld
0x13PickupTouchClient → ServerWorld
0x14KickNotifyServer → ClientConnection
0x15TeleportPlayerServer → ClientPlayer
0x16GiveWeaponServer → ClientCombat
0x17GiveHealthServer → ClientCombat
0x18GiveArmorServer → ClientCombat
0x19ClientCommandClient → ServerChat, HUD and dialogs
0x1AServerMessageServer → ClientChat, HUD and dialogs
0x1BDeathReportClient → ServerPlayer
0x1CPlayerWastedServer → ClientPlayer
0x1DPlayerSpawnedServer → ClientPlayer
0x1ESetHealthServer → ClientCombat
0x1FSetArmorServer → ClientCombat
0x20SetSkinServer → ClientPlayer
0x21SetTimeServer → ClientWorld
0x22SetWeatherServer → ClientWorld
0x23RunClockServer → ClientWorld
0x24TakeWeaponServer → ClientCombat
0x25SetWeaponAmmoServer → ClientCombat
0x26ClearWeaponsServer → ClientCombat
0x27SetArmedWeaponServer → ClientCombat
0x28SetMoneyServer → ClientPlayer
0x29RequestSpawnClient → ServerPlayer
0x2ASpawnPlayerServer → ClientPlayer
0x2BApplyAnimationServer → ClientPlayer
0x2CClearAnimationsServer → ClientPlayer
0x2DSetWalkingStyleServer → ClientPlayer
0x2ESetAnimationProgressServer → ClientPlayer
0x2FSetAnimationSpeedServer → ClientPlayer
0x30ProjectileCreateClient → ServerCombat
0x31RemoteProjectileCreateServer → ClientCombat
0x32SatchelDetonateClient → ServerCombat
0x33RemoteSatchelDetonateServer → ClientCombat
0x34StealthKillRequestClient → ServerCombat
0x35RemoteStealthKillServer → ClientCombat
0x36VehicleSyncServer → ClientVehicles
0x37VehicleEnterClient → ServerVehicles
0x38VehicleExitClient → ServerVehicles
0x39VehicleOccupancyServer → ClientVehicles
0x3AVehicleFrameClient → ServerVehicles
0x3BRemoteVehicleFrameServer → ClientVehicles
0x3CVehicleSyncerServer → ClientVehicles
0x3DVehicleExplodeClient → ServerVehicles
0x3EVehicleDeathServer → ClientVehicles
0x3FVehicleDamageClient → ServerVehicles
0x40RemoteVehicleDamageServer → ClientVehicles
0x41VehicleHealthServer → ClientVehicles
0x42VehicleParamsServer → ClientVehicles
0x43VehicleControlClient → ServerVehicles
0x44LethalDamageReportClient → ServerCombat
0x45PlayerStreamOutServer → ClientPlayer
0x46DriveByIntervalsServer → ClientCombat
0x47VehicleShotClient → ServerVehicles
0x48RemoteVehicleShotServer → ClientVehicles
0x49VehicleTowClient → ServerVehicles
0x4AVehicleTrailerServer → ClientVehicles
0x4BTrainStateServer → ClientVehicles
0x4CVehicleRemoteServer → ClientVehicles
0x4DVehicleRemoteExitClient → ServerVehicles
0x4EVehicleRemoteEnterClient → ServerVehicles
0x4FVehicleWinchClient → ServerVehicles
0x50VehicleLiftServer → ClientVehicles
0x51GarageDoorsServer → ClientWorld
0x52VehicleTuningServer → ClientVehicles
0x53VehicleHandlingServer → ClientVehicles
0x54VehicleTransformServer → ClientVehicles
0x55VehicleColorsServer → ClientVehicles
0x56SetFightingStyleServer → ClientPlayer
0x57SetHeadlessServer → ClientPlayer
0x58SetOnFireServer → ClientPlayer
0x59SetSpecialActionServer → ClientPlayer
0x5ACreateExplosionServer → ClientCombat
0x5BDetonateSatchelsServer → ClientCombat
0x5CDestroySatchelsServer → ClientCombat
0x5DScopeChangedServer → ClientPlayer
0x5ECreateFireServer → ClientCombat
0x5FExtinguishFireServer → ClientCombat
0x60WeaponPropertiesServer → ClientCombat
0x61UiThemeServer → ClientChat, HUD and dialogs
0x62PlatformKeysServer → ClientChat, HUD and dialogs
0x63ActionDeclareServer → ClientChat, HUD and dialogs
0x64ActionRemoveServer → ClientChat, HUD and dialogs
0x65ActionInputClient → ServerChat, HUD and dialogs
0x66Label3DServer → ClientWorld
0x67CheckpointServer → ClientWorld
0x68BlipServer → ClientWorld
0x69DialogShowServer → ClientChat, HUD and dialogs
0x6ADialogHideServer → ClientChat, HUD and dialogs
0x6BDialogResponseClient → ServerChat, HUD and dialogs
0x6CHudAnnouncementServer → ClientChat, HUD and dialogs
0x6DHudCountdownServer → ClientChat, HUD and dialogs
0x6EHudStatusLineServer → ClientChat, HUD and dialogs
0x6FHudKillFeedAddServer → ClientChat, HUD and dialogs
0x70HudKillFeedClearServer → ClientChat, HUD and dialogs
0x71GangZoneServer → ClientWorld
0x72SetFrozenServer → ClientPlayer
0x73SetCameraServer → ClientPlayer
0x74PlayerNametagServer → ClientChat, HUD and dialogs
0x75PlayerListEntryServer → ClientChat, HUD and dialogs
0x76ConnectRejectServer → ClientConnection
0x77DialogTableRowsServer → ClientChat, HUD and dialogs
0x78DialogTableServer → ClientChat, HUD and dialogs
0x79ActionPromptServer → ClientChat, HUD and dialogs
0x7AHudProgressServer → ClientChat, HUD and dialogs
0x7BHudNotificationAddServer → ClientChat, HUD and dialogs
0x7CHudNotificationClearServer → ClientChat, HUD and dialogs
0x7DDialogFormServer → ClientChat, HUD and dialogs
0x7EDialogFormResponseClient → ServerChat, HUD and dialogs
0x7FMenuItemsServer → ClientChat, HUD and dialogs
0x80MenuShowServer → ClientChat, HUD and dialogs
0x81MenuHideServer → ClientChat, HUD and dialogs
0x82MenuInputClient → ServerChat, HUD and dialogs
0x83OfferShowServer → ClientChat, HUD and dialogs
0x84OfferHideServer → ClientChat, HUD and dialogs
0x85OfferResponseClient → ServerChat, HUD and dialogs
0x86ObjectiveMarkerServer → ClientChat, HUD and dialogs
0x87HudGaugeServer → ClientChat, HUD and dialogs
0x88HudSpeedometerServer → ClientChat, HUD and dialogs
0x89PlayerChatBubbleServer → ClientChat, HUD and dialogs
0x8AObjectStateServer → ClientWorld
0x8BConnectChallengeServer → ClientConnection
0x8CServerKeepaliveServer → ClientConnection
0x8DEntityEditClient → ServerMap editing
0x8EEditCameraClient → ServerMap editing
0x8FEditStateServer → ClientMap editing
0x90SetVelocityServer → ClientPlayer
0x91SetGravityServer → ClientPlayer
0x92SetDrunkLevelServer → ClientPlayer
0x93SetPlayerStatsServer → ClientPlayer
0x94SetWorldBoundsServer → ClientPlayer
0x95ColshapeShapeServer → ClientWorld
0x96ResourceFilesServer → ClientResource files and views
0x97ResourceRemoveServer → ClientResource files and views
0x98ViewOpenServer → ClientResource files and views
0x99ViewCloseServer → ClientResource files and views
0x9AViewDataServer → ClientResource files and views
0x9BViewStatusClient → ServerResource files and views
0x9CViewActionClient → ServerResource files and views
0x9DPlayerWaypointClient → ServerWorld
0x9ESetWaypointServer → ClientWorld
0x9FClientPongClient → ServerConnection
0xA0DamageMultipliersServer → ClientCombat
0xA1AuthAcceptedServer → ClientConnection
0xA2AuthAssertionClient → ServerConnection
0xFFServer queryBoth directionsConnection

0xFF is outside the revision: the server query keeps its own frozen format, so a launcher of any revision can read it.

Reliable event lane ​

Discrete events travel on the reliable event lane (ADR 0007); a packet is on the lane when its layout carries event_id: u32. Continuous state (PlayerSync, RemotePlayerSync and the other frame packets) stays unreliable and latest-wins and does not use the lane.

Each connection has one stream per direction. All reliable packets of that direction share the stream and are ordered by its event_id. The scheme is Go-Back-N with a cumulative ack: ClientAck acknowledges the Server → Client stream, ServerAck the Client → Server stream.

  • event_id is a 1-based, monotonic position in the stream and starts again at 1 on every connection. Events therefore need no generation tag: the session token on Client → Server packets and the per-connection streams keep a reconnect or a reused player_id apart from the previous connection.
  • Receiver. It delivers only the next expected event_id. A duplicate (< expected) or an event ahead of a gap (> expected) is discarded unapplied. Every reliable packet it receives, delivered or not, is answered with an ack that carries the highest event_id delivered without a gap. Re-acking a duplicate repairs a lost ack; a gap holds the ack in place, so the sender resends from the gap.
  • Sender. It assigns event_id, keeps each event until it is acked, and resends an event once its age since the last send reaches the RTO of 250 ms (fixed, not adapted to the round trip). An ack removes every pending event with event_id <= ack. There is no per-event give-up; a dead peer is removed by the disconnect rules.
  • Resend timing on the server. The server checks for due resends every 100 ms, so a lost event goes out again 250–350 ms after its last send. Per connection and check it resends at most 32 due events, oldest first.
  • No gaps. A sender that refuses to queue an event does not consume an event_id for it, so the stream never has a gap.
  • Server queue limits. With 256 unacked events on a connection, the server drops new droppable events (such as chat, skills, pickups and wanted level) instead of queueing them, without disconnecting. Events that must not be lost (such as lifecycle edges, satchel detonation and the clock) are still queued up to 512 unacked; reaching 512 disconnects the client. The server also disconnects a client whose unacked events have waited 15 s without an ack moving the queue, even if other packets keep the connection alive.

Sequence and generation ​

Continuous state needs protection against UDP reordering and against a player_id that is reused by a new player. RemotePlayerSync carries the subject's player_token (its generation) and a seq. Tokens come from one server-wide counter, so they are monotonic: a later generation of any player_id has a larger token. Other Server → Client packets about a player carry its player_token too, so a delayed packet cannot resurrect a reused player_id.

The receiver keeps per player_id:

  • gen: the player_token of the live generation;
  • last_seq: the last applied seq of that generation;
  • a tombstone: the player_token of the generation that has just left.

Rules:

  • RemotePlayerSync(id, token, seq). A packet whose token equals the tombstone is dropped: a departed player is not resurrected. With a live generation, token == gen applies the packet only if seq is newer than last_seq in serial-number arithmetic (the wrapping u32 difference, read as i32, is positive); token > gen is a new generation (the id was reused, possibly with its PlayerLeave lost) and is adopted; token < gen is a straggler of an earlier owner and is dropped. With no live generation the packet is adopted (gen = token, last_seq = seq).
  • PlayerLeave(id, token). The receiver removes the remote player only when token == gen and ignores the packet otherwise. After the removal the tombstone holds that generation, so delayed packets of it are dropped; adopting a new generation clears the tombstone.

Because tokens are monotonic, a reordered packet older than the live generation never replaces it. The tombstone covers only the most recent departed generation: a straggler of an earlier one that arrives while the id has no live generation is adopted, and the next owner's larger token replaces it.

PlayerStreamOut removes a remote player from view but keeps its generation; the last_seq it carries stops stragglers from showing the player again, and a newer frame shows it again.

Strict decoding ​

Both sides decode strictly: a malformed packet is dropped whole, never partially applied.

  • Exact length. A packet must be exactly as long as its layout: a fixed-size packet exactly its size, a packet with a variable part exactly the length its count and length fields give. A short packet or one with trailing bytes is dropped.
  • Finite floats. A Frame (PlayerSync, RemotePlayerSync) with any non-finite f32 (NaN or infinity) is dropped, and so is a VehicleState (VehicleFrame, RemoteVehicleFrame). Other packets state their float checks in their own sections.
  • Unknown or empty. An unknown packet_id or an empty datagram is dropped. A revision mismatch is refused at the handshake, as described above.

Documentation licensed under CC BY 4.0. DarqlineMP is not affiliated with Rockstar Games or Take-Two Interactive. Grand Theft Auto is a trademark of Take-Two Interactive Software, Inc.