[Tutorial] Sincronizaзгo no SA-MP.
#1

• Sincronizaзгo no SA-MP.
Conteъdo:
- Sincronizaзгo de dados;
- Funзхes Get*;
- Mundos virtuais e processo de "streaming";
- Pool interna de processamento de RPCs.
- Dessincronizaзгo.
• Sincronizaзгo de dados.
Todos os dados como posiзгo, arma atual e velocidade vem em pacotes. Ou mais precisamente no caso de UDP, datagramas. Cada datagrama contйm uma ou mais mensagens, podendo ser vida, posiзгo atual, entre outros.

Cada pacote й identificado pelos seus primeiros 8 bits (1 byte), que nesse caso й o seu identificador numйrico. Existem diferentes tipos de pacotes contendo diferentes mensagens/dados em si, sendo:

ID_PLAYER_SYNC (ID: 207) - Um pacote com este identificador numйrico й responsбvel por atualizaзхes a pй, dos jogadores. Este pacote sempre serб enviado APENAS se o jogador estiver a pй, e й enviado a cada um segundo se o jogador nгo estiver se movendo. A sua estrutura de dados й a seguinte:
  • lrKey - Seta para esquerda/direita (←→) - Se a tecla atual for seta para esquerda, entгo lrKey se iguala a KEY_LEFT, caso contrбrio KEY_RIGHT. 0 se nenhum dos casos.
  • udKey - Seta para cima/baixo (↑↓) - Se a tecla atual for seta para cima, entгo lrKey se iguala a KEY_UP, caso contrбrio KEY_DOWN. 0 se nenhum dos casos.
  • keys - Um mapa (bitmask) com as teclas pressionadas.
  • position[3] - Posiзгo atual (X, Y, Z).
  • quaternion[4] - Quaterniхes de rotaзгo (W, X, Y, Z).
  • health - Vida atual do jogador.
  • armour - Colete atual do jogador.
  • weaponId - Arma atual do jogador.
  • additionalKey - Tecla adicional.
  • specialAction - Aзгo especial.
  • velocity[3] - Velocidade nos eixos X, Y e Z.
  • surfingOffsets[3] - Offsets de surfing em um veнculo - 0.0 em todas as offsets se o jogador nгo estiver surfando um veнculo.
  • surfingVehicleId - O ID do veнculo que o jogador estб surfando (0 se nenhum).
  • animationId - ID da animaзгo atual.
  • animationFlags - Flags da animaзгo atual.
ID_VEHICLE_SYNC (ID: 200) - Um pacote com este identificador numйrico й responsбvel por atualizaзхes do jogador dentro de um veнculo (como motorista). A sua estrutura de dados й a seguinte:
  • vehicleId - ID de veнculo atual.
  • lrKey - Seta para esquerda/direita (←→) - Se a tecla atual for seta para esquerda, entгo lrKey se iguala a KEY_LEFT, caso contrбrio KEY_RIGHT. 0 se nenhum dos casos.
  • udKey - Seta para cima/baixo (↑↓) - Se a tecla atual for seta para cima, entгo lrKey se iguala a KEY_UP, caso contrбrio KEY_DOWN. 0 se nenhum dos casos.
  • keys - Um mapa (bitmask) com as teclas pressionadas.
  • quaternion[4] - Quaterniхes de rotaзгo do veнculo (W, X, Y, Z).
  • position[3] - Posiзгo atual (X, Y, Z)
  • velocity[3] - Velocidade nos eixos X, Y e Z.
  • vehicleHealth - Vida atual do veнculo.
  • playerHealth - Vida do jogador.
  • armour - Colete do jogador.
  • weaponId - Arma atual do jogador.
  • additionalKey - Tecla adicional.
  • sirenState - Estado da sirene do veнculo.
  • landingGearState - Estado do trem de pouso (dado tambйm utilizado por veнculos como empilhadeira para representar o estado do garfo/forquilha).
  • trailerId - ID de trailer anexado ao veнculo (0 se nenhum).
  • trainSpeed - Velocidade do trem (dado utilizado por trens).
ID_PASSENGER_SYNC (ID: 211) - Um pacote com este identificador numйrico й responsбvel por atualizaзхes do jogador dentro de um veнculo (como passageiro). A sua estrutura de dados й a seguinte:
  • vehicleId - ID de veнculo atual.
    seatId - Nъmero do assento atual.
    driveBy - 0 se o jogador nгo estiver em modo de drive-by, caso contrбrio 1.
    weaponId - ID de arma atual.
    additionalKey - Tecla adicional.
    playerHealth - Vida do jogador.
    playerArmour - Colete do jogador.
  • lrKey - Seta para esquerda/direita (←→) - Se a tecla atual for seta para esquerda, entгo lrKey se iguala a KEY_LEFT, caso contrбrio KEY_RIGHT. 0 se nenhum dos casos.
  • udKey - Seta para cima/baixo (↑↓) - Se a tecla atual for seta para cima, entгo lrKey se iguala a KEY_UP, caso contrбrio KEY_DOWN. 0 se nenhum dos casos.
  • keys - Um mapa (bitmask) com as teclas pressionadas.
    position[3] - Posiзгo atual do jogador (X, Y, Z).
ID_AIM_SYNC (ID: 203) - Um pacote com este identificador numйrico й responsбvel por atualizaзхes relacionadas com a cвmera/mira do jogador. A sua estrutura de dados й a seguinte:
ID_BULLET_SYNC (ID: 206) - Um pacote com este identificador numйrico й responsбvel por atualizaзхes de tiros/balas disparados por um jogador. A sua estrutura de dados й a seguinte:
  • hitType - Tipo de acerto: https://sampwiki.blast.hk/wiki/BulletHitTypes
  • hitId - ID do veнculo, objeto ou jogador que levou o tiro.
  • origin[3] - Origem da bala.
  • hitPos[3] - Posiзгo de acerto.
  • offsets[3] - offsets da bala.
  • weaponId - ID da arma que a bala pertence.
ID_TRAILER_SYNC (ID: 210) - Um pacote com este identificador numйrico й responsбvel por atualizaзхes de trailers anexados a veнculos sendo utilizados por jogadores. A sua estrutura de dados й a seguinte:
  • trailerId - ID do trailer anexado.
  • position[3] - Posiзгo atual (X, Y, Z).
  • quaternion[4] - Quaterniхes de rotaзгo do trailer (W, X, Y, Z).
  • velocity[3] - Velocidade nos eixos X, Y e Z.
  • angularVelocity[3] - Velocidade angular.
ID_WEAPONS_UPDATE (ID: 204) - Um pacote com este identificador numйrico й responsбvel por atualizaзхes de balas e armas em todas as slots. A sua estrutura de dados й a seguinte:
  • slot[12] - Slot.
  • arma0[12] - ID da arma.
  • balas0[12] - Quantidade de balas.
ID_RCON_COMMAND (ID: 201) - Um pacote com este identificador numйrico й responsбvel por mandar tentativas de comandos rcon para o servidor. Todos os comandos rcons sгo mandados por esse pacote, atй mesmo tentativas de login. A sua estrutura de dados й a seguinte:
  • text_length - UINT32 com a quantidade de cйlulas do texto do comando.
  • cmdtext - Texto do comando.
• Funзхes Get*.
Funзхes Get* (como GetPlayerWeapon) retornam valores que o servidor jб tem, sem nenhuma operaзгo I/O. Esses valores sгo contidos nos dados dos pacotes de sincronizaзгo que jogadores enviam para o servidor. Assim que recebidos os dados, os valores sгo escritos em variбveis nas estruturas internas do servidor em CPlayerPool, assim, a funзгo retornarб o valor jб presente em uma das variбveis nas estruturas internas.

Apуs um pacote de sincronizaзгo chegar no servidor e ter seus dados escritos nas estruturas internas, a callback OnPlayerUpdate й chamada. O valor retornado na callback OnPlayerUpdate determina se os dados recebidos pelo servidor vгo ser transmitidos com outros jogadores ou nгo, nesse caso retornando 1 permite que os dados sejam transmitidos com outros jogadores apуs terem sidos salvos nas estruturas internas do servidor, e retornando 0 impedirб a transmissгo desses dados.
• Mundos virtuais e processo de "streaming".
O servidor controla aquilo que serб transmitido com o cliente. Outros jogadorйs sу vгo ser criados se vocк estiver a uma certa distвncia de suas posiзхes atuais e se o mundo virtual for o mesmo, resultando no processo de stream-in com outros clientes.

No processo de stream-in com jogadores, o servidor manda a chamada de procedimento remуto (RPC - Remote Procedure Call) WorldPlayerAdd para seu cliente, criando os outros jogadores em seu cliente e entгo permitindo que vocк receba dados de sincronizaзгo desses outros clientes. O mesmo serve para veнculos e objetos, o processo de stream-in ocorre quando vocк chega na distвncia necessбria (geralmente uma distвncia menor que 200.0 no plano X, Y - O valor pode variar, depende de como vocк definiu stream_distance em server.cfg, mas por padrгo й 200.0) e se estiver no mesmo mundo virtual.

Chegando a uma distвncia superior а stream_distance, os jogadores/veнculos/objetos sofrem stream-out, em que sгo removidos do seu cliente, logo esses jogadores nгo teram dados de sincronizaзгo mandados para vocк.

O cliente nгo controla aquilo que serб transmitido consigo mesmo, o servidor й responsбvel por isso baseado em fatores como posiзгo e mundo virtual. O cliente pode chegar ao ponto de modificar a posiзгo resultando no servidor em fazer o processo de stream-in/out, mas, o cliente nunca poderб alterar o mundo virtual, que й totalmente controlado pelo servidor.

No momento que o mundo virtual muda, todo jogador/objeto/carro que estб prуximo de vocк e dentro da distвncia de streaming e nгo pertencer ao seu mundo virtual, sofrerб o processo de stream-out, e aquilo que ainda nгo foi transmitido nгo serб. Vocк estarб limitado a outros jogadores/veнculos/objetos que estejam no seu mesmo mundo virtual.
• Pool interna de processamento de RPCs.
Chamadas de procedimento remoto (RPCs - Remote Procedure Calls) tem o objetivo de executar funзхes internas no cliente. Quando vocк muda a aзгo especial de um jogador com a funзгo SetPlayerSpecialAction, o RPC 88 й mandado para o cliente, tendo o ID da aзгo especial como parвmetro, e logo uma funзгo interna й chamada no cliente e a aзгo especial muda de acordo com a providenciada na chamada de procedimento remуto.

Antes de uma chamada de procedimento remуto ser enviada, o servidor verifica se o cliente estб mandando atualizaзхes para se certificar que nгo esteja AFK. Se o cliente estiver AFK, os RPCs sгo colocados em uma pool de processamento interna, e assim que o cliente voltar, os RPCs sгo removidos da pool e processados, chegando no cliente.

Vamos considerar o seguinte exemplo:

- O servidor manda uma chamada de procedimento remуto para mudar a aзгo especial do cliente.
- O cliente estб pausado, resultando no colocamento do RPC, na pool interna de processamento.
- O cliente volta, entгo o RPC й processado e removido da pool de processamento, chegando no cliente.
- O cliente manda a nova aзгo especial no pacote de sincronizaзгo a pй.
- Os dados do pacote sгo escritos nas variбveis das estruturas internas do servidor.
- OnPlayerUpdate й chamada, e se ela retornar 1, a atualizaзгo serб transmitida para jogadores dentro da бrea de streaming.
- GetPlayerSpecialAction retornarб o novo ID de aзгo especial mantido em uma variбvel em CPlayerPool->CPlayer[id_do_jogador].
• Dessincronizaзгo.
A dessincronizaзгo, tambйm conhecida como "relуgio travado" por algumas pessoas, й uma grande causa de falsos-positivos em relaзгo a verificaзхes de anti-cheat.

Um jogador sofrendo dessincronizaзгo, ainda manda pacotes de atualizaзгo para o servidor e recebe eles, mas nгo vai reagir a alguns RPCs mandados pelo servidor, como 145 (SetPlayerAmmo) com o intuito de atualizar/mudar alguma informaзгo do cliente.

Como o cliente acaba nгo reagindo a certos RPCs, o mesmo nгo passarб pelo processo de stream in/out que й feito com RPCs, resultando jogadores/veнculos/objetos em nгo serem removidos, mas vгo parar de mandar dados de sincronizaзгo, resultando em que o jogador dessincronizado veja todos como se estivessem pausados/AFK.

Fazer a detecзгo de um jogador dessincronizado nгo й complicado, leve em consideraзгo que ele ainda manda atualizaзхes para o servidor, logo a callback OnPlayerUpdate continua sendo chamada. Vocк pode fazer a detecзгo tentando mudar a muniзгo na slot 0 utilizando SetPlayerAmmo, jб que os jogadores nгo vгo perceber a mudanзa de muniзгo em punhos (id 0) ou soco inglкs (id 1), e verificar se hб alguma diferenзa de valores com a ъltima atualizaзгo.
Reply
#2

Muito bom, +Rep
Reply
#3

Continue trazendo conteъdos sobre Pawn.RakNet pra board porque й muito interessante.
Parabйns pela iniciativa e pelo tutorial.
Reply
#4

Informaзгo sobre dessincronizaзгo, adicionada.
Reply
#5

Parabйns pelo tutorial, ta muito show.
Reply
#6

Tutorial de qualidade excelente.

Prevejo novas eras na board BR.
Reply
#7

Pode me dizer outra maneira de detectar sem usar SetPlayerAmmo ?
Reply
#8

Quote:
Originally Posted by KoloradO
View Post
Da pra detectar sem usar SetPlayerAmmo ?
Vocк poderia utilizar drunk level (SetPlayerDrunkLevel), por exemplo, pois ao utilizar GetPlayerDrunkLevel, ele vai continuar o mesmo.

Faзa a verificaзгo na callback OnPlayerUpdate, assim o jogador nгo serб acusado de estar desincronizado se estiver AFK, jб que, se a callback parar de ser executada, logo a verificaзгo tambйm para, e o jogador nгo pode ser acusado de estar desincronizado.
Reply
#9

Funciona com SetPlayerColor tambйm ?
Reply
#10

Quote:
Originally Posted by KoloradO
View Post
Funciona com SetPlayerTeam tambйm ?
Nгo.
Reply
#11

Mais uma vez excelente trabalho cara amiga.

Sua contribuiзгo na board e muito ъtil
Reply
#12

Quote:
Originally Posted by PT
View Post
Mais uma vez excelente trabalho cara amiga.

Sua contribuiзгo na board e muito ъtil
Jelly й uma mulher?
Reply
#13

Quote:
Originally Posted by Mises
View Post
Jelly й uma mulher?
Qual o problema??

Machismo agora no fуrum tambйm? E mais um membro no fуrum que deve ser respeitado como outro qualquer nгo importa o sexo.
Reply
#14

Quote:
Originally Posted by PT
View Post
Qual o problema??

Machismo agora no fуrum tambйm? E mais um membro no fуrum que deve ser respeitado como outro qualquer nгo importa o sexo.
O rapaz fez uma simples pergunta.
Reply
#15

Saudaзхes!


Quando o cliente fica ausente os pacotes sгo empilhados em um pol interna como disse, porйm esses pacotes possuem alguma espйcie de limite? ou quando o cliente retorna ao jogo esses pacotes sгo re enviados na ordem ou podem chegar aleatуriamente, hб risco de se perderem algum ?



Obs:
Quote:
Originally Posted by PT
View Post
Qual o problema??

Machismo agora no fуrum tambйm? E mais um membro no fуrum que deve ser respeitado como outro qualquer nгo importa o sexo.
Cara, sinceramente, sem necessidade.

Quote:
Originally Posted by GRiMMREAPER
View Post
O rapaz fez uma simples pergunta.
"Spam Machine" Challenge.
Reply
#16

Quote:
Originally Posted by Sky™
View Post
Saudaзхes!


Quando o cliente fica ausente os pacotes sгo empilhados em um pol interna como disse, porйm esses pacotes possuem alguma espйcie de limite? ou quando o cliente retorna ao jogo esses pacotes sгo re enviados na ordem ou podem chegar aleatуriamente, hб risco de se perderem algum ?
Os pacotes devem chegar na ordem que foram enviados, e sim, tem risco de chegarem fora de ordem ou de atй mesmo se perderem. O primeiro caso se chama packet misorder, o outro que й o mais уbvio, de packet loss.

Sobre a quantidade mбxima de RPCs que o cliente pode receber; um servidor nгo deve enviar mais de 85-140 mensagens por segundo, algo abaixo e entre esse valor estб ok.

Quanto mais RPCs vocк enviar para o cliente, mais ACKs seriam enviados para o servidor confirmando que os RPCs foram recebidos pelo cliente. Quando o nъmero de ACKs й muito alto, significa que o cliente excedeu o limite de informaзхes enviadas para o servidor, e podera resultar no cliente em ser kickado automaticamente por comportamento inesperado.

Acks sгo um reconhecimento, ou melhor, um sinal passado entre processos de comunicaзгo, computadores ou dispositivos para confirmar o recebimento de uma mensagem, como parte de um protocolo de comunicaзгo.

O limite de acks pode ser controlado no server.cfg, o nome da opзгo й "ackslimit" que й por padrгo 3000.
Reply
#17

Quote:
Originally Posted by PT
View Post
Qual o problema??

Machismo agora no fуrum tambйm? E mais um membro no fуrum que deve ser respeitado como outro qualquer nгo importa o sexo.
Caralho PT como tu й vitimista, cria uma avalanche num prato de sopa por nada. Machismo й o cu da sua mгe.

Se for realmente ela, fico surpreso e contente em saber que hб mulheres dominando programaзгo, o que й sem dъvidas algo incomum de se ver.
Reply
#18

Quote:
Originally Posted by Mises
View Post
Machismo й o cu da sua mгe.
E й assim que comeзa as treta no fуrum samp.
Reply
#19

Quote:
Originally Posted by Mises
View Post
Caralho PT como tu й vitimista, cria uma avalanche num prato de sopa por nada. Machismo й o cu da sua mгe.

Se for realmente ela, fico surpreso e contente em saber que hб mulheres dominando programaзгo, o que й sem dъvidas algo incomum de se ver.
Nгo tem necessidade de discutir por uma coisa tгo pequena e nem citar a mгe do cara.
Reply
#20

Se isso continuar, vou simplesmente remover o tуpico.
Reply


Forum Jump:


Users browsing this thread: 3 Guest(s)