35 #if defined(PIOS_INCLUDE_HMC5883)
42 #define HMC5883_TASK_PRIORITY PIOS_THREAD_PRIO_HIGHEST
43 #define HMC5883_TASK_STACK_BYTES 512
44 #define PIOS_HMC5883_MAX_DOWNSAMPLE 1
49 enum pios_hmc5883_dev_magic {
50 PIOS_HMC5883_DEV_MAGIC = 0x3d8e17ab,
57 struct pios_thread *
task;
59 enum pios_hmc5883_dev_magic
magic;
65 static int32_t PIOS_HMC5883_Read(uint8_t address, uint8_t * buffer, uint8_t len);
66 static int32_t PIOS_HMC5883_Write(uint8_t address, uint8_t buffer);
67 static void PIOS_HMC5883_Task(
void *parameters);
69 static struct hmc5883_dev *dev;
74 static struct hmc5883_dev * PIOS_HMC5883_alloc(
void)
76 struct hmc5883_dev *hmc5883_dev;
78 hmc5883_dev = (
struct hmc5883_dev *)
PIOS_malloc(
sizeof(*hmc5883_dev));
79 if (!hmc5883_dev)
return (NULL);
81 hmc5883_dev->magic = PIOS_HMC5883_DEV_MAGIC;
84 if (hmc5883_dev->queue == NULL) {
96 static int32_t PIOS_HMC5883_Validate(
struct hmc5883_dev *dev)
100 if (dev->magic != PIOS_HMC5883_DEV_MAGIC)
102 if (dev->i2c_id == 0)
113 dev = (
struct hmc5883_dev *) PIOS_HMC5883_alloc();
118 dev->i2c_id = i2c_id;
122 #ifndef PIOS_HMC5883_NO_EXTI
130 dev->data_ready_sema = NULL;
134 if (PIOS_HMC5883_Config(cfg) != 0)
139 dev->task =
PIOS_Thread_Create(PIOS_HMC5883_Task,
"pios_hmc5883", HMC5883_TASK_STACK_BYTES, NULL, HMC5883_TASK_PRIORITY);
152 if (PIOS_HMC5883_Validate(dev) != 0)
155 dev->orientation = orientation;
240 static uint16_t PIOS_HMC5883_Config_GetSensitivity()
242 switch (dev->cfg->Gain) {
271 if (PIOS_HMC5883_Validate(dev) != 0)
279 uint8_t buffer_read[6];
283 uint8_t buffer_write[2] = {
293 .len =
sizeof(addr_read),
300 .len =
sizeof(buffer_read),
307 .len =
sizeof(buffer_write),
315 int16_t mag_x, mag_y, mag_z;
316 uint16_t sensitivity = PIOS_HMC5883_Config_GetSensitivity();
317 mag_x = ((int16_t) ((uint16_t)buffer_read[0] << 8) + buffer_read[1]) * 1000 / sensitivity;
318 mag_z = ((int16_t) ((uint16_t)buffer_read[2] << 8) + buffer_read[3]) * 1000 / sensitivity;
319 mag_y = ((int16_t) ((uint16_t)buffer_read[4] << 8) + buffer_read[5]) * 1000 / sensitivity;
322 switch (dev->orientation) {
324 mag_data->
x = -mag_x;
326 mag_data->
z = -mag_z;
329 mag_data->
x = -mag_y;
330 mag_data->
y = -mag_x;
331 mag_data->
z = -mag_z;
335 mag_data->
y = -mag_y;
336 mag_data->
z = -mag_z;
341 mag_data->
z = -mag_z;
344 mag_data->
x = -mag_x;
345 mag_data->
y = -mag_y;
350 mag_data->
y = -mag_x;
359 mag_data->
x = -mag_y;
374 static uint8_t PIOS_HMC5883_ReadID(uint8_t out[4])
391 static int32_t PIOS_HMC5883_Read(uint8_t address, uint8_t * buffer, uint8_t
len)
393 if(PIOS_HMC5883_Validate(dev) != 0)
396 uint8_t addr_buffer[] = {
405 .len =
sizeof(addr_buffer),
429 static int32_t PIOS_HMC5883_Write(uint8_t address, uint8_t buffer)
431 if(PIOS_HMC5883_Validate(dev) != 0)
461 PIOS_HMC5883_ReadID((uint8_t *)
id);
462 if((
id[0] !=
'H') || (
id[1] !=
'4') || (
id[2] !=
'3'))
471 #ifndef PIOS_HMC5883_NO_EXTI
474 if (PIOS_HMC5883_Validate(dev) != 0)
487 static void PIOS_HMC5883_Task(
void *parameters)
489 while (PIOS_HMC5883_Validate(dev) != 0) {
493 uint32_t sample_delay;
495 switch (dev->cfg->M_ODR) {
497 sample_delay = 1000 / 0.75f + 0.99999f;
500 sample_delay = 1000 / 1.5f + 0.99999f;
503 sample_delay = 1000 / 3.0f + 0.99999f;
506 sample_delay = 1000 / 7.5f + 0.99999f;
509 sample_delay = 1000 / 15.0f + 0.99999f;
512 sample_delay = 1000 / 30.0f + 0.99999f;
516 sample_delay = 1000 / 75.0f + 0.99999f;
533 if (PIOS_HMC5883_ReadMag(&mag_data) == 0)
uint32_t PIOS_Thread_Systime(void)
#define PIOS_HMC5883_GAIN_5_6
const struct pios_exti_cfg * exti_cfg
#define PIOS_HMC5883_MODE_REG
#define PIOS_HMC5883_ODR_1_5
struct pios_queue * PIOS_Queue_Create(size_t queue_length, size_t item_size)
#define PIOS_SEMAPHORE_TIMEOUT_MAX
int32_t PIOS_HMC5883_SetOrientation(enum pios_hmc5883_orientation orientation)
#define PIOS_HMC5883_ODR_75
Main PiOS header to include all the compiled in PiOS options.
#define PIOS_HMC5883_GAIN_1_3
int32_t PIOS_HMC5883_Test(void)
int32_t PIOS_EXTI_Init(const struct pios_exti_cfg *cfg)
#define PIOS_HMC5883_MODE_CONTINUOUS
void * PIOS_malloc(size_t size)
bool PIOS_Queue_Send(struct pios_queue *queuep, const void *itemp, uint32_t timeout_ms)
bool PIOS_Semaphore_Give_FromISR(struct pios_semaphore *sema, bool *woken)
bool PIOS_HMC5883_IRQHandler()
#define PIOS_HMC5883_DATAOUT_IDA_REG
#define PIOS_HMC5883_ODR_15
#define PIOS_HMC5883_ODR_7_5
#define PIOS_HMC5883_GAIN_4_0
#define PIOS_HMC5883_CONFIG_REG_B
uint8_t data[XFER_BYTES_PER_PACKET]
static struct flyingpicmd_cfg_fa cfg
struct pios_semaphore * PIOS_Semaphore_Create(void)
Creates a binary semaphore.
struct pios_i2c_adapter * pios_i2c_t
struct pios_thread * PIOS_Thread_Create(void(*fp)(void *), const char *namep, size_t stack_bytes, void *argp, enum pios_thread_prio_e prio)
#define PIOS_HMC5883_GAIN_2_5
int32_t PIOS_SENSORS_Register(enum pios_sensor_type type, struct pios_queue *queue)
Register a queue-based sensor with the PIOS_SENSORS interface.
static TaskInfoRunningElem task
#define PIOS_HMC5883_GAIN_1_9
int32_t PIOS_I2C_Transfer(pios_i2c_t i2c_id, const struct pios_i2c_txn txn_list[], uint32_t num_txns)
#define PIOS_HMC5883_GAIN_4_7
void PIOS_Thread_Sleep_Until(uint32_t *previous_ms, uint32_t increment_ms)
void PIOS_free(void *buf)
void PIOS_Thread_Sleep(uint32_t time_ms)
#define PIOS_HMC5883_ODR_30
Pios sensor structure for generic mag data.
int32_t PIOS_HMC5883_Init(pios_i2c_t i2c_id, const struct pios_hmc5883_cfg *cfg)
#define PIOS_HMC5883_DATAOUT_XMSB_REG
bool PIOS_Semaphore_Take(struct pios_semaphore *sema, uint32_t timeout_ms)
Takes binary semaphore.
#define PIOS_HMC5883_CONFIG_REG_A
#define PIOS_HMC5883_I2C_ADDR
static struct pios_queue * queue
enum pios_hmc5883_orientation Default_Orientation
#define PIOS_HMC5883_GAIN_0_88
#define PIOS_HMC5883_ODR_3
#define PIOS_Assert(test)
#define PIOS_HMC5883_ODR_0_75
#define PIOS_HMC5883_GAIN_8_1