poniedziałek, 27 lipca 2009

Linux, Bluetooth, mobile, Internet

There is something about Bluetooth

Last week I've decided to go wireless and connect to the Internet with my netbook via a cellphone without using a USB cable.

Connecting to the Internet with a USB cable is quite simple - a glimpse at /var/log/syslog is enough. Usually /dev/ttyACM0 appears. What you have to do then is to just use pppd. It's similar when using Bluetooth, but getting to the moment when a device analogous to ttyACM0 appears (usually /dev/rfcomm0) may be difficult.

This article presents how to achieve the goal using command line tools. It's quite probable that it's possible to get a similar effect using blueman or gnome-bluetooth. It's a pity these tools have so many bugs. What's also important I would like to know what really happens. I hope I won't have to use them, as I don't use NetworkManager (popular in distributions like Ubuntu). Being in charge in exchange for convenience.

Ingredients (nontechnical version)

  • A computer with a Bluetooth interface (Asus Eee PC 1000 has one built-in)
  • A cell phone with Bluetooth (in my case Nokia E66)
  • Enabled Internet service to use with your SIM card (I suppose it's a standard nowadays)

My experimental platform

Bluetooth module in my EeePC:

$ lsusb
ASUSTek Computer, Inc. Broadcom Bluetooth 2.1
idVendor 0x0b05 ASUSTek Computer, Inc.
idProduct 0xb700 Broadcom Bluetooth 2.1

My cell phone Bluetooth module features:

# hcitool info <bd_addr>
Requesting information ...
BD Address: <bd_addr>
Device Name: Topik
LMP Version: 2.0 (0x3) LMP Subversion: 0x2222
Manufacturer: Broadcom Corporation (15)
Features: 0xbf 0xee 0x0f 0x4e 0x98 0x19 0x00 0x00
<3-slot> <5-slot> <encryption> <slot>
<timing> <role> <sniff> <rssi>
<channel> <sco> <hv3> <u-law>
<a-law> <cvsd> <paging> <power>
<transparent> <edr> <edr>
<enhanced> <inquiry> <afh>
<afh> <3-slot> <5-slot>
<afh> <afh>

Debian and its packages:

ii  bluez  4.42-2         Bluetooth tools and daemons
ii ppp 2.4.4rel-10.1 Point-to-Point Protocol (PPP) - daemon
Optional:
ii  bluez-hcidump  1.42-1+b1     Analyses Bluetooth HCI packets

Environment check

Check if the kernel loaded any Bluetooth modules:

$ lsmod | grep bt
btusb 10276 2
bluetooth 47060 9 bnep,sco,rfcomm,l2cap,btusb
usbcore 125888 9 btusb,usbhid,snd_usb_audio,snd_usb_lib,uvcvideo,usb_storage,uhci_hcd,ehci_hcd

During this experiment it's useful to keep hcidump running. It may help in debugging process or at least provide handful of information on sent packets.

For the beginning hciconfig:

$ /usr/sbin/hciconfig
hci0: Type: USB
BD Address: 00:15:AF:F8:EA:75 ACL MTU: 1021:8 SCO MTU: 64:1
UP RUNNING PSCAN
RX bytes:56525 acl:734 sco:0 events:1053 errors:0
TX bytes:21903 acl:752 sco:0 commands:335 errors:0
We can see our local PC Bluetooth interface.


Now, let's search for mobile devices in proximity (it's a good moment to turn Bluetooth on in the cell phone):

$ hcitool scan
Scanning ...
<bd_addr> Topik
We can see our mobile. We get the information about its BD_ADDR (Bluetooth Device Address) which is a cousin of the Ethernet MAC addresses.

Now using the SDP protocol (special protocol for service discovery) we will know what we can do with our cell.

$ sdptool browse <the BD_ADDR from the previous section>
[...]
Service Name: Dial-Up Networking
Service RecHandle: 0x1004c
Service Class ID List:
"Dialup Networking" (0x1103)
Protocol Descriptor List:
"L2CAP" (0x0100)
"RFCOMM" (0x0003)
Channel: 4
Language Base Attr List:
code_ISO639: 0x454e
encoding: 0x6a
base_offset: 0x100
Profile Descriptor List:
"Dialup Networking" (0x1103)
Version: 0x0100
[...]
You can see we can establish an Internet connection via the mobile. By the way, please notice which channel Dial-Up Networking (DUN) service and profile uses (Channel: 4).

It's convenient to create a script which is going to detect the right channel before every connection. Services' channels may change after turning the phone off and on again. The getDUNchannel.sh script:

#!/bin/sh

MAC=$1

if [ "$1" ]; then
MAC="--bdaddr $MAC"
fi

sdptool search $MAC DUN | grep Channel: | grep -o '[0-9]*'

Preparing for the connection

Firstly, we are going to configure an element which we are going to use last - pppd. This is a configuration for the PlusGSM network, for other networks it's similar or even the same - you can always ask your operator for assistance.

pppd

/etc/ppp/peers/plus:

connect "/usr/sbin/chat -v -f /etc/chatscripts/plus"
debug
/dev/rfcomm0
115200
defaultroute
noipdefault
usepeerdns
noauth

/etc/chatscripts/plus:

ABORT BUSY ABORT 'NO CARRIER' ABORT VOICE ABORT 'NO DIALTONE' ABORT 'NO DIAL TONE' ABORT 'NO ANSWER' ABORT DELAYED
'' ATZ
OK-AT-OK AT+CGDCONT=1,"IP","internet"
OK-AT-OK "ATDT*99#"
CONNECT ''

bluetooth-agent

During devices pairing a PIN code (chosen by the user) is needed. It's going to be entered on both devices. Tools from the bluez package have their agent called bluetooth-agent. They request a PIN code from it if they need one.

rfcomm

Application is called rfcomm, same as the protocol stack layer which it provides. This is a layer that emulates a RS-232 port in Bluetooth devices. Thanks to that feature we can communicate with the mobile as we would with a modem.

Rfcomm can read configuration from /etc/bluetooth/rfcomm.conf, but I can't find any advantages of this solution. Channel for the DUN service is going to change, so we want it to be easy to provide during execution. That is why we're going to pass all the arguments via the command line.

Starting sequence

In a couple of terminals execute in sequence:
  1. During the first connection (pairing process) rfcomm will need a PIN agent.
    bluetooth-agent <wybrany PIN>
    It will print PIN requests on the screen. This tool won't be needed during subsequent connections, because a key is going to be generated (based on BD_ADDR, PIN and a random part), which both devices will remember.
  2. $ rfcomm connect 0 <bd_addr> `./getDUNchannel.sh <bd_addr>`
    We should get an emulated RS-232 port /dev/rfcomm0.
  3. Upon success we should see:
    Connected /dev/rfcomm0 to <bd_addr> on channel 4
    Press CTRL-C for hangup
  4. pppd file /etc/ppp/peers/plus
    Via tail -f /var/log/syslog we can watch what's happening.
And that's it.

Literature

Literature is a big word but I've used these sites:

Brak komentarzy:

Publikowanie komentarza