JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 11:27 am

Hi everyone,

Firstly, my apologies as this is a bit of a long post. I just wanted to show that I have covered all the bases I could find.

I have followed the Interfacing Digital Compass (HMC5883L) With Raspberry Pi 2 Using Python3 instructable in an attempt to get my GY-271 HMC5883L working on my Raspberry Pi B+. When I run the provided code...

Code: Select all

from i2clibraries import i2c_hmc5883l

hmc5883l = i2c_hmc5883l.i2c_hmc5883l(1) #choosing which i2c port to use, RPi2 model B uses port 1

hmc5883l.setContinuousMode()

hmc5883l.setDeclination(0,6) #type in the magnetic declination of your location in the bracket (degrees, minute)

print(hmc5883l)

...python3 returns the following;

Code: Select all

Traceback (most recent call last):
  File "quickcompass.py", line 3, in <module>
    hmc5883l = i2c_hmc5883l.i2c_hmc5883l(1) #choosing which i2c port to use, RPi2 model B uses port 1
  File "/home/pi/code/blade/quick2wire-python-api/i2clibraries/i2c_hmc5883l.py", line 29, in __init__
    self.setScale(gauss)
  File "/home/pi/code/blade/quick2wire-python-api/i2clibraries/i2c_hmc5883l.py", line 76, in setScale
    self.setOption(self.ConfigurationRegisterB, self.scale_reg)
  File "/home/pi/code/blade/quick2wire-python-api/i2clibraries/i2c_hmc5883l.py", line 87, in setOption
    self.bus.write_byte(register, options)
  File "/home/pi/code/blade/quick2wire-python-api/i2clibraries/i2c.py", line 14, in write_byte
    writing_bytes(self.addr, *bytes))
  File "/home/pi/code/blade/quick2wire-python-api/quick2wire/i2c.py", line 78, in transaction
    ioctl(self.fd, I2C_RDWR, ioctl_arg)
OSError: [Errno 121] Remote I/O error
I then turned to bitify, who provided this code which I modified for python3 and the Raspberry Pi B+. I also read the comments and made a suggested alteration to the byte writes.

Code: Select all

#!/usr/bin/python
import smbus
import time
import math

bus = smbus.SMBus(1)
address = 0x0d


def read_byte(adr):
    return bus.read_byte_data(address, adr)

def read_word(adr):
    high = bus.read_byte_data(address, adr)
    low = bus.read_byte_data(address, adr+1)
    val = (high << 8) + low
    return val

def read_word_2c(adr):
    val = read_word(adr)
    if (val >= 0x8000):
        return -((65535 - val) + 1)
    else:
        return val

def write_byte(adr, value):
    bus.write_byte_data(address, adr, value)

# write_byte(0, 0b01110000) # Set to 8 samples @ 15Hz
# write_byte(1, 0b00100000) # 1.3 gain LSb / Gauss 1090 (default)
# write_byte(2, 0b00000000) # Continuous sampling

# write_byte amendment as suggested by Valentin Barral
write_byte(0, 0b00000000)
write_byte(1, 0b1111111)
write_byte(2, 0b00000000)

scale = 0.92

x_out = read_word_2c(3) * scale
y_out = read_word_2c(7) * scale
z_out = read_word_2c(5) * scale

bearing  = math.atan2(y_out, x_out) 
if (bearing < 0):
    bearing += 2 * math.pi

print ("Bearing: ", math.degrees(bearing))
When I run this, no errors are thrown but instead, 0.00 is returned no matter which way I turn the compass. I thought that I may have bricked the first compass I purchased, so I purchased another and got the same results; heading of 0 no matter what.

When I run

Code: Select all

sudo i2cdetect -y 1
it returns the following

Image

When I run

Code: Select all

sudo i2cget -y 1 0x0d 0x75
the following is returned.

Code: Select all

0xff
I suspect that the compass is not bricked since it appears to be responding, however, I cannot figure out how to get some useful data from it! Any suggestions?

Thanks!

James
Last edited by JamesGeddes on Thu May 25, 2017 1:26 pm, edited 1 time in total.

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 1:16 pm

You should be using SMBus(1) not SMBus(0).

If that doesn't work for a noddy script try http://abyz.co.uk/rpi/pigpio/examples.h ... MC5883L_py

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 2:09 pm

joan wrote:You should be using SMBus(1) not SMBus(0).
Yes, that was a typo. In my copy, I had already set it to 1 but still zeros being returned. Changed the 0 to a 1 here.
joan wrote:If that doesn't work for a noddy script try http://abyz.co.uk/rpi/pigpio/examples.h ... MC5883L_py
Tried that script, but it too is returning 0 0 0

What am I doing wrong?

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 2:13 pm

A photo of the wiring may show.

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 2:21 pm

Will find a camera but for the time being;
VCC --> Pin 4
GND --> Pin 6
SCL --> Pin 5
SDA --> Pin 3

User avatar
bensimmo
Posts: 3344
Joined: Sun Dec 28, 2014 3:02 pm
Location: East Yorkshire

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 2:38 pm

I've done this a few months back, used the notify.
Ignored a lot of the original I2C other than installing tools and setting I2C on in raspi-config (since that does the hard work).

I altered to Python3, iirc it was just print statements and firing 'int' 'float' etc where needed.

It worked fine.

However mine connected to 3V3 not 5V.
VCC - Pin1

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 2:53 pm

Using 3V3 for power will be much safer.

The I2C address of 0x0D appears wrong, mine is at 0x1E.

Have you soldered the pins to the module or are you using loose wires? If you haven't soldered the pins in place that can lead to all sorts of strange problems with I2C.

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 4:15 pm

Have now moved VCC to pin 1 as advised.
bensimmo wrote:I altered to Python3, iirc it was just print statements and firing 'int' 'float' etc where needed.
It worked fine.
Sorry, I'm not sure I understand. Could you elaborate, please?
joan wrote:The I2C address of 0x0D appears wrong, mine is at 0x1E.
I'm not sure what to say really, that's the output I'm getting
joan wrote:Have you soldered the pins to the module or are you using loose wires? If you haven't soldered the pins in place that can lead to all sorts of strange problems with I2C.
Pins are soldered, then inserted into breadboard.
Last edited by JamesGeddes on Thu May 25, 2017 4:23 pm, edited 2 times in total.

User avatar
bensimmo
Posts: 3344
Joined: Sun Dec 28, 2014 3:02 pm
Location: East Yorkshire

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 4:27 pm

The maths calculations needed altering as it threw up errors. At least I think it did. Ignore if it didn't for you.

If Joan's code didn't work then something is wrong with the board or you initial setup..

What did you do to set up I2C.
Do you just turn it on or did you alter some files too?

(I'm no expert, I just know what I did for some I2C parts.)

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 4:45 pm

I followed the instructions on instructables and bitify to set up I2C. Is there a better guide? Perhaps I did something wrong.

The code that Joan recommended does not throw errors, it just returns 0 as the other script does.

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 4:50 pm

JamesGeddes wrote:I followed the instructions on instructables and bitify to set up I2C. Is there a better guide? Perhaps I did something wrong.

The code that Joan recommended does not throw errors, it just returns 0 as the other script does.
That's the odd thing. That code is hard wired to use address 0x1E. Something must be responding on 0x1E or an error code would be returned, not 0. Or did you change the address to 0x0D?

Could you cut&paste sample output?

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 4:55 pm

Perhaps you have got a QMC5883L.

See viewtopic.php?p=1102197#p1102197

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 5:06 pm

I changed the address to match the address I have been getting.

Code: Select all

#!/usr/bin/env python

# i2c_HMC5883L.py
# 2015-04-01
# Public Domain

import time
import struct
import sys

import pigpio # http://abyz.co.uk/rpi/pigpio/python.html

if sys.version > '3':
   buffer = memoryview

BUS=1

HMC5883L_I2C_ADDR=0x0d

RUNTIME=60.0

pi=pigpio.pi() # open local Pi

h = pi.i2c_open(BUS, HMC5883L_I2C_ADDR)

if h >= 0: # Connected OK?

   # Initialise HMC5883L.
   pi.i2c_write_byte_data(h, 0x00, 0xF8)  # CRA 75Hz.
   pi.i2c_write_byte_data(h, 0x02, 0x00)  # Mode continuous reads.

   read = 0

   start_time = time.time()

   while (time.time()-start_time) < RUNTIME:

      # 0x3 = X MSB, 0x4 = X LSB
      # 0x5 = Y MSB, 0x6 = Y LSB
      # 0x7 = Z MSB, 0x8 = Z LSB

      # > = big endian

      (s, b) = pi.i2c_read_i2c_block_data(h, 0x03, 6)

      if s >= 0:
         (x, y, z) = struct.unpack('>3h', buffer(b))
         print("{} {} {}".format(x, y, z))
         read += 1
         time.sleep(1)

   pi.i2c_close(h)

pi.stop()

print(read, read/RUNTIME)


Output
Image

If I change the HMC5883L_I2C_ADDR=0x1e then it returns 'I2C write failed'

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 5:09 pm

joan wrote:Perhaps you have got a QMC5883L.

See viewtopic.php?p=1102197#p1102197
I purchased this item from amazon

http://amzn.to/2qZATRf

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 5:14 pm

JamesGeddes wrote:
joan wrote:Perhaps you have got a QMC5883L.

See viewtopic.php?p=1102197#p1102197
I purchased this item from amazon

http://amzn.to/2qZATRf
They probably wouldn't know themselves.

It's the only thing which explains the software talking to a device on 0x0D (the address of the QMC). The HMC address is 0x1E.

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 5:31 pm

Urgh. I clearly thought too highly of manufacturers. I have contacted the Amazon seller in order to get some direction from them.

Does the unit I have actually work? If so, how? If not, does anyone got any recommendations for digital compasses that do?

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 6:02 pm

Yes, it does work. It may even be a better chip for all I know. I thought the last post in the thread I linked gave details.

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 7:32 pm

joan wrote:I thought the last post in the thread I linked gave details.
Perhaps I'm missing something, however, it would appear that the general consensus of that thread is that the unit I have is a fake. They don't seem to discuss how to get it working.

If anyone has any ideas on how to get this one working, I would be really grateful as I purchased two!

User avatar
bensimmo
Posts: 3344
Joined: Sun Dec 28, 2014 3:02 pm
Location: East Yorkshire

Re: GY-271 HMC5883L Compass Returning 0

Thu May 25, 2017 8:07 pm

I'm guessing, from scanning that thread, that you'll need to read the documentation linked and use the registers given.

One of the bitify topics has an explanation of registers if you need it (I certainly did)
http://blog.bitify.co.uk/2013/11/readin ... berry.html

It's a different device but it explains what, why, how etc.
Last edited by bensimmo on Fri May 26, 2017 11:14 am, edited 1 time in total.

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Fri May 26, 2017 7:54 am

bensimmo wrote:It's a different device but it explains what, why, how etc.
Awesome, thanks!

I have just heard back from the Amazon seller, who had this to say;
Dear Customer,

Thanks for your reminder.
Sorry, we don't know "HMC5883L" is *not *an HMC5883L.
Purchased from our supplier. We will contact our supplier for the products.
Have applied for a full for the two units, and have removed the product.
Please check.

Kind regards,
HALJIA
I am looking forward to getting my money back! I will do my best to get these dodgy units working, but I do also have a (hopefully) decent unit on the way, so we'll see what works out. Thanks for your help, everyone!

JamesGeddes
Posts: 23
Joined: Fri Oct 31, 2014 12:45 am

Re: GY-271 HMC5883L Compass Returning 0

Fri May 26, 2017 3:24 pm

Just found out that RS Components sell (what I hope is) the real HMC5883L! It's a little more expensive than the one I found on Amazon, plus I trust RS far more than I trust random Amazon sellers, so hopefully, this one should just work with the code provided.

Thanks again for your help everyone, this has been a good reminder that the world of knock-offs is not just limited to handbags and sunglasses. Additionally, buy cheap, buy twice!

User avatar
joan
Posts: 13582
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: GY-271 HMC5883L Compass Returning 0

Fri May 26, 2017 3:44 pm

The HMC5883L will be of little use to you unless you are great at soldering tiny components (what is it, something like 3mm by 3mm) and can design and build all the support circuitry.

User avatar
Niccolo
Posts: 19
Joined: Mon Dec 14, 2015 8:45 am
Contact: Website

Re: GY-271 HMC5883L Compass Returning 0

Sun Oct 14, 2018 10:36 pm

Hi to all, I just write here because this post was one of the first I found when searching a driver for the QMC5883L on the Raspberry Pi.
Indeed the QMC5883L chip is different, the code for the HMC5883L does not work. Some software I found for the QMC5883L (also published on Pypi.org) does not work at all.
So I wrote a little driver for the QMC5883L and published it here: https://github.com/RigacciOrg/py-qmc5883l
Using it is quite simple and it gives very stable data:

Code: Select all

#!/usr/bin/python
import time
import py_qmc5883l
sensor = py_qmc5883l.QMC5883L()
while True:
    print sensor.get_magnet()
    time.sleep(0.2)

Return to “Advanced users”