Multithreading avec GTK en python sur N900

Une application sous linux en python telle que Caritang doit résoudre le problème de réactivité de l’interface utilisateur en prenant en compte les spécificités suivantes:

  1. la thread principale qui execute GTK
  2. l’interpréteur python
  3. le serveur X

Une IHM se doit d’être réactive. Toute action de l’utilisateur doit provoquer une réponse immédiate de l’IHM. Or la mise à jour de l’IHM se fait quand la thread principal qui execute la boocle gtk sort du code appelé par l’évènement de l’interface graphique. Autrement dit ce n’est que lorsque le code créeé par le programmeur pour effectuer l’action est terminé qu’on est sûr que l’IHM sera mis à jour. Donc si le code de l’action n’est pas trés rapide alors on va monopoliser la thread principale de gtk à faire de l’applicatif au lieu de faire de l’IHM.
Quand on veut effectuer un traitement long, il faut lancer une thread dédiée à ce traitement afin de libérer la thread principale. Plusieurs techniques existent: on peut utiliser les fonctions utilitaires de gobject comme timeout_add ou bien une classe Timer ou alors créer soit même une Thread.
Quelque soit la technique il faut néanmoins indiquer à gtk qu’il va s,exécuter en multithreading en invoquant gtk.gdk.threads_init()

Libérer la thread principal permet à GTK de mettre à jour l’IHM. Ainsi si la thread du traitement modifie le texte d’un gtk.Label, la thread de GTK pourra mettre à jour l’IHM. Inversement l’IHM étant disponible, l’utilisateur peut demander la fermeture de l’application. Dans ce cas que se passe-t-il pour la thread de traitement? Soit elle continue en empêchant la fermeture du programme soit elle est brûtalement arrétée si elle est marquée comme deamon. Ce dernier cas n’est pas la meilleur solution car il entraine des erreurs dans la thread de traitement. Ainsi durant l’arrêt de l’interpréteur python, la thread de traitement se retrouve dépourvu des variables locales ou d’instances.
L’idéal est d’envoyer un signal à la tread de traitement pour qu’elle se termine proprement.

Enfin le serveur X (peut?) n’est pas « thread safe ». Malgrès tout ce qui précède il se peut que le thread principale de GTK accède à l’IHM en même temps que la thread de traitement. Une simple modification du texte d’un gtk.Label provoquera de manière aléatoire une erreur dans XLib. La solution est de protéger (synchroniser) les accès aux composants graphiques en encadrant toute modification de l’IHM dans la thread de traitement par gtk.gdk.threads_enter() et gtk.gdk.threads_leave()

Cet article, publié dans Langage, est tagué , , , , . Ajoutez ce permalien à vos favoris.

Laisser un commentaire

Entrez vos coordonnées ci-dessous ou cliquez sur une icône pour vous connecter:

Logo WordPress.com

Vous commentez à l'aide de votre compte WordPress.com. Déconnexion / Changer )

Image Twitter

Vous commentez à l'aide de votre compte Twitter. Déconnexion / Changer )

Photo Facebook

Vous commentez à l'aide de votre compte Facebook. Déconnexion / Changer )

Photo Google+

Vous commentez à l'aide de votre compte Google+. Déconnexion / Changer )

Connexion à %s