summaryrefslogtreecommitdiffstats
path: root/firmware/export
diff options
context:
space:
mode:
authorAidan MacDonald <amachronic@protonmail.com>2021-12-05 14:30:03 +0000
committerAidan MacDonald <amachronic@protonmail.com>2021-12-28 15:20:27 +0000
commit2d891439623bb76d38b98202ca5f3eea3c01c5f0 (patch)
tree50e52529843835d057bd07b4797545da2b0e4d9e /firmware/export
parentb774699560dc37db272d122cb140e73dd08b643b (diff)
downloadrockbox-2d891439623bb76d38b98202ca5f3eea3c01c5f0.tar.gz
rockbox-2d891439623bb76d38b98202ca5f3eea3c01c5f0.zip
AXP PMU rewrite (again)
I noticed a few mistakes in the old driver code and it was in need of an overhaul anyway... I decided to scale things back, simplify the code and remove most of the debug menus, netting a nice code size savings. One new feature is an advanced debug menu which is accessible by recompiling the code with AXP_EXTRA_DEBUG. It adds quite a bit of code size and isn't useful other than for development so it must be manually enabled by editing the source. Change-Id: I30e17c1194c14823decd726a574ed14451d4cb2d
Diffstat (limited to 'firmware/export')
-rw-r--r--firmware/export/axp-pmu.h151
-rw-r--r--firmware/export/axp192-defs.h308
-rw-r--r--firmware/export/axp192.h131
3 files changed, 439 insertions, 151 deletions
diff --git a/firmware/export/axp-pmu.h b/firmware/export/axp-pmu.h
deleted file mode 100644
index 457f746e8c..0000000000
--- a/firmware/export/axp-pmu.h
+++ /dev/null
@@ -1,151 +0,0 @@
-/***************************************************************************
- * __________ __ ___.
- * Open \______ \ ____ ____ | | _\_ |__ _______ ___
- * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
- * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
- * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
- * \/ \/ \/ \/ \/
- * $Id$
- *
- * Copyright (C) 2021 Aidan MacDonald
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version 2
- * of the License, or (at your option) any later version.
- *
- * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
- * KIND, either express or implied.
- *
- ****************************************************************************/
-
-#ifndef __AXP_PMU_H__
-#define __AXP_PMU_H__
-
-#include "config.h"
-#include <stdbool.h>
-#include <stdint.h>
-
-/* ADC channels */
-#define ADC_ACIN_VOLTAGE 0
-#define ADC_ACIN_CURRENT 1
-#define ADC_VBUS_VOLTAGE 2
-#define ADC_VBUS_CURRENT 3
-#define ADC_INTERNAL_TEMP 4
-#define ADC_TS_INPUT 5
-#define ADC_BATTERY_VOLTAGE 6
-#define ADC_CHARGE_CURRENT 7
-#define ADC_DISCHARGE_CURRENT 8
-#define ADC_APS_VOLTAGE 9
-#define ADC_BATTERY_POWER 10
-#define NUM_ADC_CHANNELS 11
-
-/* ADC sampling rates */
-#define AXP_ADC_RATE_25HZ 0
-#define AXP_ADC_RATE_50HZ 1
-#define AXP_ADC_RATE_100HZ 2
-#define AXP_ADC_RATE_200HZ 3
-
-/* Return values of axp_battery_status() */
-#define AXP_BATT_DISCHARGING 0
-#define AXP_BATT_CHARGING 1
-#define AXP_BATT_FULL 2
-
-/* Bits returned by axp_input_status() */
-#define AXP_INPUT_AC (1 << 0)
-#define AXP_INPUT_USB (1 << 1)
-#define AXP_INPUT_BATTERY (1 << 2)
-#define AXP_INPUT_EXTERNAL (AXP_INPUT_AC|AXP_INPUT_USB)
-
-/* Power supplies known by this driver. Not every chip has all supplies! */
-#define AXP_SUPPLY_DCDC1 0
-#define AXP_SUPPLY_DCDC2 1
-#define AXP_SUPPLY_DCDC3 2
-#define AXP_SUPPLY_LDO1 3
-#define AXP_SUPPLY_LDO2 4
-#define AXP_SUPPLY_LDO3 5
-#define AXP_SUPPLY_LDO_IO0 6
-#define AXP_NUM_SUPPLIES 7
-
-/* Special values returned by axp_supply_get_voltage */
-#define AXP_SUPPLY_NOT_PRESENT INT_MIN
-#define AXP_SUPPLY_DISABLED (-1)
-
-/* Registers -- common to AXP173 and AXP192 (incomplete listing) */
-#define AXP_REG_POWERSTATUS 0x00
-#define AXP_REG_CHARGESTATUS 0x01
-#define AXP_REG_CHIP_ID 0x03
-#define AXP_REG_PWROUTPUTCTRL1 0x10
-#define AXP_REG_PWROUTPUTCTRL2 0x12
-#define AXP_REG_SHUTDOWNLEDCTRL 0x32
-#define AXP_REG_CHARGECONTROL1 0x33
-#define AXP_REG_DCDCWORKINGMODE 0x80
-#define AXP_REG_ADCENABLE1 0x82
-#define AXP_REG_ADCENABLE2 0x83
-#define AXP_REG_ADCSAMPLERATE 0x84
-#define AXP_REG_COULOMBCOUNTERBASE 0xb0
-#define AXP_REG_COULOMBCOUNTERCTRL 0xb8
-
-/* AXP192-only registers (incomplete listing) */
-#define AXP192_REG_GPIO0FUNCTION 0x90
-#define AXP192_REG_GPIO1FUNCTION 0x92
-#define AXP192_REG_GPIO2FUNCTION 0x93
-#define AXP192_REG_GPIOSTATE1 0x94
-
-/* Must be called from power_init() to initialize the driver state */
-extern void axp_init(void);
-
-/* - axp_supply_set_voltage(): set a supply voltage to the given value
- * in millivolts. Pass a voltage of AXP_SUPPLY_DISABLED to shut off
- * the supply. Any invalid supply or voltage will make the call a no-op.
- *
- * - axp_supply_get_voltage() returns a supply voltage in millivolts.
- * If the supply is powered off, returns AXP_SUPPLY_DISABLED.
- * If the chip does not have the supply, returns AXP_SUPPLY_NOT_PRESENT.
- */
-extern void axp_supply_set_voltage(int supply, int voltage);
-extern int axp_supply_get_voltage(int supply);
-
-/* Basic battery and power supply status */
-extern int axp_battery_status(void);
-extern int axp_input_status(void);
-
-/* ADC access -- ADCs which are not enabled will return INT_MIN if read.
- * The output of axp_adc_read() is normalized to appropriate units:
- *
- * - for voltages, the scale is millivolts
- * - for currents, the scale is milliamps
- * - for temperatures, the scale is tenths of a degree Celsius
- * - for power, the scale is microwatts
- *
- * See the comment in axp_adc_conv_raw() for raw value precision/scale.
- */
-extern int axp_adc_read(int adc);
-extern int axp_adc_read_raw(int adc);
-extern int axp_adc_conv_raw(int adc, int value);
-extern int axp_adc_get_enabled(void);
-extern void axp_adc_set_enabled(int adc_bits);
-extern int axp_adc_get_rate(void);
-extern void axp_adc_set_rate(int rate);
-
-/* - axp_cc_read() reads the coulomb counters
- * - axp_cc_clear() resets both counters to zero
- * - axp_cc_enable() will stop/start the counters running
- * - axp_cc_is_enabled() returns true if the counters are running
- */
-extern void axp_cc_read(uint32_t* charge, uint32_t* discharge);
-extern void axp_cc_clear(void);
-extern void axp_cc_enable(bool en);
-extern bool axp_cc_is_enabled(void);
-
-/* Set/get maximum charging current in milliamps */
-extern void axp_set_charge_current(int maxcurrent);
-extern int axp_get_charge_current(void);
-
-/* Set the shutdown bit */
-extern void axp_power_off(void);
-
-/* Debug menu */
-extern bool axp_debug_menu(void);
-
-#endif /* __AXP_PMU_H__ */
diff --git a/firmware/export/axp192-defs.h b/firmware/export/axp192-defs.h
new file mode 100644
index 0000000000..13b465351b
--- /dev/null
+++ b/firmware/export/axp192-defs.h
@@ -0,0 +1,308 @@
+/* Internal header for axp192 driver - not for general inclusion */
+
+#ifndef DEFREG
+# define DEFREG(...)
+#endif
+#ifndef DEFFLD
+# define DEFFLD(...)
+#endif
+
+#define DEFBIT(regname, fldname, bitpos, ...) \
+ DEFFLD(regname, fldname, bitpos, bitpos, __VA_ARGS__)
+
+DEFREG(PWRSTS, 0x00)
+DEFREG(CHGSTS, 0x01)
+DEFREG(CHIPID, 0x03)
+DEFREG(VBUSSTS, 0x04)
+DEFREG(DATA0, 0x06)
+DEFREG(DATA1, 0x07)
+DEFREG(DATA2, 0x08)
+DEFREG(DATA3, 0x09)
+DEFREG(DATA4, 0x0a)
+DEFREG(DATA5, 0x0b)
+DEFREG(PWRCTL1, 0x10)
+DEFREG(PWRCTL2, 0x12)
+DEFREG(DCDC2VOLT, 0x23)
+DEFREG(DCDC2RAMP, 0x25)
+DEFREG(DCDC1VOLT, 0x26)
+DEFREG(DCDC3VOLT, 0x27)
+DEFREG(LDO2LDO3VOLT, 0x28)
+DEFREG(VBUSIPSOUT, 0x30)
+DEFREG(VOFF, 0x31)
+DEFREG(PWROFF, 0x32)
+DEFREG(CHGCTL1, 0x33)
+DEFREG(CHGCTL2, 0x34)
+DEFREG(BKPCHGCTL, 0x35)
+DEFREG(PEKPARAM, 0x36)
+DEFREG(DCDCFREQ, 0x37)
+DEFREG(VLTFCHG, 0x38)
+DEFREG(VHTFCHG, 0x39)
+DEFREG(APSLOW1, 0x3a)
+DEFREG(APSLOW2, 0x3b)
+DEFREG(VLTFDCHG, 0x3c)
+DEFREG(VHTFDCHG, 0x3d)
+DEFREG(IRQEN1, 0x40)
+DEFREG(IRQEN2, 0x41)
+DEFREG(IRQEN3, 0x42)
+DEFREG(IRQEN4, 0x43)
+DEFREG(IRQSTS1, 0x44)
+DEFREG(IRQSTS2, 0x45)
+DEFREG(IRQSTS3, 0x46)
+DEFREG(IRQSTS4, 0x47)
+DEFREG(IRQEN5, 0x4a)
+DEFREG(IRQSTS5, 0x4d)
+DEFREG(DCDCMODE, 0x80)
+DEFREG(ADCEN1, 0x82)
+DEFREG(ADCEN2, 0x83)
+DEFREG(ADCCTL, 0x84)
+DEFREG(ADCRANGE, 0x85)
+DEFREG(TIMERCTL, 0x8a)
+DEFREG(VBUSSRP, 0x8b)
+DEFREG(OTPOWEROFF, 0x8f)
+DEFREG(GPIO0FUNC, 0x90)
+DEFREG(GPIO0LDO, 0x91)
+DEFREG(GPIO1FUNC, 0x92)
+DEFREG(GPIO2FUNC, 0x93)
+DEFREG(GPIOLEVEL1, 0x94)
+DEFREG(GPIO3GPIO4FUNC, 0x95)
+DEFREG(GPIOLEVEL2, 0x96)
+DEFREG(GPIOPULL, 0x97)
+DEFREG(PWM1X, 0x98)
+DEFREG(PWM1Y1, 0x99)
+DEFREG(PWM1Y2, 0x9a)
+DEFREG(PWM2X, 0x9b)
+DEFREG(PWM2Y1, 0x9c)
+DEFREG(PWM2Y2, 0x9d)
+DEFREG(NRSTO, 0x9e)
+DEFREG(CC_CTL, 0xb8)
+
+DEFBIT(PWRSTS, ACIN_PRESENT, 7)
+DEFBIT(PWRSTS, ACIN_VALID, 6)
+DEFBIT(PWRSTS, VBUS_PRESENT, 5)
+DEFBIT(PWRSTS, VBUS_VALID, 4)
+DEFBIT(PWRSTS, VBUS_VHOLD, 3)
+DEFBIT(PWRSTS, BATT_CURR_DIR, 2)
+DEFBIT(PWRSTS, PCB_SHORTED, 1)
+DEFBIT(PWRSTS, BOOT_TRIG, 0)
+
+DEFBIT(VBUSSTS, VALID, 2)
+DEFBIT(VBUSSTS, SESS_AB_VALID, 1)
+DEFBIT(VBUSSTS, SESS_END, 0)
+
+DEFBIT(CHGSTS, OVER_TEMP, 7)
+DEFBIT(CHGSTS, CHARGING, 6)
+DEFBIT(CHGSTS, BATT_PRESENT, 5)
+DEFBIT(CHGSTS, BATT_ERROR, 3)
+DEFBIT(CHGSTS, LOW_CHARGE, 2)
+
+/* NOTE: These two bits are mirrored in the upper nibble of PWRCTL2.
+ * Modifications through one register will immediately reflect in the
+ * other register. */
+DEFBIT(PWRCTL1, EXTEN_SW, 2)
+DEFBIT(PWRCTL1, DCDC2_SW, 0)
+
+DEFBIT(PWRCTL2, EXTEN_SW, 6)
+DEFBIT(PWRCTL2, DCDC2_SW, 4)
+DEFBIT(PWRCTL2, LDO3_SW, 3)
+DEFBIT(PWRCTL2, LDO2_SW, 2)
+DEFBIT(PWRCTL2, DCDC3_SW, 1)
+DEFBIT(PWRCTL2, DCDC1_SW, 0)
+
+DEFFLD(DCDC2VOLT, VALUE, 5, 0)
+
+DEFBIT(DCDC2RAMP, ENABLE, 2)
+DEFBIT(DCDC2RAMP, SLOPE, 0)
+
+DEFFLD(DCDC1VOLT, VALUE, 6, 0)
+DEFFLD(DCDC3VOLT, VALUE, 6, 0)
+
+DEFFLD(LDO2LDO3VOLT, LDO2_VALUE, 7, 4)
+DEFFLD(LDO2LDO3VOLT, LDO3_VALUE, 3, 0)
+
+DEFBIT(VBUSIPSOUT, ACCESS, 7)
+DEFBIT(VBUSIPSOUT, VHOLD_LIM, 6)
+DEFFLD(VBUSIPSOUT, VHOLD_LEV, 5, 3)
+DEFBIT(VBUSIPSOUT, VBUS_LIM, 1)
+DEFBIT(VBUSIPSOUT, LIM_100mA, 0)
+
+DEFFLD(VOFF, VALUE, 3, 0)
+
+DEFBIT(PWROFF, SHUTDOWN, 7)
+DEFBIT(PWROFF, MON_EN, 6)
+DEFFLD(PWROFF, LEDFUNC, 5, 4)
+DEFBIT(PWROFF, LEDCTL, 3)
+DEFBIT(PWROFF, DELAY, 1, 0)
+
+DEFBIT(CHGCTL1, CHARGE_EN, 7)
+DEFFLD(CHGCTL1, CHARGE_TGT, 6, 5)
+DEFBIT(CHGCTL1, CHARGE_ENDCURR, 4)
+DEFFLD(CHGCTL1, CHARGE_CURRENT, 3, 0)
+
+DEFFLD(CHGCTL2, PRECHARGE_OT, 7, 6)
+DEFFLD(CHGCTL2, EACCESS_CURRENT, 5, 3)
+DEFBIT(CHGCTL2, EACCESS_CHG_EN, 2)
+DEFFLD(CHGCTL2, CONST_CURR_OT, 1, 0)
+
+DEFBIT(BKPCHGCTL, ENABLE, 7)
+DEFFLD(BKPCHGCTL, TGT_VOLTAGE, 6, 5)
+DEFFLD(BKPCHGCTL, CHARGE_CURRENT, 1, 0)
+
+DEFFLD(PEKPARAM, POWER_ON_TIME, 7, 6)
+DEFFLD(PEKPARAM, LONG_TIME, 5, 4)
+DEFBIT(PEKPARAM, POWEROFF_EN, 3)
+DEFBIT(PEKPARAM, PWROK_DELAY, 2)
+DEFFLD(PEKPARAM, POWEROFF_TIME, 1, 0)
+
+DEFFLD(DCDCFREQ, VALUE, 3, 0)
+DEFFLD(VLTFCHG, VALUE, 7, 0)
+DEFFLD(VHTFCHG, VALUE, 7, 0)
+DEFFLD(APSLOW1, VALUE, 7, 0)
+DEFFLD(APSLOW2, VALUE, 7, 0)
+DEFFLD(VLTFDCHG, VALUE, 7, 0)
+DEFFLD(VHTFDCHG, VALUE, 7, 0)
+
+DEFBIT(IRQEN1, ACIN_OVER_VOLTAGE, 7)
+DEFBIT(IRQEN1, ACIN_INSERT, 6)
+DEFBIT(IRQEN1, ACIN_REMOVE, 5)
+DEFBIT(IRQEN1, VBUS_OVER_VOLTAGE, 4)
+DEFBIT(IRQEN1, VBUS_INSERT, 3)
+DEFBIT(IRQEN1, VBUS_REMOVE, 2)
+DEFBIT(IRQEN1, VBUS_BELOW_VHOLD, 1)
+DEFBIT(IRQEN2, BATTERY_INSERT, 7)
+DEFBIT(IRQEN2, BATTERY_REMOVE, 6)
+DEFBIT(IRQEN2, BATTERY_ERROR, 5)
+DEFBIT(IRQEN2, BATTERY_ERROR_CLR, 4)
+DEFBIT(IRQEN2, CHARGING_STARTED, 3)
+DEFBIT(IRQEN2, CHARGING_COMPLETE, 2)
+DEFBIT(IRQEN2, BATTERY_OVER_TEMP, 1)
+DEFBIT(IRQEN2, BATTERY_UNDER_TEMP, 0)
+DEFBIT(IRQEN3, INTERNAL_OVER_TEMP, 7)
+DEFBIT(IRQEN3, LOW_CHARGE_CURRENT, 6)
+DEFBIT(IRQEN3, DCDC1_UNDER_VOLT, 5)
+DEFBIT(IRQEN3, DCDC2_UNDER_VOLT, 4)
+DEFBIT(IRQEN3, DCDC3_UNDER_VOLT, 3)
+DEFBIT(IRQEN3, SHORT_PRESS, 1)
+DEFBIT(IRQEN3, LONG_PRESS, 0)
+DEFBIT(IRQEN4, POWER_ON_N_OE, 7)
+DEFBIT(IRQEN4, POWER_OFF_N_OE, 6)
+DEFBIT(IRQEN4, VBUS_VALID, 5)
+DEFBIT(IRQEN4, VBUS_INVALID, 4)
+DEFBIT(IRQEN4, VBUS_SESS_AB, 3)
+DEFBIT(IRQEN4, VBUS_SESS_END, 2)
+DEFBIT(IRQEN4, APS_UNDER_VOLT, 0)
+
+DEFBIT(IRQSTS1, ACIN_OVER_VOLTAGE, 7)
+DEFBIT(IRQSTS1, ACIN_INSERT, 6)
+DEFBIT(IRQSTS1, ACIN_REMOVE, 5)
+DEFBIT(IRQSTS1, VBUS_OVER_VOLTAGE, 4)
+DEFBIT(IRQSTS1, VBUS_INSERT, 3)
+DEFBIT(IRQSTS1, VBUS_REMOVE, 2)
+DEFBIT(IRQSTS1, VBUS_BELOW_VHOLD, 1)
+DEFBIT(IRQSTS2, BATTERY_INSERT, 7)
+DEFBIT(IRQSTS2, BATTERY_REMOVE, 6)
+DEFBIT(IRQSTS2, BATTERY_ERROR, 5)
+DEFBIT(IRQSTS2, BATTERY_ERROR_CLR, 4)
+DEFBIT(IRQSTS2, CHARGING_STARTED, 3)
+DEFBIT(IRQSTS2, CHARGING_STOPPED, 2)
+DEFBIT(IRQSTS2, BATTERY_OVER_TEMP, 1)
+DEFBIT(IRQSTS2, BATTERY_UNDER_TEMP, 0)
+DEFBIT(IRQSTS3, INTERNAL_OVER_TEMP, 7)
+DEFBIT(IRQSTS3, LOW_CHARGE_CURRENT, 6)
+DEFBIT(IRQSTS3, DCDC1_UNDER_VOLT, 5)
+DEFBIT(IRQSTS3, DCDC2_UNDER_VOLT, 4)
+DEFBIT(IRQSTS3, DCDC3_UNDER_VOLT, 3)
+DEFBIT(IRQSTS3, SHORT_PRESS, 1)
+DEFBIT(IRQSTS3, LONG_PRESS, 0)
+DEFBIT(IRQSTS4, POWER_ON_N_OE, 7)
+DEFBIT(IRQSTS4, POWER_OFF_N_OE, 6)
+DEFBIT(IRQSTS4, VBUS_VALID, 5)
+DEFBIT(IRQSTS4, VBUS_INVALID, 4)
+DEFBIT(IRQSTS4, VBUS_SESS_AB, 3)
+DEFBIT(IRQSTS4, VBUS_SESS_END, 2)
+DEFBIT(IRQSTS4, APS_UNDER_VOLT, 0)
+
+/* NOTE: IRQEN5 and IRQSTS5 are only listed on the Chinese datasheet. */
+DEFBIT(IRQEN5, TIME_OUT, 7)
+DEFBIT(IRQEN5, GPIO2_CHANGE, 2)
+DEFBIT(IRQEN5, GPIO1_CHANGE, 1)
+DEFBIT(IRQEN5, GPIO0_CHANGE, 0)
+
+DEFBIT(IRQSTS5, TIME_OUT, 7)
+DEFBIT(IRQSTS5, GPIO2_CHANGE, 2)
+DEFBIT(IRQSTS5, GPIO1_CHANGE, 1)
+DEFBIT(IRQSTS5, GPIO0_CHANGE, 0)
+
+DEFFLD(DCDCMODE, VALUE, 3, 1)
+
+DEFBIT(ADCEN1, BATTERY_VOLTAGE, 7)
+DEFBIT(ADCEN1, BATTERY_CURRENT, 6)
+DEFBIT(ADCEN1, ACIN_VOLTAGE, 5)
+DEFBIT(ADCEN1, ACIN_CURRENT, 4)
+DEFBIT(ADCEN1, VBUS_VOLTAGE, 3)
+DEFBIT(ADCEN1, VBUS_CURRENT, 2)
+DEFBIT(ADCEN1, APS_VOLTAGE, 1)
+DEFBIT(ADCEN1, TS_PIN, 0)
+
+DEFBIT(ADCEN2, INTERNAL_TEMP, 7)
+DEFBIT(ADCEN2, GPIO0, 3)
+DEFBIT(ADCEN2, GPIO1, 2)
+DEFBIT(ADCEN2, GPIO2, 1)
+DEFBIT(ADCEN2, GPIO3, 0)
+
+DEFFLD(ADCCTL, SAMPLE_RATE, 7, 6)
+DEFFLD(ADCCTL, TS_OUT_CURR, 5, 4)
+DEFBIT(ADCCTL, TS_FUNCTION, 2)
+DEFFLD(ADCCTL, TS_OUT_MODE, 1, 0)
+
+DEFBIT(ADCRANGE, GPIO3HIGH, 3)
+DEFBIT(ADCRANGE, GPIO2HIGH, 2)
+DEFBIT(ADCRANGE, GPIO1HIGH, 1)
+DEFBIT(ADCRANGE, GPIO0HIGH, 0)
+
+DEFBIT(TIMERCTL, TIMEOUT, 7)
+DEFFLD(TIMERCTL, DURATION, 6, 0)
+
+DEFFLD(VBUSSRP, VBUSVALID_VOLTAGE, 5, 4)
+DEFBIT(VBUSSRP, VBUSVALID_MONITOR, 3)
+DEFBIT(VBUSSRP, VBUS_SESS_MONITOR, 2)
+DEFBIT(VBUSSRP, VBUS_DCHG_RESISTOR, 1)
+DEFBIT(VBUSSRP, VBUS_CHG_RESISTOR, 0)
+
+DEFBIT(OTPOWEROFF, ENABLE, 2)
+
+DEFFLD(GPIO0FUNC, VALUE, 2, 0)
+DEFFLD(GPIO0LDO, VALUE, 7, 4)
+DEFFLD(GPIO1FUNC, VALUE, 2, 0)
+DEFFLD(GPIO2FUNC, VALUE, 2, 0)
+
+DEFBIT(GPIOLEVEL1, IN2, 6)
+DEFBIT(GPIOLEVEL1, IN1, 5)
+DEFBIT(GPIOLEVEL1, IN0, 4)
+DEFBIT(GPIOLEVEL1, OUT2, 2)
+DEFBIT(GPIOLEVEL1, OUT1, 1)
+DEFBIT(GPIOLEVEL1, OUT0, 0)
+
+DEFFLD(GPIO3GPIO4FUNC, FUNC3, 3, 2)
+DEFFLD(GPIO3GPIO4FUNC, FUNC4, 1, 0)
+
+DEFBIT(GPIOLEVEL2, IN4, 5)
+DEFBIT(GPIOLEVEL2, IN3, 4)
+DEFBIT(GPIOLEVEL2, OUT4, 1)
+DEFBIT(GPIOLEVEL2, OUT3, 0)
+
+DEFBIT(GPIOPULL, PULL2, 2)
+DEFBIT(GPIOPULL, PULL1, 1)
+DEFBIT(GPIOPULL, PULL0, 0)
+
+DEFBIT(NRSTO, FUNC, 7)
+DEFBIT(NRSTO, GPIO_DIR, 6)
+DEFBIT(NRSTO, GPIO_OUT, 5)
+DEFBIT(NRSTO, GPIO_IN, 4)
+
+DEFBIT(CC_CTL, OPEN, 7)
+DEFBIT(CC_CTL, PAUSE, 6)
+DEFBIT(CC_CTL, CLEAR, 5)
+
+#undef DEFBIT
+#undef DEFFLD
+#undef DEFREG
diff --git a/firmware/export/axp192.h b/firmware/export/axp192.h
new file mode 100644
index 0000000000..6ed278d086
--- /dev/null
+++ b/firmware/export/axp192.h
@@ -0,0 +1,131 @@
+/***************************************************************************
+ * __________ __ ___.
+ * Open \______ \ ____ ____ | | _\_ |__ _______ ___
+ * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ /
+ * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < <
+ * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \
+ * \/ \/ \/ \/ \/
+ * $Id$
+ *
+ * Copyright (C) 2021 Aidan MacDonald
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY
+ * KIND, either express or implied.
+ *
+ ****************************************************************************/
+
+#ifndef __AXP192_H__
+#define __AXP192_H__
+
+#include <stdint.h>
+#include <stdbool.h>
+
+enum {
+#define DEFREG(regname, addr) AXP_REG_##regname = addr,
+#include "axp192-defs.h"
+};
+
+enum {
+#define DEFFLD(regname, fldname, msb, lsb, ...) \
+ BM_AXP_##regname##_##fldname = ((1 << ((msb) - (lsb) + 1)) - 1) << lsb, \
+ BP_AXP_##regname##_##fldname = lsb,
+#include "axp192-defs.h"
+};
+
+enum {
+ AXP_SUPPLY_EXTEN,
+ AXP_SUPPLY_DCDC1,
+ AXP_SUPPLY_DCDC2,
+ AXP_SUPPLY_DCDC3,
+ AXP_SUPPLY_LDO2,
+ AXP_SUPPLY_LDO3,
+ AXP_SUPPLY_LDOIO0,
+ AXP_NUM_SUPPLIES,
+};
+
+enum {
+ AXP_ADC_ACIN_VOLTAGE,
+ AXP_ADC_ACIN_CURRENT,
+ AXP_ADC_VBUS_VOLTAGE,
+ AXP_ADC_VBUS_CURRENT,
+ AXP_ADC_INTERNAL_TEMP,
+ AXP_ADC_TS_INPUT,
+ AXP_ADC_GPIO0,
+ AXP_ADC_GPIO1,
+ AXP_ADC_GPIO2,
+ AXP_ADC_GPIO3,
+ AXP_ADC_BATTERY_VOLTAGE,
+ AXP_ADC_CHARGE_CURRENT,
+ AXP_ADC_DISCHARGE_CURRENT,
+ AXP_ADC_APS_VOLTAGE,
+ AXP_NUM_ADCS,
+};
+
+enum {
+ AXP_GPIO_OPEN_DRAIN_OUTPUT = 0x0,
+ AXP_GPIO_INPUT = 0x1,
+ AXP_GPIO_SPECIAL = 0x2,
+ AXP_GPIO_ADC_IN = 0x4,
+ AXP_GPIO_LOW_OUTPUT = 0x5,
+ AXP_GPIO_FLOATING = 0x7,
+};
+
+enum {
+ /* Limit USB current consumption to 100 mA. */
+ AXP_VBUS_LIMIT_100mA = (1 << BP_AXP_VBUSIPSOUT_VHOLD_LIM) |
+ (1 << BP_AXP_VBUSIPSOUT_VBUS_LIM) |
+ (1 << BP_AXP_VBUSIPSOUT_LIM_100mA),
+
+ /* Limit USB current consumption to 500 mA. */
+ AXP_VBUS_LIMIT_500mA = (1 << BP_AXP_VBUSIPSOUT_VHOLD_LIM) |
+ (1 << BP_AXP_VBUSIPSOUT_VBUS_LIM) |
+ (0 << BP_AXP_VBUSIPSOUT_LIM_100mA),
+
+ /* No upper bound on USB current, but the current will still
+ * be reduced to maintain the bus voltage above V_hold. */
+ AXP_VBUS_UNLIMITED = (1 << BP_AXP_VBUSIPSOUT_VHOLD_LIM) |
+ (0 << BP_AXP_VBUSIPSOUT_VBUS_LIM) |
+ (0 << BP_AXP_VBUSIPSOUT_LIM_100mA),
+
+ /* Unlimited USB current consumption. Voltage is allowed to drop
+ * below V_hold, which may interfere with normal USB operation.
+ * This mode is really only useful with AC charging adapters. */
+ AXP_VBUS_FULLY_UNLIMITED = (0 << BP_AXP_VBUSIPSOUT_VHOLD_LIM) |
+ (0 << BP_AXP_VBUSIPSOUT_VBUS_LIM) |
+ (0 << BP_AXP_VBUSIPSOUT_LIM_100mA),
+};
+
+extern int axp_read(uint8_t reg);
+extern int axp_write(uint8_t reg, uint8_t value);
+extern int axp_modify(uint8_t reg, uint8_t clr, uint8_t set);
+
+extern void axp_enable_supply(int supply, bool enable);
+extern void axp_set_enabled_supplies(unsigned int supply_mask);
+extern void axp_set_supply_voltage(int supply, int output_mV);
+
+extern void axp_enable_adc(int adc, bool enable);
+extern void axp_set_enabled_adcs(unsigned int adc_mask);
+extern int axp_read_adc_raw(int adc);
+extern int axp_conv_adc(int adc, int value);
+extern int axp_read_adc(int adc);
+
+extern void axp_set_gpio_function(int gpio, int function);
+extern void axp_set_gpio_pulldown(int gpio, bool enable);
+extern int axp_get_gpio(int gpio);
+extern void axp_set_gpio(int gpio, bool enable);
+
+extern void axp_set_charge_current(int current_mA);
+extern int axp_get_charge_current(void);
+extern void axp_set_vbus_limit(int vbus_limit);
+extern void axp_set_vhold_level(int vhold_mV);
+extern bool axp_is_charging(void);
+extern unsigned int axp_power_input_status(void);
+
+extern void axp_power_off(void);
+
+#endif /* __AXP192_H__ */