Skip to content

Instantly share code, notes, and snippets.

@Franky1
Created May 3, 2022 13:21
Show Gist options
  • Save Franky1/47d496c2b25dbdef2b259d573a8c8458 to your computer and use it in GitHub Desktop.
Save Franky1/47d496c2b25dbdef2b259d573a8c8458 to your computer and use it in GitHub Desktop.
bq2022A example reading library for STM32 or other MCUs
#include <stdint.h>
#include <stdbool.h>
#include <stm32f0xx_ll_gpio.h>
const int tRST = 600;
const int tPPD = 40;
const int tPPmin = 60;
const int tRSTREC = 480;
const int tWSTRB = 7;
const int tWDH = 90;
const int tREC = 5;
const int tRSTRB = 7;
const int tODD = 13;
const int tODHO = 60;
const uint8_t cReadROM = 0x33;
const uint8_t cSkipROM = 0xCC;
const uint8_t cReadMemoryCRC = 0xC3;
#define GPIO_PORT GPIOA
#define GPIO_PIN LL_GPIO_PIN_1
static void BusyDelayMicroseconds(int us) {
// Overwrite your delay here; must be precise
while (us--) {
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
__ASM("NOP");
}
}
static uint8_t CRC8(uint8_t * ptr, int len) {
uint8_t result = 0;
while (len--) {
result ^= * ptr++;
for (uint8_t i = 0; i < 8; i++) {
if (result & 0x01)
result = (result >> 1) ^ 0x8C;
else
result >>= 1;
}
}
return result;
}
void Init() {
LL_GPIO_InitTypeDef GPIO_InitStruct;
GPIO_InitStruct.Pin = GPIO_PIN;
GPIO_InitStruct.Mode = LL_GPIO_MODE_ANALOG;
GPIO_InitStruct.Speed = LL_GPIO_SPEED_FREQ_LOW;
GPIO_InitStruct.OutputType = LL_GPIO_OUTPUT_OPENDRAIN;
GPIO_InitStruct.Pull = LL_GPIO_PULL_NO;
LL_GPIO_Init(GPIO_PORT, & GPIO_InitStruct);
}
static void Output(bool high) {
LL_GPIO_SetPinMode(GPIO_PORT, GPIO_PIN, LL_GPIO_MODE_OUTPUT);
if (high)
LL_GPIO_SetOutputPin(GPIO_PORT, GPIO_PIN);
else
LL_GPIO_ResetOutputPin(GPIO_PORT, GPIO_PIN);
}
static bool Input() {
LL_GPIO_SetPinMode(GPIO_PORT, GPIO_PIN, LL_GPIO_MODE_INPUT);
return (bool) LL_GPIO_IsInputPinSet(GPIO_PORT, GPIO_PIN);
}
static void Release() {
LL_GPIO_SetPinMode(GPIO_PORT, GPIO_PIN, LL_GPIO_MODE_ANALOG);
}
static void WriteBit(bool bit) {
Output(false);
BusyDelayMicroseconds(tWSTRB);
if (bit)
Output(true);
BusyDelayMicroseconds(tWDH - tWSTRB);
Output(true);
BusyDelayMicroseconds(tREC);
}
static bool ReadBit() {
Output(false);
BusyDelayMicroseconds(tRSTRB);
Release();
BusyDelayMicroseconds(tODD);
bool result = Input();
BusyDelayMicroseconds(tREC + tODHO - tODD);
return result;
}
static void WriteByte(uint8_t x) {
for (int i = 0; i < 8; i++) {
bool val = x & (1 << i);
WriteBit(val);
}
}
static uint8_t ReadByte() {
uint8_t result = 0;
for (int i = 0; i < 8; i++) {
bool val = ReadBit();
result |= (val << i);
}
return result;
}
ErrorStatus Reset() {
// Hard reset
Output(false);
BusyDelayMicroseconds(5000);
Release();
BusyDelayMicroseconds(5);
// Detect if the pin is pulled down unexpectedly
if (!Input())
return ERROR;
Output(true);
BusyDelayMicroseconds(100);
Output(false);
BusyDelayMicroseconds(tRST);
Output(true);
BusyDelayMicroseconds(tPPD);
Release();
BusyDelayMicroseconds(tPPmin);
// If input is low then chip is present
bool presence = !Input();
Output(true);
if (presence)
BusyDelayMicroseconds(tRSTREC - tPPmin - tPPD);
return presence ? SUCCESS : ERROR;
}
ErrorStatus ReadROM(uint8_t * buf) {
if (Reset() == ERROR)
return ERROR;
WriteByte(cReadROM);
const int len = 7;
for (int i = 0; i < len; i++) {
buf[i] = ReadByte();
}
uint8_t crc = ReadByte();
if (crc != CRC8(buf, len))
return ERROR;
return SUCCESS;
}
// page: 0-3
ErrorStatus ReadEPROM(uint8_t page, uint8_t * buf) {
if (Reset() == ERROR)
return ERROR;
WriteByte(cSkipROM);
uint8_t cmd[3];
cmd[0] = cReadMemoryCRC;
cmd[1] = 0x20 * page;
cmd[2] = 0;
for(int i = 0; i < 3; i++)
WriteByte(cmd[i]);
uint8_t crc1 = ReadByte();
if (CRC8(cmd, 3) != crc1)
return ERROR;
const int size = 32;
for (int i = 0; i < size; i++) {
buf[i] = ReadByte();
}
uint8_t crc2 = ReadByte();
if (CRC8(buf, size) != crc2)
return ERROR;
return SUCCESS;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment