From 87fba8d659d5947b40567766fd0a1451f38a9bc6 Mon Sep 17 00:00:00 2001
From: schneider <schneider@blinkenlichts.net>
Date: Fri, 5 Jul 2019 22:30:18 +0200
Subject: [PATCH] fix(pmic): Check pmic interrupt state from application
 context

Closes #13
---
 bootloader/bootloader-usb.c |  4 +++-
 epicardium/support.c        |  6 ++++++
 lib/card10/card10.c         |  4 ++++
 lib/card10/card10.h         |  1 +
 lib/card10/pmic.c           | 22 +++++++++++++++++-----
 lib/card10/pmic.h           |  1 +
 6 files changed, 32 insertions(+), 6 deletions(-)

diff --git a/bootloader/bootloader-usb.c b/bootloader/bootloader-usb.c
index 6dad89b3f..2e1bd9f32 100644
--- a/bootloader/bootloader-usb.c
+++ b/bootloader/bootloader-usb.c
@@ -51,7 +51,7 @@
 #include "msc.h"
 #include "descriptors.h"
 #include "mscmem.h"
-
+#include "card10.h"
 
 /***** Definitions *****/
 #define EVENT_ENUM_COMP     MAXUSB_NUM_EVENTS
@@ -212,6 +212,8 @@ void run_usbmsc(void)
                 printf("Remote Wakeup\n");
             }
         }
+
+        card10_poll();
     }
 }
 
diff --git a/epicardium/support.c b/epicardium/support.c
index 1504d1efb..957e787b8 100644
--- a/epicardium/support.c
+++ b/epicardium/support.c
@@ -7,6 +7,8 @@
 
 #include "api/dispatcher.h"
 
+#include "card10.h"
+
 extern TaskHandle_t dispatcher_task_id;
 
 /*
@@ -39,6 +41,10 @@ void post_idle_sleep(TickType_t xExpectedIdleTime)
 	if (api_dispatcher_poll_once()) {
 		xTaskNotifyGive(dispatcher_task_id);
 	}
+
+    // Do card10 house keeping. E.g. polling the i2c devices if they triggered an interrupt
+    // TODO: Do this in a more task fokused way (high/low ISR)
+    card10_poll();
 }
 
 void vApplicationGetIdleTaskMemory(
diff --git a/lib/card10/card10.c b/lib/card10/card10.c
index a2037ff9a..0b6b38fd5 100644
--- a/lib/card10/card10.c
+++ b/lib/card10/card10.c
@@ -185,3 +185,7 @@ void core1_stop(void) {
     MXC_GCR->perckcn1 |= MXC_F_GCR_PERCKCN1_CPU1;
 }
 
+void card10_poll(void)
+{
+    pmic_poll();
+}
diff --git a/lib/card10/card10.h b/lib/card10/card10.h
index b7c5b0630..e06b8a3f7 100644
--- a/lib/card10/card10.h
+++ b/lib/card10/card10.h
@@ -12,4 +12,5 @@ void card10_diag(void);
 void core1_start(void);
 void core1_stop(void);
 
+void card10_poll(void);
 #endif
diff --git a/lib/card10/pmic.c b/lib/card10/pmic.c
index 28feae708..30519a07c 100644
--- a/lib/card10/pmic.c
+++ b/lib/card10/pmic.c
@@ -9,11 +9,14 @@ static const gpio_cfg_t pmic_interrupt_pin = {
     PORT_0, PIN_12, GPIO_FUNC_IN, GPIO_PAD_PULL_UP
 };
 static pmic_button_callback_fn pmic_button_callback = NULL;
+static volatile bool interrupt_pending;
 
 void pmic_init(void)
 {
     uint8_t didm = MAX77650_getDIDM();
     uint8_t cid = MAX77650_getChipID();
+    interrupt_pending = false;
+
     printf("MAX7765x DIDM: 0x%02x CID: 0x%02x\n", didm, cid);
 
     MAX77650_setIP_SBB0(0b11);  //Limit switch current of SBB0 to 500mA for noise reduction
@@ -99,14 +102,23 @@ void pmic_init(void)
 
 static void pmic_interrupt_callback(void*_)
 {
-    uint8_t int_flag = MAX77650_getINT_GLBL();
+    interrupt_pending = true;
+}
 
-    if (int_flag & (MAX77650_INT_nEN_R | MAX77650_INT_nEN_F)) {
-        if (pmic_button_callback != NULL) {
-            (*pmic_button_callback)(int_flag & MAX77650_INT_nEN_F);
+void pmic_poll(void)
+{
+    if(interrupt_pending) {
+        /* There might be a race condition here. Don't care ATM. */
+        interrupt_pending = false;
+        uint8_t int_flag = MAX77650_getINT_GLBL();
+
+        if (int_flag & (MAX77650_INT_nEN_R | MAX77650_INT_nEN_F)) {
+            if (pmic_button_callback != NULL) {
+                (*pmic_button_callback)(int_flag & MAX77650_INT_nEN_F);
+            }
         }
+        /* TODO: Other pmic interrupts */
     }
-    /* TODO: Other pmic interrupts */
 }
 
 void pmic_set_button_callback(pmic_button_callback_fn cb)
diff --git a/lib/card10/pmic.h b/lib/card10/pmic.h
index 06874c289..fb522c15a 100644
--- a/lib/card10/pmic.h
+++ b/lib/card10/pmic.h
@@ -6,6 +6,7 @@
 
 void pmic_init(void);
 void pmic_set_led(uint8_t led, uint8_t val);
+void pmic_poll(void);
 
 typedef void (*pmic_button_callback_fn)(bool falling);
 void pmic_set_button_callback(pmic_button_callback_fn cb);
-- 
GitLab