Gyroscope problem - L3GD20H

Hi,

I have a little problem with figuring out how L3GD20H works. It shows quite random values, also when i read value of x-axis, by moving gyroscope randomly (not only around x-axis change his value. Isn’t it supose to change only if i move it around x-axis? (in situation when i read only x-axis register). Below is the code that i wrote. Thanks for all your help.

/*
 * zyroskop.c
 *
 *  Created on: 7 gru 2015
 *      Author: PC
 */

	#include "zyroskop.h"
	#include <avr/io.h>
    #include <avr/wdt.h>
    #include <util/delay.h>
    #include <avr/power.h>


	void Inicjacja(void)
    {
            TWCR &= ~(1<<TWIE);
            TWBR = 16;
            TWSR &= ~(1<<TWPS1) | (1<<TWPS0);
    }

    void Start(void)
    {
            TWCR = (1<<TWINT)|(1<<TWEN)|(1<<TWSTA);
            while(!(TWCR & (1<<TWINT)));
    }

    void Write(uint8_t address)
    {
            TWDR = address;
            TWCR = (1<<TWINT)|(1<<TWEN);
            while(!(TWCR&(1<<TWINT)));
    }

    void Read(void)
    {
            uint8_t zmienna=0;
            zmienna = TWDR;
            TWCR = (1<<TWINT)|(1<<TWEN);
            while(!(TWCR&(1<<TWINT)));
    }

    void Stop(void)
    {
            TWCR = (1<<TWINT)|(1<<TWEN)|(1<<TWSTO);
    }



void TWI_write_register(uint8_t address, uint8_t reg, uint8_t val)
{

Start(); // Send Start
Write(address); // Send IIC "Write" Address
Write(reg); // Send Register
Write(val); // Send Value
Stop(); // Send Stop
}

uint8_t TWI_read_register(uint8_t address, uint8_t reg)
{
            Start();
            Write(address); //adres slave
            //pisanie adresu rejestru
            Write(reg); //adres rejestru
            Start();
            Write(address+1); //adres slave+1


            Read();

            Stop();
			return TWDR;
}


void initgyro(void)
{
//	TWI_write_register(ADDR_WRITE,CTRL_Reg1,WriteCTRL1);

	TWI_write_register(gyroscope_W,CTRL1,0x7F);
	TWI_write_register(gyroscope_W,CTRL4,0x80);
}
/*
 * zyroskop.h
 *
 *  Created on: 7 gru 2015
 *      Author: PC
 */

#include <avr/io.h>

#ifndef ZYROSKOP_H_
#define ZYROSKOP_H_

#define WHO_AM_I 0x0F
#define gyroscope_W 0xD6
#define gyroscope_R 0xD7 // SA0 to + VDD through 10kOhm resistor, read

#define CTRL1 0x20
#define CTRL1REG 0x0F // 12,5 Hz (ODR), n.a. (cut-off[hz]), power mode normal, all axis enabled
#define CTRL2 0x21

#define CTRL3 0x22
#define CTRL4 0x23

#define CTRL5 0x24
#define CTRL6 0x25

#define OUT_X_L 0x28
#define OUT_X_H 0x29
#define OUT_Y_L 0x2A
#define OUT_Y_H 0x2B
#define OUT_Z_L 0x2C
#define OUT_Z_H 0x2D

#define FIFO_CTRL 0x2E
#define FIFO_SRC 0x2F


void initgyro(void);
void Inicjacja(void);
void Start(void);
void Write (uint8_t address);
void Read(void);
void Stop(void);
void TWI_write_register(uint8_t address, uint8_t reg, uint8_t val);
uint8_t TWI_read_register(uint8_t address, uint8_t reg);


#endif /* ZYROSKOP_H_ */
/*
 * main.c
 *
 *  Created on: 7 gru 2015
 *      Author: PC
 */


	#include <avr/pgmspace.h>
	#include <avr/eeprom.h>
    #include <avr/io.h>
    #include <avr/wdt.h>
    #include <util/delay.h>
    #include <avr/power.h>
	#include "zyroskop.h"
	#include "lcd.h"


int main()
{
	int Gx,Gy,Gz;

	unsigned char Gx1,Gx2,Gy1,Gy2,Gz1,Gz2;

	LCD_Initalize();
    LCD_Clear();

    Inicjacja();
	initgyro();

    while(1)
     {
    	  Gx1 =(unsigned char) TWI_read_register(gyroscope_W ,OUT_X_L);
          Gx2 =(unsigned char) TWI_read_register(gyroscope_W ,OUT_X_H);

          Gx = (int) (Gx2<<8) + Gx1;

          LCD_GoTo(0,0);

          lcd_int(Gx);
          _delay_ms(400);
     }
}

The L3GD20H is a rate gyroscope, not an accelerometer. Rate gyros measure the rate of rotation, and usually have a zero offset. That means that even when the gyroscope is not being rotated, it will output some value (the offset value will change slowly, with time and temperature).

Every time you start up and use the gyro, you need to determine the zero offset for each axis and subtract those offsets from subsequent measurements.

Hello.

Jim is correct. You should calculate the zero rate offset for each axis, and subtract it from your readings. You should also double-check to see if you are properly converting to units of dps. Then, if you are still concerned about your data, you can post your processed readings and code, and I could give you an idea of whether or not something could be amiss. If you were to post your code, it would also be helpful to know what microcontroller you are using, and how you are supplying power.

-Jon

Yeah, sorry i made a mistake, i mean gyroscope. Now it should be okey. I am using atmega 328p, voltage is from computer. Entire code that im using is already posted (without code of lcd which i am using to see values from gyroscope)