Ca fait au moins 20h que j'essaie de trouver la cause de ce bug :
Je fais un petit jeu multijoueur en Python. Pour info , j'utilise twisted + pygnet.
J'ais un espace de jeu constitué d'une table en deux dimension qui contient des objets "zone". Ces objets contiennent plusieurs informations , dont le type d'unité présent dans la zone par joueur. Un joueur ne peut avoir qu'un seul type d'unité par zone.
Comme j'ai fait un networking qui se base sur un nombre fini de données à envoyer chaque zone possède par joueur un type d'unité sous la forme d'un nombre entier. Même lorsqu'il n'y a pas d'unité dans la zone , la zone possède quand même un attribut "type".
Enfin ça c'est juste pour le background , car en fait on n'a pas réellement besoin de savoir ça pour appréhender le bug.
Je décrirais le bug comme ceci :
Le programme lit une ligne de code sans lire celle d'avant ou d'après , et ce de façon aléatoire.
Dans mon programme , à un seul endroit , je modifie la valeur de l'attribut "type" pour une zone pour un joueur donné.
Résultat , le type de la zone choisie et celui de pleins d'autres zones (apparement choisies aléatoirement) est changé.
j'ai mis tout les test possibles et imaginable pour empêcher que n'importe quelle zone soit modifiée, sans succès.
J'ai vérifié que le problème ne vient pas d'autre partie du programme (aucune autre partie ne peut modifier le "type" d'une zone , et le serveur envoie bien des informations déjà erronée au client)
Le bug apparait quand je veux déplacer une unité d'une case (zone1) vers une autre (zone2). Pour cela je dois changer le type de la zone2 pour qu'il soit égal à celui de la zone1.
Le problème vient de cette ligne , car si je l'enlève , aucun type n'est changé :
self.cln correspond au numéro d'identifiant du joueur dont on veux changer le type de l'unité dans la zone.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2 zone2.army_per_pl[self.cln].special_type.type = zone1.army_per_pl[self.cln].special_type.type
special_type est un objet représentant un type d'unité ( elle contient des attribut tels que la vitesse de l'unité par exemple , et bien sur son type , qui est un nombre)
En gros , ça consiste a mettre le contenu d'une variable (un nombre entier) , dans une autre variable.
Mais voilà , ça met ce contenu non seulement dans la bonne variable , mais dans plein d'autres variables.
J'ais tenté de sauvegarder les types de toutes les zones dans une table (backup_table) , d'appliquer la ligne du dessus , et ensuite de rétablir les anciennes valeur dans toutes les zones sauf dans zone1 et zone2.
Je ne sais pas trop ce qui peut provoquer un tel bug . Peut être une interférence entre threads ? Mais je n'arrive pas à utiliser les sémaphores (il faut que je remonte au script de twisted).
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11 for x in backup_table: for zon in x: # zon est un objet ayant comme attribut la zone cible , et la valeur de son "type" if zon.zone != zone2 and zon.zone != zone1 : # on modifie tout sauf zone 1 et 2 print zon.zone.x # pour voir qui passe le test (coordonnées de zone) print zon.zone.y # on peut voir que les zones 1 et 2 ne passent pas le test print "__" #resultat : les zones 1 et 2 sont quand meme modifiees zon.zone.army_per_pl[self.cln].special_type.type = zon.value # Si on vire ca , les zones se sont pas modifiees # conclusion , cette derniere ligne est utilisée "sans autorisation"
EDIT : Magnifique , le seul fait de poster sur ce forum m'a fait trouver la solution (il fallait mettre special_type tout court et pas special_type.type ).
Partager