--- /dev/null
+/*
+ * File: btn.h
+ *
+ * Generic button module. Understands the rocker switch and push button
+ * present on the rgb lamp board. Implements switch debounce in software.
+ *
+ * When a switch is enabled, a state change triggers the ISR. The ISR
+ * posts a timer task to wait a debounce period. When the timer fires,
+ * the ISR posts a task indicating a state change on the button. The
+ * user code, in its implementation of the task, should read the current
+ * state and take an action assuming that the state is different than it
+ * was before.
+ */
+
+#ifndef _BTN_H
+#define _BTN_H
+
+#include <htc.h>
+
+enum {
+ BTN_PB_DOWN = 0,
+ BTN_PB_UP,
+
+ BTN_RS_OFF = 0,
+ BTN_RS_LEFT,
+ BTN_RS_RIGHT,
+};
+
+/* Read the current state of the pushbutton */
+#define btn_pb() (RB0)
+
+/* Read the current state of the rocker switch */
+#define btn_rs() ((RB4 + ((unsigned char)RB5 << 1)) % 3)
+
+/* Enable the pushbutton from ISR */
+#define _btn_pben() do { \
+ IOCBP0 = 1; IOCBN0 = 1; IOCBF0 = 0; \
+ } while (0)
+
+/* Disable the pushbutton from ISR */
+#define _btn_pbdis() do { \
+ IOCBP0 = 0; IOCBN0 = 0; IOCBF0 = 0; \
+ } while (0)
+
+/* Enable the rocker switch from ISR */
+#define _btn_rsen() do { \
+ IOCBP4 = 1; IOCBN4 = 1; IOCBF4 = 0; \
+ IOCBP5 = 1; IOCBN5 = 1; IOCBF5 = 0; \
+ } while (0)
+
+/* Disable the rocker switch from ISR */
+#define _btn_rsdis() do { \
+ IOCBP4 = 0; IOCBN4 = 0; IOCBF4 = 0; \
+ IOCBP5 = 0; IOCBN5 = 0; IOCBF5 = 0; \
+ } while (0)
+
+/* Enable the pushbutton from user code */
+#define btn_pben() do { \
+ ndi(); \
+ _btn_pben(); \
+ nei(); \
+ } while (0)
+
+/* Disable the pushbutton from user code */
+#define btn_pbdis() do { \
+ ndi(); \
+ _btn_pbdis(); \
+ nei(); \
+ } while (0)
+
+/* Enable the rocker switch from user code */
+#define btn_rsen() do { \
+ ndi(); \
+ _btn_rsen(); \
+ nei(); \
+ } while (0)
+
+/* Disable the rocker switch from user code */
+#define btn_rsdis() do { \
+ ndi(); \
+ _btn_rsdis(); \
+ nei(); \
+ } while (0)
+
+/* Initialize the button module */
+void btn_init();
+
+/* This function must be called from the user interrupt function. */
+void btn_isr();
+
+#endif