Vous êtes sur la page 1sur 120

Bluetooth

orient java : JSR82 + Android


jean-michel Douin, douin au cnam point fr

version du 22 Novembre 2011

Notes de cours et mise en uvre

1
BT_java
Sommaire
Le contexte
Bluetooth, caractristiques, brve prsentation
Les protocoles et profils

JSR82, Principes
Deux paquetages,
Usage identique pour J2SE et J2ME
Dcouverte
Des priphriques BT et des services

Android, en premire approche


Client

Communication
RFComm btspp://
OBEX btgoep://

2
BT_java
Bibliographie utilise

La doc de lAPI jsr82, http://jcp.org/aboutJava/communityprocess/final/jsr082/index.html


http://www.kjhole.com/Standards/BT/BTdownloads.html
http://bluevirus.googlecode.com/files/bluetooth-for-java.9781590590782.22021.pdf
http://www.bluecove.org/bluecove/apidocs/
Recherche google :
Un expos de Macherel Bruno ppt M2PGI UFRIMA
Une prsentation de Apurva Kumar(www.research.ibm.com/people/k/kapurva)
Un expos de Camille Diou, universit de Metz,

http://www.usc.edu/dept/ee/scip/assets/001/57411.pdf souvent rfrenc


http://www.ieee802.org/11/Tutorial/90538S-WPAN-Bluetooth-Tutorial.pdf
http://www.cs.umu.se/kurser/TDBD16/VT07/Bluetooth-Tutorial-2001.pdf

http://www.bluetooth.com
http://www.newlogic.com

http://javabluetooth.chris-lorenz.com/ The JavaBluetooth Stack is a 100% (no native) Java implementation of


the Bluetooth Specifications Version 1.1. It currently supports HCI, L2CAP and SDP.
http://code.google.com/p/btfree/downloads/list
http://www.bluecove.org pour un grand nombre de JVM

http://developer.android.com/guide/topics/wireless/bluetooth.html
3
BT_java
Prambule

Le contexte

J2SE 6.0, update 11


WindowsXP/SP2, http://www.iogear.com/product/GBU341W6/
http://www.iogear.com/product/GBU421W6/
Outil de dveloppement Bluej 2.2.1
PC/cl Iogear GBU341W6, GBU421W6
librairie bluecove www.bluecove.org 2.1.0,
on winsock

Les MIDlet
Outils NetBeans 6.5, WTK 2.5.2
CLDC1.1, MIDP2.0
sur PC avec le micro-emulator
http://www.microemu.org/
sur mobiles :
sony ericsson S500i, W580i, Motorola K1 KRZR
Note: priori, le WTK ne permet quune mulation du BT

HTC Galaxy Tab, 2.2 API 8, HTC Magic


4
BT_java
Marketing

Aux alentours de 10 100 mtres (BT 2.0, class 1, class 2)


Source : http://www.cs.umu.se/kurser/TDBD16/VT07/Bluetooth-Tutorial-2001.pdf
5
BT_java
Bluetooth

Protocole de communication sans fil


peu chre, peu consommatrice dnergie,
adapt aux mobiles

Spcifications ici http://www.bluetooth.com/bluetooth/


Bluetooth is not a one-on-one data transmission technology so it can
communicate with up to eight devices within its transmission radius at one time

Vocable habituel :
Dcouverte multicast des services
Client/serveur, serveur/serveur

6
BT_java
Mesures, vrifier

Figures extraites
de http://www.licm.sciences.univ-metz.fr/IMG/pdf/Cours_Bluetooth.pdf
http://www.dandu.be/article/article-bluetooth-comparaison-dongles-46.html
http://www.sena.com/blog/?p=74

BT 2.0 10-100m
Performances : vrifier
7
BT_java
Des chiffres

Ondes radios : 2400 2483,5 MHz

Dbits annoncs : 1 Mb/s .. 2 Mb/s

Porte : 1 plus de 100m (1 100mW)


Class 3 Devices 100mW plus de 100 meters
Class 2 Devices 10mW plus de 10 meters
Class 1 Devices 1mW de 0.1-10 meters

Communication par paquets


Encadrs par des blocs de donnes de contrles

8
BT_java
Principe : des ondes autour de nous

Dcouverte aux alentours


Plusieurs priphriques peuvent rpondre une demande
de services

9
BT_java
Principe : des ondes autour de nous

Le priphrique possesseur du service est connu

10
BT_java
Vocabulaire : Piconet

Un Matre et ses esclaves

Esclaves affranchis Matre


11
BT_java
Vocabulaire : Scatternets

Un Scatternet = plusieurs piconets


12
BT_java
Scatternets se font et se dfont

http://www.acm.org/crossroads/xrds9-4/blue.html
13
BT_java
Combien ?

255 appareils, 7 communications simultanes

14
BT_java
Protocoles et profils

L2CAP
Logical Link Control and adaptation Protocol
Envoi de paquets avec un protocole donn vers le gestionnaire
appropri.

RFCOMM
mulation de ports sries au dessus de L2CAP.

OBEX
Object Exchange Protocol.
Analogue HTTP/GET-POST, FTP

SDP
Service Discovery Protocol (SDP).

TCS
telephony control specification
15
BT_java
O sommes nous ?

www.cs.umu.se/kurser/TDBD16/VT07/Bluetooth-Tutorial-2001.pdf

16
BT_java
Profils

Profils ou Capacits dun priphriques BT

ftp version bluetooth,


Tlphonie sans fil,
Imprimer des documents,
Dcouverte des services (SDP),
..

Applications ddies

-> Recensement des capacits dun appareil BT

17
BT_java
De la documentation originale

18
BT_java
En rsum

www.bluetooth.com/.../Technology/Works/OBEX.htm
19
BT_java
Bluetooth, existentiel

Qui suis-je ?
Je me prsente

Qui tes vous ?


Aux alentours

Parmi vous qui possde ce service ?

Avez dautres services proposer ?


Quels sont-ils ?

UUID ou identification dun service


Adquation UUID/URL
UUID prdfinis, UUID pour une application

Quels protocoles ?

O suis-je, o vais-je ?
pas facile voir blipnet ericsson
http://www.blipsystems.com/files/filer/technical_overview.pdf

20
BT_java
J2SE / JSR82

Deux paquetages

Qui suis-je ?, qui est l ?, rpondez


javax.bluetooth.*;
Nommage,
Dcouverte
Recherche de services
Communication
btspp://localhost:{UUID} + (flux habituels)

Un protocole rpandu OBEX


java.obex.*;
btgoep://localhost:localhost:{UUID} + (flux habituels)
tcpobex://1905
Irdaobex://localhost:1900
Session
Transfert dobjets
put, get

http://java.sun.com/javame/reference/apis/jsr082/javax/bluetooth/package-summary.html
http://www.jsr82.com
http://www.bluecove.org/
21
BT_java
Android

android.bluetooth

Qui suis-je ?, qui est l ?, rpondez

http://developer.android.com/guide/topics/wireless/bluetooth.html

22
BT_java
Qui suis-je ?

Chaque priphrique BT

possde

Une adresse (physique) sur 48 bit et unique


(MAC adresse)

Un nom lui est associ (en gnral)

23
BT_java
Premier exemple : quelle est mon adresse BT ?

import javax.bluetooth.LocalDevice;

public class QuiSuisJe{


public static void main(String[] args)throws Exception{

LocalDevice localDevice = LocalDevice.getLocalDevice();

System.out.println(localDevice.getBluetoothAddress() + " : " +


localDevice.getFriendlyName());
}
}

Depuis un PC, J2SE


javac -cp .;bluecove-2.1.0.jar QuiSuisJe.java
java -cp .;bluecove-2.1.0.jar QuiSuisJe

http://www.bluecove.org/bluecove/apidocs/

24
BT_java
Sur simulateur de mobile et sur mobile : QuiSuisJe

A cette URL http://jfod.cnam.fr/SEJA/jnlp/midlet/BTQuiSuisJe/

tlchargez sur votre poste


http://jfod.cnam.fr/SEJA/jnlp/midlet/BTQuiSuisJe/bluecove-2.1.0.jar
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTQuiSuisJe/microemulator.jar
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTQuiSuisJe/BTQuiSuisJe.jar
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTQuiSuisJe/run_microemulateur.bat

Puis excutez
> run_microemulateur.bat

Sur votre mobile installez cette Midlette


BTQuiSuisJe.jar

25
BT_java
Sur Android *

QuiSuisJe ?

BluetoothAdapter btAdapter = BluetoothAdapter.getDefaultAdapter();

String name = btAdapter.getAddress();

* Sur un mobile, bluetooth non pris en compte par lmulateur

26
BT_java
Bluetooh et nommage

0019EF0117DA
Devrons nous connatre les adresses physiques ?
Non merci
Sauf les fixes

Une UUID associera nom logique / adresse physique


Universal Unique IDentifier
http://www.avetana-gmbh.de/avetana-gmbh/produkte/doc/javax/bluetooth/UUID.html

-> UUID nous utiliserons


27
BT_java
La suite

Initialisation de la pile (protocole)

A la recherche dun service


Android
J2SE/JSR82

Dcouverte de priphriques BT
Aux alentours
Nommage/UUID Universally Unique IDentifier (128 bits),
existe en version courte

Communication
java.io.*, etc

Dcouverte des services


Au sein de chaque entit
Nommage/UUID Universally Unique IDentifier (128 bits)
http://www.handheld-basic.com/documentation/text/page_1766.html

28
BT_java
Un service se trouve sur ce priphrique

Il nous faut

Ladresse MAC du priphrique


tre appair (Android)
Ex. "00:19:EF:01:17:9C"

UUID (128bits)
Qui identifie le service
("10203040-5060-7080-90A0-B0C0D0E0F0FF");

29
BT_java
Android

Architecture retenue

Recherche du service bluetooth au sein dune sous-classe dAsyncTask

Communication dans un Thread,

Synchronisation en utilisant une SynchronousQueue

30
BT_java
Sous-classe dAsyncTask

Proposition

private class ConnexionBT extends AsyncTask<String,String,BluetoothSocket>{

protected void onPreExecute() {

protected BluetoothSocket doInBackground( String... args) {

protected void publishProgress(String... infos) {

protected void onPostExecute(BluetoothSocket btSocket) {

31
BT_java
Exemple
private UUID MY_UUID = UUID.fromString("10203040-5060-7080-90A0-B0C0D0E0F0FF");

private class ConnexionBT extends


AsyncTask<String,String,BluetoothSocket>{
private ProgressDialog dialog = null;
private BluetoothDevice btDevice;

protected void onPreExecute() {


dialog = ProgressDialog.show();
}

protected BluetoothSocket doInBackground(String... args) {


try{
this.btDevice = btAdapter.getRemoteDevice(args[0]); // @ MAC
btSocket = btDevice.createRfcommSocketToServiceRecord(MY_UUID);
btAdapter.cancelDiscovery();
btSocket.connect();
}catch(Exception e){}
return btSocket;
}
protected void onPostExecute(BluetoothSocket btSocket) {
os = btSocket.getOutputStream();

32
BT_java
Communication sur os : dans un Thread
public class Sender extends Thread{
private BlockingQueue<byte[]> queue;

public Sender(){
queue = new SynchronousQueue<byte[]>();
this.start();
}

public boolean offer(byte[] cmd){


return queue.offer(cmd);
}

public void close(){


this.interrupt();
}

public void run(){


while(!isInterrupted()){
try {
byte[] cmd = queue.take();
os.write(cmd);
} catch (Exception e) {
}

}
}
}
}

33
BT_java
J2SE/Un client
// la dcouverte du service

connString = agent.selectService(new UUID("102030405060708090A0B0C0D0E0F0BB", false),
ServiceRecord.NOAUTHENTICATE_NOENCRYPT, false);

StreamConnection conn = (StreamConnection)Connector.open(connString);


OutputStream out = conn.openOutputStream();
Reader in = new InputStreamReader(conn.openInputStream());

String str = "http://jfod.cnam.fr:8999/ds2438/\n";


out.write(str.getBytes());
out.flush();
String response = readFile(in);

// dans un Thread
private static String readFile(InputStream in) throws IOException {
StringWriter data = new StringWriter();
int aByte;
while((aByte = in.read())!=-1){
data.write( (byte)aByte);
}
return data.toString();
}

34
BT_java
Parmi mes voisins

Parmi les priphriques BT aux alentours

Quel est celui qui possde ce service


Apparent la dcouverte multicast

Un service : un UUID
new UUID("102030405060708090A0B0C0D0E0F011" ,false)
128 bits pourquoi pas celui-ci

Plusieurs BT peuvent rpondre pour un service souhait


dpt dun fichier , mp3
redondance

35
BT_java
A typical usecase

36
BT_java
A la dcouverte de obtention dun agent

import javax.bluetooth.LocalDevice;
import javax.bluetooth.DiscoveryAgent;

public class ALaDcouverteDe{

public static void main(String[] args) throws Exception{


LocalDevice local = LocalDevice.getLocalDevice();

local.setDiscoverable( DiscoveryAgent.GIAC );
// GIAC General inquire Access Code
DiscoveryAgent agent = local.getDiscoveryAgent();

un agent capable de tout faire


Slection dun service
Effectuer une recherche exhaustive
37
BT_java
Adquation UUID / URL
LocalDevice local = LocalDevice.getLocalDevice();
local.setDiscoverable( DiscoveryAgent.GIAC ); // General inquire Access Code
DiscoveryAgent agent = local.getDiscoveryAgent();

UUID uuid = new UUID("102030405060708090A0B0C0D0E0F011", false);

String connString = agent.selectService(uuid,


ServiceRecord.NOAUTHENTICATE_NOENCRYPT, false);

System.out.println("connString : " + connString);

Un exemple daffichage :

connString:
btspp://0019EF01194C:1;authenticate=false;encrypt=false;master=false

0019EF01194C ladresse physique


:1 le port de communication
38
BT_java
Un service comme un autre

Nous avons

Un service -> un UUID

un UUID -> une URL

Une URL -> une communication


Une syntaxe de type J2ME

Une communication
Un flux doctets, btspp://
Un flux structur, btgeop://

39
BT_java
Exemple de service/UUID/J2SE

Cest un serveur protocole btspp://

StreamConnectionNotifier notifier =
(StreamConnectionNotifier)Connector.open(
"btspp://localhost:102030405060708090A0B0C0D0E0F010");

attente dune requte

StreamConnection conn = notifier.acceptAndOpen();

40
BT_java
Un serveur au complet
public class SimpleBTSPPServer {

public static void main(String[] args) throws Exception{


LocalDevice local = LocalDevice.getLocalDevice();
local.setDiscoverable(DiscoveryAgent.GIAC);

StreamConnectionNotifier notifier = UUID

(StreamConnectionNotifier)Connector.open(
"btspp://localhost:" + "102030405060708090A0B0C0D0E0F010");

StreamConnection conn = notifier.acceptAndOpen();

InputStream in = conn.openInputStream();
ByteArrayOutputStream out = new ByteArrayOutputStream();
int data;
while ((data = in.read()) != -1) {
out.write(data);
}
System.out.println(" message recu : " + out.toString());
in.close();
conn.close();
notifier.close();
}

note : ci-dessus vous avez un serveur dune seule connexion cest peu

41
BT_java
Le client la recherche de cet UUID

Les essentiels

agent .selectService

String connString = agent.selectService(


new UUID("102030405060708090A0B0C0D0E0F010", false),
ServiceRecord.NOAUTHENTICATE_NOENCRYPT, false);

StreamConnection

StreamConnection conn = (StreamConnection) Connector.open(connString);

42
BT_java
Un exemple de client de ce service

public static void main(String[] args) throws Exception{


LocalDevice local = LocalDevice.getLocalDevice();
local.setDiscoverable( DiscoveryAgent.GIAC );
DiscoveryAgent agent = local.getDiscoveryAgent();

String connString = agent.selectService(


new UUID("102030405060708090A0B0C0D0E0F010", false),
ServiceRecord.NOAUTHENTICATE_NOENCRYPT, false);

StreamConnection conn = (StreamConnection) Connector.open(connString);

OutputStream out = conn.openOutputStream();


out.write("next".getBytes());
out.flush();
out.close();
conn.close();

}
}

43
BT_java
Android, mme principe

Extrait de http://developer.android.com/guide/topics/wireless/bluetooth.html

BluetoothServerSocket btServerSocket;

btServerSocket =
mBluetoothAdapter.listenUsingRfcommWithServiceRecord(NAME, MY_UUID);

44
BT_java
Un premier exemple : une passerelle BT/HTTP

HTTP://
BT/Web

Pourquoi faire ?

45
BT_java
Autre exemple une borne Bluetooth/HTTP

Un service Bluetooth, PC, J2SE reli au web


Attend une connexion BT,
rception dune URL (en String)
Effectue la requte
Retourne la page reue

Un client Bluetooth
Recherche ce service
Envoie une URL
Affiche le rsultat

46
BT_java
Dmonstration : le serveur

Le Proxy BT<->HTTP
est une application JavaWebStart
Il suffit de cliquer ici
http:/jfod.cnam.fr/SEJA/jnlp/BTProxyHTTP.jnlp

UUID = 102030405060708090A0B0C0D0E0F0A

Rception dune URL


Envoi du fichier, prcd de la taille de celui-ci,
Le client reste connect

47
BT_java
Dmonstration : Ct client

Le client BT / sur un autre poste


est galement une application JavaWebStart
(depuis un autre poste) http:/jfod.cnam.fr/SEJA/BTProxyClientDS2438.jnlp
Effectue une requte en http://jfod.cnam.fr:8999/ds2438/ toutes les 10mn
Le ds2438 est un capteur dhumidit relative

Ct client un navigateur ?
Sur mobile
http://sourceforge.net/search/?type_of_search=soft&words=browser+j2ME
Opera mini, sources java disponibles ?
Analogue lusage dun proxy mais au protocole btspp://

48
BT_java
Ct client/mobile

Le client BT sur votre mobile,


tlchargez cette midlette BTProxyHTTPClient.jar
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTProxyHTTPClient/

Le client BT sur un mulateur de mobile


Tlchargez tous les fichiers, puis excuter run_microemulateur.bat

49
BT_java
Une Variante de BTProxyHTTP

BTProxyHTTP2
http://jfod.cnam.fr/SEJA/jnlp/BTProxyHTTP2.jnlp

Une connexion par client


Envoi dune URL,
Rception du fichier
Fermeture de la connexion

50
BT_java
Quelques traces

Ct serveur
http://jfod.cnam.fr/SEJA/jnlp/BTProxyHTTP2.jnlp

Ct client
http://jfod.cnam.fr/SEJA/jnlp/MiniBrowser.jnlp
un autre exemple voir page suivante

Application extraite de
http://www.java-tips.org/java-se-tips/javax.swing/how-to-create-a-simple-browser-in-swing-3.html

51
BT_java
Un client du classique
// la dcouverte du service

connString = agent.selectService(new UUID("102030405060708090A0B0C0D0E0F0BB", false),
ServiceRecord.NOAUTHENTICATE_NOENCRYPT, false);

StreamConnection conn = (StreamConnection)Connector.open(connString);


OutputStream out = conn.openOutputStream();
Reader in = new InputStreamReader(conn.openInputStream());

String str = "http://jfod.cnam.fr:8999/ds2438/\n";


out.write(str.getBytes());
out.flush();
String response = readFile(in);

private static String readFile(InputStream in) throws IOException {


StringWriter data = new StringWriter();
int aByte;
while((aByte = in.read())!=-1){
data.write( (byte)aByte);
}
return data.toString();
}

52
BT_java
Le serveur en quelques lignes

LocalDevice local = LocalDevice.getLocalDevice();


local.setDiscoverable(DiscoveryAgent.GIAC);

StreamConnectionNotifier notifier =
(StreamConnectionNotifier)Connector.open("btspp://localhost:" +
"102030405060708090A0B0C0D0E0F0BB" + ";name=BTProxyHTTP2");

while(true){
StreamConnection conn = notifier.acceptAndOpen();
new ConnexionBT(conn).start();
}

ConnexionBT Un Thread chaque connexion Bluetooth


et Un Thread pour chaque requte HTTP !

Protocole :
envoi de lURL http:// puis attente du rsultat

53
BT_java
Le serveur suite, classe interne ConnexionBT
private static class ConnexionBT extends Thread{
private StreamConnection conn;
private String url;

public ConnexionBT(StreamConnection conn){this.conn = conn;}

public void run(){


try{
OutputStream out = conn.openOutputStream();
Reader in = new InputStreamReader(conn.openInputStream());

this.url = readLine(in);
if (url!=null) {
ConnexionHTTP connect = new ConnexionHTTP(url);
System.out.print(" -> une requete en " + this.url);
String result = connect.result();
System.out.println(", page lue et envoye : " + result.length() + " octet(s), iso-8859-1");

byte data[] = result.getBytes("iso-8859-1"); // le contenu


out.write(data);
out.flush();
}
out.close();
in.close();
conn.close();
}catch(Exception e){}
}}

54
BT_java
Dcouverte suite

Avec BTProxyHTTP, BTProxyHTTP2


LURL est connue
agent.selectService(new UUID("102030405060708090A0B0C0D0E0F0BB", false),
ServiceRecord.NOAUTHENTICATE_NOENCRYPT, false);

Notion de familles de services

Quelles sont ces familles ?

Quels sont les services ?

55
BT_java
Quels sont les services aux alentours ?

Tout dabord
quels sont les priphriques BT aux alentours ?
Grce mon agent
agent.startInquiry() : patience au moins 10 secondes

ensuite
Recherche des services bien connus ?
OBEX : push obex, ftp,
Etc

56
BT_java
Obtention de la liste de tous les priphriques
bluetooth aux alentours

57
BT_java
Comment ? startInquiry deviceDiscovered

58
BT_java
En Java : un listener appel par lAPI

Linterface DiscoveryListener
4 mthodes,
2 pour la dcouverte des priphriques
2 pour la dcouverte des services

public void deviceDiscovered( RemoteDevice rd, DeviceClass cod ) ;


public void inquiryCompleted( int status );

public void serviceSearchCompleted( int transID, int respCode ) ;


public void servicesDiscovered( int transID, ServiceRecord[] rec);

59
BT_java
Exemple : Liste des priphriques BT, startInquiry

public class BTDeviceList{

private static Object inquiry = new Object();


private static Vector<RemoteDevice> devices = new Vector<RemoteDevice>();

public static void main(String argv[]) throws Exception{

LocalDevice local = LocalDevice.getLocalDevice();


DiscoveryAgent agent = local.getDiscoveryAgent();

agent.startInquiry( DiscoveryAgent.GIAC, new DeviceDiscover());

System.out.println("start device inquiry ...");

synchronized(inquiry){ inquiry.wait();} // attente en sec.

System.out.println("device list : " + devices);


}

60
BT_java
Exemple suite : le listener
private static class DeviceDiscover implements DiscoveryListener{

public void deviceDiscovered( RemoteDevice rd, DeviceClass cod ) {


devices.addElement(rd);
}

public void inquiryCompleted( int status ) {


synchronized(inquiry) {
try { inquiry.notify(); } catch(Exception e) {}
}
}

public void serviceSearchCompleted( int transID, int respCode ) {}


public void servicesDiscovered( int transID, ServiceRecord[] rec){}
}
}

61
BT_java
Dmonstration

Il suffit de cliquer ici


http:/jfod.cnam.fr/SEJA/jnlp/BTDeviceList.jnlp

Des affichages sur la console sont effectus


Il vous faut slectionner loption Afficher La Console
panneau de configuration, Java, puis dans longlet Avanc

Ou bien en tlchargeant larchive

java -cp bluecove-2.1.0.jar;BTDeviceList.jar BTDeviceList

62
BT_java
Un schma/rsum extrait de la bibliographie

http://www.usc.edu/dept/ee/scip/assets/001/57411.pdf
63
BT_java
Un autre exemple plus compact
public static void main(String[] args) throws Exception{
LocalDevice localDevice = LocalDevice.getLocalDevice();

DiscoveryAgent discoveryAgent = localDevice.getDiscoveryAgent();


discoveryAgent.startInquiry(DiscoveryAgent.GIAC,
new DiscoveryListener(){
public void deviceDiscovered(RemoteDevice btDevice, DeviceClass cod){
try{
System.out.println(" New device discovered : " +
btDevice.getFriendlyName(true) +
" (" + btDevice.getBluetoothAddress() + ")" );
} catch(Exception e){e.printStackTrace();}
}

public void inquiryCompleted(int discType){


System.out.println("inquiryCompleted");System.exit(0);
}

public void servicesDiscovered(int transID, ServiceRecord[] servRecord){}


public void serviceSearchCompleted(int transID, int respCode){}
});

64
BT_java
Quels services ?, filtrage possible ?

bluecove.inquiry.duration
Device Inquiry time in seconds defaults to 11 seconds.

General Inquiry Access Code GIAC


Limited Inquiry Access Code LIAC

Notez que pour aller plus vite


Nous pouvons retrouver les priphriques dj dcouverts
De DiscoveryAgent methode retrieveDevices():
RemoteDevice[] retrieveDevices(int option);
...
Avec comme option
CACHED priphriques dj dcouverts dans le pass
PREKNOWN la liste des pr-configur ? claicir

Mais aucune garantie que le priphrique est toujours accessible,


Il a t dcouvert dans le pass, cest tout

65
BT_java
Exemple : PREKNOW / CACHED
private void addDevices_PREKNOW_AND_CACHED(){
RemoteDevice[] list = null;

list = agent.retrieveDevices(DiscoveryAgent.PREKNOWN);

if(list!=null){
System.out.println(list.length + " preknow");
for(int i = 0; i < list.length; i++){
devices.addElement(list[i]);
}
}

list = agent.retrieveDevices(DiscoveryAgent.CACHED);

if(list!=null){
System.out.println(list.length + " devices cached");
for(int i = 0; i < list.length; i++){
devices.addElement(list[i]);
}
}
}

66
BT_java
Cached

CACHED
Dtect lors dun prcdent inquiry

La pile sen charge vite (parfois) le recours la phase inquiry

67
BT_java
Diagramme dtats, ou un rsum

La suite

68
BT_java
Services -> Nouvelles questions ?

Quels sont les services ?

Quel filtre pour lobtention des services ? Comment ?

Dmonstration
Autorisez le bluetooth de vos mobiles

http://jfod.cnam.fr/SEJA/jnlp/BTServiceBrowser.jnlp

69
BT_java
la recherche des services (famille listener)

http://www.usc.edu/dept/ee/scip/assets/001/57411.pdf

70
BT_java
Exemple, UUID et plus

Sur chaque priphrique dcouvert


discoveryAgent.searchServices(attrSet, uuidSet, remoteDevice, this);

Avec
UUID[] uuidSet = {new UUID(0x0100)};
// 0x0100 au dessus de L2CAP
// 0x105 only searches btspp services
http://www.avetana-gmbh.de/avetana-gmbh/produkte/doc/javax/bluetooth/UUID.html

int[] attrSet = {0x0100, 0x0003, 0x0004};

// 0x0100 ProtocolDescriptorList
// 0x0003 ServiceID UUID
// 0x0004 ProtocolDescriptorList
http://www.forum.nokia.com/document/Java_Developers_Library_v2/GUID-9F75713D-5642-4C39-9A33-
C20928F37BF7/javax/bluetooth/ServiceRecord.html

71
BT_java
Un lundi aprs-midi au Cnam, 3me tage

LocalDevice properties: VIVALDI (0019155A34C7)

New device discovered : LMI84 (0019EF01194C)


New device discovered : La Tigresse (00180FD94A7C)

Searching for Services on: LMI84 (0019EF01194C)


A new service is discovered: Service Discovery
A new service is discovered: S e r v i c e u t i l i s a t e u r a d - h o c p e r s o n n e l

Searching for Services on: La Tigresse (00180FD94A7C)


A new service is discovered: Dial-up networking
A new service is discovered: Nokia PC Suite
A new service is discovered: COM 1
A new service is discovered: Audio Gateway
A new service is discovered: SIM ACCESS
A new service is discovered: OBEX Object Push
A new service is discovered: OBEX File Transfer
A new service is discovered: SyncML Client

72
BT_java
Exemple liste de tous les services
http://jfod.cnam.fr/SEJA/jnlp/BTServiceBrowser.jnlp

73
BT_java
Comment ?

public void startSearchServices() throws Exception{


UUID uuids[] = {new UUID(0x0100)}; // "0100" L2CAP
int attridset[] = {0x0100}; // SERVICE_NAME_ATTRID = 0x0100;
this.services.clear();
System.out.println("start search services for " + devices.size() + " devices");

for( int i=0; i<devices.size(); i++ ) {


RemoteDevice rd = devices.elementAt(i);
System.out.println(" search services for " + rd.getBluetoothAddress());
agent.searchServices(attridset, uuids, rd, this);
synchronized(this) {
while(!serviceSearchCompleted) wait();
serviceSearchCompleted=false;
}
}
}

Les priphriques dcouverts:


Vector<RemoteDevice> devices = new Vector<RemoteDevice>();
Les services dcouverts:
Vector<ServiceRecord> services = new Vector<ServiceRecord>();
74
BT_java
Les services en clair
// tous les services, <HostDevice,nom du service, URL>

for(int i=0; i< services.size(); i++){


str.append("<");

str.append(services.elementAt(i).getHostDevice().getBluetoothAddress());
try{
DataElement nameElement =
(DataElement)services.elementAt(i).getAttributeValue(SERVICE_NAME_ATTRID);

str.append(",");
if ( nameElement != null )
str.append((String)nameElement.getValue());
else str.append("_");
str.append(",");

str.append(services.elementAt(i).getConnectionURL(
ServiceRecord.NOAUTHENTICATE_NOENCRYPT, false));

}catch(Exception e){}
str.append(">\n");
}
return str.toString();

75
BT_java
Lire les rsultats retourns

Comment ?

Quelle Structure ? faire

0x4:
DATSEQ {
DATSEQ {
UUID 0000010000001000800000805f9b34fb
}
DATSEQ {
UUID 0000000300001000800000805f9b34fb
U_INT_1 0x10
}
}
0x1:
DATSEQ {
UUID 102030405060708090a0b0c0d0e0f088
UUID 0000110100001000800000805f9b34fb
}
0x0:
U_INT_4 0x10100
}

76
BT_java
Comment ? suite

public void serviceSearchCompleted( int transID, int respCode ) {


System.out.println("service search complete");
synchronized(this) {
try {
serviceSearchCompleted=true; this.notifyAll();
} catch(Exception e) {}
}

public void servicesDiscovered( int transID, ServiceRecord[] rec){


if(rec!=null && rec.length>0){
for( int i=0; i<rec.length; i++ ) {
services.addElement(rec[i]);
}
}

http://www.bluecove.org/bluecove/apidocs/

77
BT_java
http://www.bluecove.org/bluecove/apidocs/ voir UUID

Base UUID Value


(Used in promoting 16-bit and 32-bit UUIDs to 128-bit UUIDs)
0x0000000000001000800000805F9B34FB 128-bit
SDP 0x0001 16-bit
RFCOMM 0x0003 16-bit
OBEX 0x0008 16-bit
HTTP 0x000C 16-bit
L2CAP 0x0100 16-bit
BNEP 0x000F 16-bit
Serial Port 0x1101 16-bit
ServiceDiscoveryServerServiceClassID 0x1000 16-bit
BrowseGroupDescriptorServiceClassID 0x1001 16-bit
PublicBrowseGroup 0x1002 16-bit
OBEX Object Push Profile 0x1105 16-bit
OBEX File Transfer Profile 0x1106 16-bit
Personal Area Networking User 0x1115 16-bit
Network Access Point 0x1116 16-bit
Group Network 0x1117 16-bit

78
BT_java
Autre exemple

Qui aux alentours possde ce service ?


Object push, cest un service au protocole OBEX
final UUID OBEX_OBJECT_PUSH = new UUID(0x1105);
final UUID OBEX_FILE_TRANSFER = new UUID(0x1106);
final int SERVICE_NAME_ATTRID = 0x0100;

public void startSearchServices() throws Exception{


UUID uuids[] = {OBEX_OBJECT_PUSH};
int attridset[] = {SERVICE_NAME_ATTRID};
for(int i=0;i<devices.size();i++){
RemoteDevice rd = devices.elementAt(i);

agent.searchServices(attridset, uuids, rd, this);


synchronized(this) {
while(!serviceSearchCompleted) wait();
serviceSearchCompleted=false;
}
}
}

79
BT_java
Exemple : Remote Control

A lorigine un exemple sur le web

sourceforge.net/projects/blurc

Dfilement distant de diapositives PowerPoint (par exemple)

Contrle distant du clavier


Ajouts dvnements dans la file du systme
Usage de java.awt.Robot

http://doc.javastaff.com/?p=159 le blog de Federico Paparoni


http://doc.javastaff.com/?dl=11
http://doc.javastaff.com/?dl=10

BTFree ici http://code.google.com/p/btfree/downloads/list


Une librairie qui peut tre utile

80
BT_java
Mise en uvre Prise de contrle distant

HTTP://

Choix dun protocole de communication


Plusieurs mobiles en mme temps
la connexion reste ouverte
Envoi de next\n vers le serveur, (son interprtation ->)
Envoi de previous\n vers le serveur, (son interprtation <-)
Etc

81
BT_java
Dmonstration

Ct serveur
http://jfod.cnam.fr/SEJA/jnlp/BTServerVNC2.jnlp
Usage de java.awt.Robot

Un client sur PC pour les tests


http://jfod.cnam.fr/SEJA/jnlp/BTClientVNC2.jnlp

Avec microemulator
Tlcharger ces fichiers
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTClientVNC/
Puis >run_microemulateur

Sur votre mobile installez cette MIDlette


BTClientVNC.jar
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTClientVNC/

82
BT_java
Dmonstration suite

Pas de cl BT sur PC, pas de tlphones le nant

Utilisation du WTK et de lmulateur Bluetooth intgr

Le serveur est une midlette


Le source du serveur perfectible
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTServerVNC/

Il ne vous plus qu dvelopper le client !


Serait-ce une question de tp

83
BT_java
Un schma / rsum

84
BT_java
En rsum

Le client et son agent


85
BT_java
OBEX

http://developers.sun.com/mobility/apis/articles/bluetoothobex/
http://www.ibm.com/developerworks/java/library/wi-boogie1/index.html
http://wiki.forum.nokia.com/index.php/Using_Bluetooth_obex_server_in_Java_ME

BNEP Bluetooth Network Encapsulation Protocol


AVC(D)TP Audio/Video Control(Distribution) Transport Protocol
HCI Host Controller Interface
86
BT_java
OBEX

87
BT_java
OBEX Client/Server

Les clients OBEX


CONNECT, GET, PUT
import javax.obex.ClientSession;
import javax.obex.HeaderSet;
import javax.obex.Operation;
import javax.obex.ResponseCodes;

Le Serveur
UUID uuid = new UUID("8841", true);
String url = "btgoep://localhost:" + uuid +
";name=FTP;authenticate=false;master=false;encrypt=false";
import javax.obex.Operation;
import javax.obex.HeaderSet;
import javax.obex.ResponseCodes;
import javax.obex.ServerRequestHandler;
import javax.obex.SessionNotifier;

88
BT_java
OBEX : les UUID

Object Push Profile OPP 0x1105


File Transfer Profile FTP 0x1106
Synchronization Profile SYP 0x1104
Basic Imaging Profile BIP 0x111A
Phone Book Access Profile PBAP 0x1130
Basic Printing Profile BPP 0x1122

http://www.bluecove.org/bluecove/apidocs/
Lire le Quick Tutorial

0x1105
Ou
0000110500001000800000805F9B34FB en version longue

89
BT_java
Une session Client, ici un envoi dun fichier
1. Recherche du bon service ici serverURL
2. Puis tablissement dune connexion au protocole OBEX

public boolean obexPut(String serverURL) {

ClientSession clientSession clientSession = (ClientSession) Connector.open(serverURL);


HeaderSet hsConnectReply = clientSession.connect(clientSession.createHeaderSet());

if (hsConnectReply.getResponseCode() != ResponseCodes.OBEX_HTTP_OK) {
System.out.println("Connect Error " + hsConnectReply.getResponseCode());
}

HeaderSet hsOperation = clientSession.createHeaderSet();


hsOperation.setHeader(HeaderSet.NAME, fileName);
String type = ObexTypes.getObexFileType(fileName);
hsOperation.setHeader(HeaderSet.LENGTH, new Long(data.length));
Operation po = clientSession.put(hsOperation);

// envoi du fichier analyse po.getResponseCode()

po.close();
HeaderSet hsDisconnect = clientSession.disconnect(null);
// hsDisconnect.getResponseCode() == ResponseCodes.OBEX_HTTP_OK

90
BT_java
ObexTypes.getObexFileType, apparent mimes

public static class ObexTypes {

private static Hashtable<String,String> types =


new Hashtable<String,String>();

static {
types.put("jpg", "image/jpeg");
types.put("jpeg", "image/jpeg");
types.put("gif", "image/gif");
types.put("mp3", "audio/mpeg");
types.put("txt", "text/plain");
types.put("jar", "application/java-archive");
}

static String getFileExtension(String fileName) {


int extEnd = fileName.lastIndexOf('.');
if (extEnd == -1) {
return "";
} else {
return fileName.substring(extEnd + 1).toLowerCase();
}
}

static String getObexFileType(String fileName) {


return (String) types.get(getFileExtension(fileName));
}
}

91
BT_java
Le service

Inscription du service
SessionNotifier serverConnection = (SessionNotifier)
Connector.open("btgoep://localhost:"+ serverUUID + ";name=ObexPutServer2");

A chaque client
Une requte/un thread

Connection conn = serverConnection.acceptAndOpen(new RequestHandler());

Traitement de la reqete, PUT,GET, : -> RequestHandler

92
BT_java
Le service : RequestHandler
private class RequestHandler extends ServerRequestHandler {

public int onPut(Operation op) {


try {
HeaderSet hs = op.getReceivedHeaders();
String name = (String) hs.getHeader(HeaderSet.NAME);

InputStream is = op.openInputStream();
StringBuffer buf = new StringBuffer();
int data;
while ((data = is.read()) != -1) {
buf.append((char) data);
}

op.close();

synchronized(lock){notify();}
return ResponseCodes.OBEX_HTTP_OK;
} catch (IOException e) {
e.printStackTrace();
return ResponseCodes.OBEX_HTTP_UNAVAILABLE;
}
}}
93
BT_java
Un client OBEX du serveur au complet
private static class ClientObex extends Thread{
private Connection conn;
private SessionNotifier serverConnection;
private Object lock;

private class RequestHandler extends ServerRequestHandler {}

public ClientObex(SessionNotifier serverConnection) throws IOException{


this.serverConnection = serverConnection;
this.lock = new Object();
this.conn = serverConnection.acceptAndOpen(new RequestHandler());
this.setPriority(10);
this.start();
}

public void run(){


synchronized(lock){
try{
wait();
conn.close();
}catch(Exception e){}
}}}

94
BT_java
Applications, c.f. bluecove

Extraites des exemples joints avec bluecove


http://jfod.cnam.fr/SEJA/jnlp/OBEX_server.jnlp

http://jfod.cnam.fr/SEJA/jnlp/OBEX_client.jnlp

http://www.bluecove.org/bluecove/apidocs/
95
BT_java
Dmonstration BTFileUpload

Envoi dun fichier sur tous les mobiles ici prsents


1) Recherche de tous les priphriques BT
Autoriser vos portables
2) Slection de tous les priphriques possdant ce service
OBEX Object push 0x1105

http://jfod.cnam.fr/SEJA/jnlp/BTFileUpLoad.jnlp

96
BT_java
Un petit outil trs contagieux

Diffusion, mise jour, dploiement

Hypothse :
Une Midlet capable de diffuser une Midlet capable de diffuser une
Usage du service OBEX Push Object prdfini

Comment ?

Une archive contenue dans le .jar de la midlette est envoye tous ses voisins
Le voisin reoit une archive soit une midlette qui contient une archive

Viable ?
TTL dguis
Fonctionne quelque soit le mobile ?

97
BT_java
Petit outil de diffusion suite

La Midlette BTFileUpLoad
Contient une archive BTFileUpLoad.jar qui contient son tour

98
BT_java
Petit Outil en dmonstration

Prambule
Ok
Avec le micro-mulateur !

Sony Ericsson, S500i

Motorola K1,
envoi ok,
rception incorrecte

La Midlette est l
http://jfod.cnam.fr/SEJA/jnlp/midlet/BTFileUpload/

99
BT_java
Dmo du WTK

Voir obexdemo
Et le sous rpertoire j2seObexDemo
Et surtout http://wiki.forum.nokia.com/index.php/Using_Bluetooth_obex_server_in_Java_ME

100
BT_java
Dmo microemulator/ pile bluecove

server

http://wiki.forum.nokia.com/index.php/Using_Bluetooth_obex_server_in_Java_ME
Installes ici http://jfod.cnam.fr/SEJA/projet/obex_midlet/

101
BT_java
Le patron/observateur/Observ-MVC

HTTP
Observateurs/Observ
modele
2,mise jour)
http://vue1/update/?temperature=300
http://vue2/update/?temperature=300

1,notification) Contrle Vue


Vue
Vue
http://modele/notifyObservers/?temperature=300 vue1

0,init) http://modele/addObserver/http://vue1/update/
102
BT_java
MVC HTTP+BT

HTTP/BT
Observateurs/Observ
Midlettes
BTProxyHTTP
modele
BTServerHTTP 2,mise jour)
http://vue1/update/?temperature=300
http://vue2/update/?temperature=300

1,notification) Contrle Vue


Vue
Vue
http://modele/notifyObservers/?temperature=300 vue1
0,init) http://modele/addObserver/http://vue1/update/

http://modele/addObserver/uuid=11223344556677889900 103
BT_java
Patrons Observateur + Fabrique

ObservableServer
addObserver, notifyObservers comme services Web/HTTP
ObserverServer
Update comme service Web
ObserversHTTPList
La liste des observateurs

ConnectionFactory
Une fabrique de Connexion

Deux connexions concrtes


Bluetooth et HTTP (dpend de lurl choisie)

104
BT_java
Un exemple avec Httpunit
public void test_notifyBTObservers(){
try{
new Thread(new Runnable(){ // cration de lobservable
public void run(){
ObservableServer.main(new String[]{"8226"});
}}).start();

WebConversation conversation = new WebConversation();


WebRequest request = null;

// inscription dun observateur

request = new GetMethodWebRequest("http://localhost:8226/addObserver/?uuid=102030405060708090A0B0C0D0E0F088");

WebResponse response = conversation.getResponse( request );


assertTrue(" pas de rponse ???", response.getText().length() > 0);
assertTrue(" la rponse doit doit ici retourne true ???", response.getText().contains("true"));

// une premire notification

request = new GetMethodWebRequest("http://localhost:8226/notifyObservers/?temperature=300&capteur=DS1921" );


response = conversation.getResponse( request );
assertTrue(" pas de rponse ???", response.getText().length() > 0);

// une seconde notification


request = new GetMethodWebRequest("http://localhost:8226/notifyObservers/?temperature=200&capteur=DS1922" );

response = conversation.getResponse( request );


assertTrue(" pas de rponse ???", response.getText().length() > 0);
}finally{
ObservableServer.stopServer();
}
}
105
BT_java
Une dmonstration

Dmonstration en ligne :
http://jfod.cnam.fr/SEJA/jnlp/TestsObervable.html

Traces ct Observable
BlueCove version 2.1.0 on winsock
Request: GET /notifyObservers/?temperature=200&capteur=DS1922 HTTP/1.1
Request: GET /addObserver/?uuid=102030405060708090A0B0C0D0E0F088 HTTP/1.1
addObserver : 102030405060708090A0B0C0D0E0F088
Request: GET /notifyObservers/?temperature=300&capteur=DS1921 HTTP/1.1
Request: GET /notifyObservers/?temperature=200&capteur=DS1922 HTTP/1.1

Ct Mobile, bluetooth

106
BT_java
Petite conclusion

Observateur/Observ sur le web

Mobiles
Contrles/ Vue

Modle ? / liaison web ?

En quelques lignes
Abstraction des distances

terminer

107
BT_java
Conclusion plus grande ?

Bluetooth
Mobile/java
Motorola K1, Sony Ericsson
tester : http://www.opera.com/mini/download/all/

Cl USB ou intgr sur PC

bluecove API jsr82


http://www.bluecove.org/

Cette prsentation : impasse sur l2cap ?


Dans une prochaine mouture

108
BT_java
Conclusion

http://www.bluecove.org/
vrifier sur dautres priphriques
109
BT_java
Annexes

UbiqMuseum
Rseaux adhoc broadcast
Tlcommandes

110
BT_java
UbiqMuseum comme projet

http://monet.knu.ac.kr/~cktoh/data/Springer_jucano_pmanzoni_Toh.pdf
111
BT_java
UbiqMuseum

Tout visiteur reoit une MIDlet de visite


MIDLet cliente
et/ou
MIDLet serveur

Chaque pice du muse est quip dun PC/BT/Wifi


Serveur / Client
PC reli entre eux voir Java Messaging Service (JMS)

Mode connect
< 8 priphriques simultans
Mode de type Session

Ct client
RFComm
OBEX

112
BT_java
UbiqMuseum

Discussion

113
BT_java
Annexe javawebStart

http://jfod.cnam.fr/SEJA/jnlp/mode_emploi_jnlp.html
Un certificat
> keytool -genkey -alias jmd -keypass PASSWORD -keystore jmdstore -storepass PASSWORD
jar cvf MiniBrowser.jar webBrowser/*.class
jarsigner -keystore jmdstore MiniBrowser.jar jmd

<jnlp spec="1.0+"
codebase="http://jfod.cnam.fr/SEJA/jnlp/"
href="MiniBrowser.jnlp">
<information>
<title>MiniBrowser</title>
<vendor>SEJA Cnam</vendor>
<description>MiniBrowser</description>
<offline-allowed/>
</information>
<security>
<all-permissions/>
</security>
<resources>
<j2se version="1.5+"/>
<jar href="MiniBrowser.jar"/>
<jar href="bluecove-2.1.0.jar"/>
</resources>
<application-desc main-class="webBrowser.MiniBrowser"/>
</jnlp>

http://jfod.cnam.fr/SEJA/jnlp/BTProxyHTTP2.jnlp
114
BT_java
Annexe : MIDlet javax.bluetooth.*

JSR82
javax.bluetooth

115
BT_java
Device Management

Device Management
LocalDevice() appel par lapplication cliente
setDiscoverable()
updateRecord()
getBluetoothAddress()
getProperty()
RemoteDevice() informations du fournisseur
getBluetoothAddress()
authenticate()
authorize()
isEncrypted()

116
BT_java
Rsum Communication

JSR 82 supports a low-level data transfer (Logic Link Control


& Adaptation) and a stream communication interface (RFCOMM)

L2CAP interface not commonly used


Need significant effort from user to handle the packets, fragmentation etc.,

Stream communication API is used extensively in MIDP development


btspp://hostname:[CN | UUID];parameters

1. - btspp indique le protocole RFCOMM (StreamConnection)


2. - hostname soit localhost, ou ladresse Bluetooth
3. - CN est le numro de port
4. - UUID lidentifiant du service
5. - parameters authenticate, authorize, and encrypt information

- Eg: btspp://hostname;authenticate=true;authorize=true;encrypt=true
117
BT_java
Annexe Klings

118
BT_java
BTBrowserMIDlet de klings

http://wireless.klings.org/main.php/BTBrowser/

Mise en uvre, dveloppement


WTK

Avec le microemulateur*
Pile bluecove et avetana

Les sources et excutables


http://jfod.cnam.fr/SEJA/projet/btbrowser_klings_midlet/

*java -cp ./microemulator.jar;./bluecove-2.0.3.jar;. org.microemu.app.Main BTBrowserMIDlet

119
BT_java
BTBrowser, avec un autre mulateur

http://kobjects.sourceforge.net/me4se/

java -cp ./me4se-2.2.0.jar;./bluecove-2.0.3.jar;. org.me4se.MIDletRunner BTBrowserMIDlet

120
BT_java