Accéder au contenu principal

D-BUS, un bus de messagerie pour UNIX (et Windows)

Introduction

J'ai déjà parlé dans un billet précédent de JMX qui peut être utilisé en Java pour surveiller une application ou faire des appels distants. Je vais parlé ici d'un autre système de communication assez répandu sous UNIX, mais pourtant pas très connu : D-Bus.

D-Bus est un système de communication interprocess qui permet d'échanger des messages entre deux applications sur la même machine. Il est en cela comparable à CORBA (Unix et Windows) ou COM/DCOM (Windows) car il permet de piloter une application à distance et ajoute également un mécanisme de signalisation. L'avantage de D-BUS est sa légèreté car il utilise un simple "démon" pour la communication et il peut être utilisé par différents langages (C, C++, Java, Python). La communication entre les processus s'effectue à l'aide de Sockets Unix ou TCP.

D-Bus est essentiellement utilisé par Gnome pour ses applications graphiques, ainsi que par un certain nombre d'applications multimédia. Il permet par exemple de recevoir une notification lorsqu'un CD est inséré dans le lecteur, lorsque le volume est augmenté ou diminué, lorsqu'une connexion Bluetooth est détectée, etc. Son usage peut également être détourné pour une utilisation embarquée.

Je vais principalement m’intéresser ici à la compilation sous Windows et à son utilisation en Java.

Compilation de D-Bus sous Windows

Les versions compilées de D-Bus sont livrées nativement avec Cygwin qui est un environnement sous Windows permettant de compiler et d'exécuter des applications POSIX (Unix pour simplifier). Dans l'environnement Cygwin, la plupart des librairies et fichiers d'entêtes sont disponibles pour ré-compiler sous Windows des applications initialement livrées pour Linux. Il existe également MINGW qui est un environnement minimaliste pour la compilation d'application Unix sous Windows, mais il manque souvent des librairies et des fichiers d'entêtes nécessaires à la compilation. Dans mon cas, j'ai donc utilisé Cygwin dans sa version 64 bits.

1. Récupérez D-Bus
D-Bus peut être téléchargé à l'adresse suivante : http://dbus.freedesktop.org/releases/dbus/
J'ai récupéré la version 1.7.10 pour mes tests.

2. Décompressez le fichier récupéré
Le fichier dbus-1.7.10.tar.gz doit être décompressé à l'aide de
gunzip dbus-1.7.10.tar.gz

, puis détarré avec la commande
tar xvf dbus-1.7.10.tar

Vous pouvez également utiliser la commande
tar xvfz dbus-1.7.10.tar.gz
qui effectue les deux opérations en même temps.

Si vous souhaitez faire l'opération graphiquement, l'utilitaire 7-Zip permet d'effectuer ces 2 opérations.

3. Lancez la configuration, puis la compilation à l'aide des 3 opérations "classiques"
./configure
make
make install

La compilation prend un certain temps. L'installation finale s'effectue dans les répertoires /usr/local/bin pour les binaires, /usr/local/lib pour les libraries et /usr/local/include pour les fichiers d'entêtes. Sous Windows, ces répertoires sont situés dans le répertoire de Cygwin (ex : "C:\cygwin64").

4. Lancez le démon
Le démon D-Bus est lancé avec la commande
dbus-launch.exe
Cette commande lance le processus "/usr/local/bin/dbus-daemon" en tâche de fond un peu comme un Service Windows. C'est la seule application nécessaire au fonctionnement de D-Bus. Notez bien l'adresse de la session du bus qui est affichée. Cette adresse sera nécessaire pour communiquer avec l'application.
DBUS_SESSION_BUS_ADDRESS=unix:path=/tmp/dbus-fnxsbC2zqt,guid=23719b0a709e4557a7195ee952d92e32

Les autres applications livrées avec D-Bus sont :
- dbus-send : permet d'envoyer des messages ou des signaux vers un process
- dbus-monitor : permet d'écouter tous les évènements échangés sur le bus
- dbus-cleanup-sockets : permet de nettoyer les sockets créés dans le répertoire /tmp.

Utilisation de D-Bus en Java sous Windows


Une librairie développée par Matthew Johnson, pour l'utilisation de D-Bus en Java est disponible sous http://dbus.freedesktop.org/releases/dbus-java/. La dernière version 2.10 date de 2009 mais reste fonctionnelle. La documentation est disponible sous http://dbus.freedesktop.org/doc/dbus-java/dbus-java.pdf. Cette dernière est relativement lourde et pas très simple à utiliser. Il existe un autre tutoriel http://rm5248.com/d-bus-tutorial qui explique de manière très simple l'utilisation de D-Bus en Java et en C++.

Avant de pouvoir utiliser l'API Java, il faut compiler la librairie fournie. C'est là que les choses se gâtent. La librairie dbus-java s'appuie sur une autre librairie de Matthew Johnson permettant l'utilisation des Sockets Unix utilisées dans D-Sub. Cette librairie nécessaire à la compilation, ainsi qu'à l'exécution des applications Java est disponible à l'adresse http://www.matthew.ath.cx/projects/java/libmatthew-java-0.8.tar.gz. Cette librairie combine du code en Java et en C pour l'utilisation des sockets et s'appuie donc sur JNI (Java Native Interface).

Pour la compilation sous Unix, décompressés cette librairie et lancez "make".
Sous Cygwin, il vous faut faire les modifications suivantes :
1. export JAVA_HOME=c:/jdk1.7.0_25. Notez bien le "/" à la place du "\". Les fichiers nécessaires à JNI sont disponibles dans le répertoire c:/jdk1.7.0_25/include et c:/jdk1.7.0_25/include/win32.

2. Modifiez le Makefile pour faire référence à win32 à la place de linux. L'option -fpic doit également être supprimée sous Windows. Repérez les variables suivantes et remplacez les.
INCLUDES+=-I$(JAVA_HOME)/include -I$(JAVA_HOME)/include/win32
CFLAGS+=-Wall -D_JNI_IMPLEMENTATION_ -Wl,--kill-at
CSHAREFLAG+=-fno-stack-protector
LDSHAREFLAGS+= -Wall -D_JNI_IMPLEMENTATION_ -Wl,--kill-at -shared

3. Lancez la compilation de la librarie libmatthew-java
make

Le résultat de cette compilation fournira un 6 libraries java (cgi-0.6.jar, debug-disable-1.1.jar, debug-enable-1.1.jar, hexdump-0.2.jar, io-0.1.jar, unix-0.5.jar) et 2 libraries JNI (libcgi-java.so, libunix-java.so). Les librairies hexdump-0.2.jar et unix-0.5.jar sont nécessaires pour la compilation de dsub-java. La librairie libunix-java.so doit être renommée en unix-java.dll et est nécessaire pour l'exécution des applications Java.

4. Vous pouvez ensuite décompiler la librairie dbusjava, et le recompiler avec compile.bat après avoir mis les bons settings. Vous pouvez alternativement, créer un projet Eclipse incluant tous les sources de manière à créer une librairie unique dbusjava.jar incluant tous les fichiers nécessaires. C'est ce que j'ai fait. Le projet complet est disponible ici.

5. Il y a une difficulté supplémentaire pour l'exécution des fichiers sous Windows. Les librairies JNI utilisées avec Java ne sont pas compatibles avec Cygwin qui charge des dlls particulières. Vous obtiendrez ainsi l'erreur suivante.

$ java -jar lib/dbusjava.jar org.freedesktop.dbus.viewer.DBusViewer
      1 [main] java (7236) C:\jdk1.7.0_25\bin\java.exe: *** fatal error - cygheap base mismatch detected - 0x1802DB410/0xD19B410.
This problem is probably due to using incompatible versions of the cygwin DLL.
Search for cygwin1.dll using the Windows Start->Find/Search facility
and delete all but the most recent version.  The most recent version *should*
reside in x:\cygwin\bin, where 'x' is the drive on which you have
installed the cygwin distribution.  Rebooting is also suggested if you
are unable to find another cygwin DLL.
Exception in thread "DBus Loader" java.lang.UnsatisfiedLinkError: C:\Java_Dev_1\dbusjava\unix-java.dll: L▒acc▒s ▒ cet emplacement de la m▒moire n▒est pas valide
        at java.lang.ClassLoader$NativeLibrary.load(Native Method)
        at java.lang.ClassLoader.loadLibrary1(ClassLoader.java:1957)
        at java.lang.ClassLoader.loadLibrary0(ClassLoader.java:1882)
        at java.lang.ClassLoader.loadLibrary(ClassLoader.java:1872)
        at java.lang.Runtime.loadLibrary0(Runtime.java:849)
        at java.lang.System.loadLibrary(System.java:1087)
        at cx.ath.matthew.unix.UnixSocket.<clinit>(UnixSocket.java:40)
        at org.freedesktop.dbus.Transport.connect(Transport.java:772)
        at org.freedesktop.dbus.Transport.<init>(Transport.java:737)
        at org.freedesktop.dbus.DBusConnection.<init>(DBusConnection.java:299)
        at org.freedesktop.dbus.DBusConnection.getConnection(DBusConnection.java:282)
        at org.freedesktop.dbus.viewer.DBusViewer$2.run(DBusViewer.java:139)
        at java.lang.Thread.run(Thread.java:724)

Il faut donc utiliser un launcher Java spécial qui permet de lancer les applications Java utilisant des librairies JNI compilées avec Cygwin dans l'environnement Cygwin. Ce launcher a été construit à partir des sources récupérés sur le site https://code.google.com/p/jessies/source/browse/salma-hayek/trunk/native/all/java-launcher/java-launcher.cpp. J'ai extrait le code source correspondant ainsi que la version compilée ici.  Ce launcher  peut être utilisé pour d'autres projets utilisant des libraries JNI. L'utilisation se fait à peu près comme le compilateur Java classique.
./javalauncher.exe -cp lib/dbusjava.jar org.freedesktop.dbus.viewer.DBusViewer

Voici dans un premier temps les différentes étapes pour la compilation du projet. Je continuerai avec les différentes utilisations.





Commentaires

Posts les plus consultés de ce blog

Supprimer les partitions Raspberry sur une carte SD sous Windows 7 avec Diskpart

Si vous souhaitez récupérer une ancienne carte SD utilisée pour démarrer un Raspberry pour un autre usage (appareil photo, etc), il vous faudra supprimer les deux partitions créées au moment de l'écriture de l'image sur la carte SD. Vous pouvez voir les partition en sélectionnant Menu Windows/Ordinateur/bouton droit "Gérer". Voici un exemple du résultat final. Vous pouvez supprimer la partition Unix de 7 Gb (ou 4Gb en fonction de la taille de votre carte) en sélectionnant la partition puis en faisant "bouton droit Supprimer". Laissez juste une partition pour pouvoir faire les autres manipulations avec DISKPART. Démarrez l'outil DISKPART en ligne de commande. Une nouvelle fenêtre s'ouvrira. Microsoft DiskPart version 6.1.7601 Copyright (C) 1999-2008 Microsoft Corporation. Sur l'ordinateur : FRVILN0H305806 DISKPART> list disk   N° disque  Statut         Taille   Libre    Dyn  GPT   ---------  -------------  -------  -------  ---  ---   D

Comment lire son écran de téléphone Android sur PC (2)

Voici une nouvelle manière d'accéder à votre téléphone depuis votre PC. Cette méthode utilise le câble USB et Google Chrome. Elle fonctionne donc sur Windows, Mac et Linux. Les pré-requis sont les mêmes que ceux du billet précédent : Téléphone configuré en mode Développement Drivers USB installés sur le PC Google Chrome installé L'application Vysor s'installe comme une extension de Google Chrome. Cherchez dans le Webstore et lancez l'installation. Une fois installée, l'application apparaît dans les extensions. Vous pouvez la lancer de différentes manières. La manière la plus simple est d'ouvrir la fenêtre des applications : chrome://apps/ Une autre manière est de créer un raccourci en cliquant sur « Détails ». Ensuite créez un raccourci sur le bureau, le menu démarrer et/ou la barre de tâche. Vous pouvez également cliquer sur afficher dans la boutique et lancer l'application depuis la boutique. Une fois

Serveur d'impression CUPS sur Raspberry Pi

Je possède une très vieille imprimante laser HP Laserjet 6L noir et blanc de 12 ans d'age qui a survécu à plusieurs imprimantes jet d'encre couleurs tombées en désuétude pour obsolescence programmée. J'envisage tout de même sérieusement de les démanteler pour les recycler en CNC, graveur ou autre.   Je continue donc a utiliser cette bonne petite imprimante parallèle qui me rend bien des services (en 12 ans, j'ai changé le toner 3 fois pour un coût de 20 € la cartouche). J'ai donc dû m'équiper d'une adaptateur USB/Parallèle pour pouvoir la connecter sur un PC récent. Le problème principal est que le driver de cette imprimate n'est reconnu que par un seul de mes PC sous Windows 7. Les autres PC sous Windows 8 ou Windows 10 reconnaissent bien l'imprimante, mais sortent des feuilles avec le code Postscript. L'impression depuis une tablette ou un téléphone Androïd est également tout simplement impossible. Pour remédier à ce problème, j'ai don