Use your GPS dongle with QGIS

So I had this GPS dongle laying on my table from the time I used TomTom on a Palm Treo (that is way before Android was alive) ...

my GPS bleutooth / USB dongle

It would be nice to make use of that GPS in combination with QGIS...

Configure with USB

How to connect that dongle as a USB device on my Debian running laptop.

It appears that attaching a GPS to your machine makes it appear as a serial device. When I plug in the GPS via an USB cable, and have a look with dmesg I see:

$ dmesg

[  616.535845] usb 1-1.4: USB disconnect, device number 4
[  640.802530] usb 1-1.2: new full-speed USB device number 8 using ehci-pci
[  640.898844] usb 1-1.2: New USB device found, idVendor=0e8d, idProduct=3329
[  640.898853] usb 1-1.2: New USB device strings: Mfr=3, Product=4, SerialNumber=0
[  640.898859] usb 1-1.2: Product: GPS Receiver
[  640.898863] usb 1-1.2: Manufacturer: MTK
[  640.919364] cdc_acm 1-1.2:1.1: ttyACM0: USB ACM device
[  640.920556] usbcore: registered new interface driver cdc_acm

As you see there is this line with ‘ttyACM0’, this means that it is available as a serial device at /dev/ttyACM0.

For a normal user to ‘read’ the output of information (actually NMEA: you have to have the right permissions:

$ ls -al /dev/ttyACM0
crw-rw---- 1 root dialout 166, 0 Jun 12 10:49 /dev/ttyACM0

Mmm, only root and members of the dialout group can read this:

$ sudo addgroup richard dialout
# and after a new login:
$ groups
richard tty dialout cdrom floppy

Now you can just read the stream that the gps is spitting out:

$ cat /dev/ttyACM0

As soon as you are able to see this, QGIS can use it too.

You want extra information? Try:

$ lsusb
Bus 001 Device 017: ID 0e8d:3329 MediaTek Inc. Qstarz BT-Q1000XT
Device Descriptor:
  bLength                18
  bDescriptorType         1
  bcdUSB               2.00
  bDeviceClass            2 Communications
  bDeviceSubClass         0
  bDeviceProtocol         0
  bMaxPacketSize0        64
  idVendor           0x0e8d MediaTek Inc.
  idProduct          0x3329 Qstarz BT-Q1000XT
  bcdDevice            1.00
  iManufacturer           3 MTK
  iProduct                4 GPS Receiver
etc etc...

Configure with Bluetooth

Another option is to use a Bluetooth connection.

The QGIS documentation about the actual connecting of the GPS is a little course, so I got most of my information from here:

First step: ‘pair’ your Dongle with your laptop (easiest via the Bleutooth settings).

Then you can use hcitool to scan for connected devices and find the device ID:

$ hcitool scan
Scanning ...
sdptool records 00:1C:88:12:A4:DB   Qstarz GPS

Given that ID, you can have a look on what channel your device is working:

$ sdptool records 00:1C:88:12:A4:DB
Service Name: SPP slave
Service RecHandle: 0x10000
Service Class ID List:
  "Serial Port" (0x1101)
Protocol Descriptor List:
  "L2CAP" (0x0100)
  "RFCOMM" (0x0003)
    Channel: 1
Language Base Attr List:
  code_ISO639: 0x656e
  encoding:    0x6a
  base_offset: 0x100

As you can see it is apparently using Channel 1 (while the thinkwiki example uses 3). Now you can bind the device:

$ rfcomm bind 0 00:1C:88:12:A4:DB 1
Can't create device: Operation not permitted

Mmm, only root can do that:

$ sudo rfcomm bind 0 00:1C:88:12:A4:DB 1
[sudo] password for richard:

$ ls -al /dev/rfcomm0
crw-rw---- 1 root dialout 216, 0 Jun 12 10:43 /dev/rfcomm0

Ok, same group, I’m already in that:

$ cat /dev/rfcomm0
$  <-- silence !

Another try:

$ cat /dev/rfcomm0

Bingo, now I can connect my GPS to my laptop using USB or Bluetooth.


The QGIS documentation shows you the diffrent screens for the GPS Information Panel.

So let me show you here the the connected dongle giving my home location using this dongle as a serial device on usb

gps connected to /dev/ttyACM0

And on bluetooth

gps connected to /dev/rfcomm0

Python and GPS

One question I had was if it would be possible to use this QGIS-GPS connection using Python. In that way you would be able to create a QGIS plugin which for example: could guide you to a borehole in the field, or give you live distances from certain locations or...

With the help of Nathan Woodrow on IRC I was able to write this tiny python script, to be copied into the Python console of QGIS:

from qgis.core import QgsGPSDetector, QgsGPSInformation

def gpsStateChanged(gpsInfo):
    # NMEA_FIX_BAD = 1 NMEA_FIX_2D = 2 NMEA_FIX_3D = 3
    if gpsInfo.fixType >= 2:
        print "lon: %s - lat: %s" % (gpsInfo.longitude, gpsInfo.latitude)
        print "bad gps status info or quality"

def gpsfound(gpsConnection):
    print "GPS connection found! Start listening to stateChanged events"

portname = "/dev/rfcomm0"  # or "scan"

detector = QgsGPSDetector(portname)
# connect the detected signal to our gpsfound function


# if all went wel (have a look into the debug messages) it should say something like:
#   trying to open file "/dev/rfcomm0"
#   file opened successfully
# and then spit out the lon - lat lines like:

output in Python console of QGIS connected GPS

Most of the logic and code come from Nathans code, see the code here:

For DMS (Digital Mapping Solutions) Nathan wrote ‘IntraMaps Roam’: “a simple data collection application built using QGIS”. It is a standalone python application build on QGIS libraries, to be used on (Windows) tablets.

Have a look on the Wiki and Roam Github repository to see what it looks like, and if you have a windows tablet: TRY it!

DMS Roam screenshot


Working directly with a serial device is tricky. It is easy to hang your terminal session or even your login session (or to say: that happened several times to me :-) ).

So probably safest is to use a ‘man in the middle’ like the gpsd deamon, which will do the dirty work like opening and closing serial connections etc.