Tukar paket biner sendiri antara client mod dan server.
SA-MP menyisakan banyak id RPC yang tidak terpakai. Knight membiarkan gamemode mengambil id tersebut dan bertukar payload biner sendiri dengan client yang dimodifikasi. Engine memvalidasi frame, membatasi ukuran dan laju per pemain, lalu meneruskan payload ke handler Anda.
Id yang sudah dipakai protokol bawaan (mis. 101 chat, 25 ClientJoin, 50 ServerCommand) tidak bisa diambil; HandleCustomRPC mengembalikan false dan mencatat alasannya.
3. Objek RPC
Field
Tipe
Arti
rpc.id
int
Id RPC
rpc.playerid
int
Pemain pengirim
rpc.payload
string
Byte mentah
rpc.length
int
Panjang payload
rpc.reader
Reader
Pembaca biner dengan pemeriksaan batas
rpc.direction
string
"incoming" atau "outgoing"
rpc.is_valid
bool
False bila frame ditolak
4. Method Reader
Method
Byte
Catatan
read_int8() / read_uint8()
1
Bertanda / tak bertanda
read_int16() / read_uint16()
2
Little-endian
read_int32() / read_uint32()
4
Little-endian
read_float()
4
IEEE-754 float32
read_bool()
1
Bukan nol = true
read_string(n)
n
Byte mentah tanpa awalan panjang
remaining()
—
Sisa byte
valid()
—
False setelah pembacaan kurang
tell()
—
Offset saat ini
Note
Setiap pembacaan diperiksa batasnya. Payload pendek atau jahat menghasilkan nol, menandai valid() false, dan tidak pernah membuat server crash.
5. Membangun payload
knight
let payload =RPCPack("u8", 7, "u16", 300, "u32", 70000, "f32", 1.5, "s", "hi");
SendCustomRPC(playerid, 201, payload); // satu pemainSendCustomRPC(-1, 201, payload); // semua (broadcast)
Tag
Ukuran
u8
1 byte
u16
2 byte
u32 / i32
4 byte
f32
4 byte
s
byte string mentah
6. Client mana yang boleh mengirim
Dengan client_mod: true, hanya client yang menambahkan +knight-rpc pada version string ClientJoin yang diterima. Selain itu diabaikan diam-diam, jadi client 0.3.7 biasa tidak bisa memicu handler.
Frame di-parse engine; RPC rusak dibuang sebelum handler.
Payload melebihi max_size tidak pernah sampai ke handler.
Rate limit per pemain dan per id, dihitung per detik.
Reader tidak bisa membaca melewati payload dan tidak pernah panic.
Id RPC bawaan tidak bisa dibajak.
9. Banyak handler: HandleRPC
HandleCustomRPC memasang satu handler per id. HandleRPC memasang banyak: masing-masing punya priority dan filter payload opsional, dijalankan dari prioritas tertinggi, dan yang pertama cocok mengonsumsi paket. Bila tidak ada yang cocok, paket diabaikan.
Handler dan HandleCustomRPC hidup bersama: engine mencoba rantai HandleRPC dulu, lalu handler HandleCustomRPC untuk id yang sama.
10. Filter payload
Match
Benar bila
any
Payload diterima (default)
exact
Window yang diperiksa sama dengan bytes
prefix
Window diawali bytes
contains
bytes ada di mana pun dalam window
bytes
Sama seperti contains, untuk data biner
offset (default 0) dan length (default sampai akhir) menentukan window sebelum pencocokan. Nilai di luar batas tidak pernah cocok dan tidak membuat crash.
11. CheckRPC
CheckRPC(id, payload, options) adalah predikat murni: tidak mendaftarkan apa pun dan mengembalikan apakah id dan payload cocok dengan kriteria. Berguna di dalam handler untuk merutekan berdasarkan header, atau sebelum mengirim balasan.
Opsi
Arti
direction
Divalidasi agar simetris dengan HandleRPC
match
exact, contains, prefix, bytes, atau any
bytes
Byte yang dicari
offset
Awal window
length
Panjang window
playerid
Bila diisi (>= 0), pengirim harus terhubung
12. Mengelola handler
Fungsi
Hasil
Kegunaan
HandleRPC(id, handler, options)
bool
Tambah handler berprioritas
UnregisterRPC(id)
bool
Hapus semua entri HandleRPC untuk id
RPCHookCount(id)
int
Jumlah entri HandleRPC
Warning
Id protokol bawaan (chat, ClientJoin, ServerCommand, dialog, sync...) ditolak kedua API, jadi RPC internal tidak bisa dioverride.