aboutsummaryrefslogtreecommitdiff
path: root/keyboards/bioi/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'keyboards/bioi/main.c')
-rw-r--r--keyboards/bioi/main.c388
1 files changed, 388 insertions, 0 deletions
diff --git a/keyboards/bioi/main.c b/keyboards/bioi/main.c
new file mode 100644
index 000000000..7c8922c0a
--- /dev/null
+++ b/keyboards/bioi/main.c
@@ -0,0 +1,388 @@
1/*
2Copyright 2019 Basic I/O Instruments(Scott Wei) <[email protected]>
3This program is free software: you can redistribute it and/or modify
4it under the terms of the GNU General Public License as published by
5the Free Software Foundation, either version 2 of the License, or
6(at your option) any later version.
7This program is distributed in the hope that it will be useful,
8but WITHOUT ANY WARRANTY; without even the implied warranty of
9MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10GNU General Public License for more details.
11You should have received a copy of the GNU General Public License
12along with this program. If not, see <http://www.gnu.org/licenses/>.
13*/
14
15#include <avr/pgmspace.h>
16#include <util/delay.h>
17
18#include "report.h"
19#include "host.h"
20#include "host_driver.h"
21#include "keyboard.h"
22#include "action.h"
23#include "led.h"
24#include "sendchar.h"
25#include "debug.h"
26#include "print.h"
27#ifdef SLEEP_LED_ENABLE
28#include "sleep_led.h"
29#endif
30#include "suspend.h"
31
32#include "usb_descriptor.h"
33#include "lufa.h"
34#include "quantum.h"
35#include <util/atomic.h>
36
37#ifdef NKRO_ENABLE
38#include "keycode_config.h"
39
40extern keymap_config_t keymap_config;
41#endif
42
43#ifdef AUDIO_ENABLE
44#include <audio.h>
45#endif
46
47#ifdef BLUETOOTH_ENABLE
48#ifdef MODULE_ADAFRUIT_BLE
49#include "adafruit_ble.h"
50#else
51#include "bluetooth.h"
52#endif
53#endif
54
55#ifdef VIRTSER_ENABLE
56#include "virtser.h"
57#endif
58
59#if (defined(RGB_MIDI) | defined(RGBLIGHT_ANIMATIONS)) & defined(RGBLIGHT_ENABLE)
60#include "rgblight.h"
61#endif
62
63#ifdef MIDI_ENABLE
64#include "qmk_midi.h"
65#endif
66
67#ifdef RAW_ENABLE
68#include "raw_hid.h"
69#endif
70
71#include "ble.h"
72#include "usart.h"
73
74#include <avr/power.h>
75#include <avr/sleep.h>
76
77bool force_usb = false; //Reserved for FORCE USB Mode function.
78bool force_ble = false; //Reserved for FORCE USB Mode function.
79
80bool usb_connected = false;
81bool ble_enabled = false;
82
83uint32_t kb_idle_timer = 0;
84
85bool usb_state_sent = false;
86
87uint8_t USB_DeviceLastState = 0;
88
89#ifdef RAW_ENABLE
90/** \brief Raw HID Task
91 *
92 * FIXME: Needs doc
93 */
94static void raw_hid_task(void)
95{
96 // Create a temporary buffer to hold the read in data from the host
97 uint8_t data[RAW_EPSIZE];
98 bool data_read = false;
99
100 // Device must be connected and configured for the task to run
101 if (USB_DeviceState != DEVICE_STATE_Configured)
102 return;
103
104 Endpoint_SelectEndpoint(RAW_OUT_EPNUM);
105
106 // Check to see if a packet has been sent from the host
107 if (Endpoint_IsOUTReceived())
108 {
109 // Check to see if the packet contains data
110 if (Endpoint_IsReadWriteAllowed())
111 {
112 /* Read data */
113 Endpoint_Read_Stream_LE(data, sizeof(data), NULL);
114 data_read = true;
115 }
116
117 // Finalize the stream transfer to receive the last packet
118 Endpoint_ClearOUT();
119
120 if (data_read)
121 {
122 raw_hid_receive(data, sizeof(data));
123 }
124 }
125}
126#endif
127
128static void setup_mcu(void)
129{
130 /* Disable watchdog if enabled by bootloader/fuses */
131 MCUSR &= ~(1 << WDRF);
132 wdt_disable();
133
134 CLKPR = (1 << CLKPCE);
135 CLKPR = (0 << CLKPS3) | (0 << CLKPS2) | (0 << CLKPS1) | (0 << CLKPS0);
136}
137
138static void setup_usb(void)
139{
140 // Leonardo needs. Without this USB device is not recognized.
141 USB_Disable();
142
143 USB_Init();
144
145 // for Console_Task
146 USB_Device_EnableSOFEvents();
147 print_set_sendchar(sendchar);
148}
149
150void power_saving(void)
151{
152 power_adc_disable();
153 power_usart0_disable();
154 power_spi_disable();
155 power_twi_disable();
156
157 USBCON |= (1 << FRZCLK); // Freeze the USB Clock
158 PLLCSR &= ~(1 << PLLE); // Disable the USB Clock (PPL)
159 USBCON &= ~(1 << USBE);
160}
161
162void power_recover(void)
163{
164
165 USBCON |= (1 << USBE);
166 PLLCSR |= (1 << PLLE); // Resume the USB Clock (PPL)
167 USBCON &= ~(1 << FRZCLK); // Resume the USB Clock
168
169 power_adc_enable();
170 power_usart0_enable();
171 power_spi_enable();
172 power_twi_enable();
173}
174
175void ble_task_init(void)
176{
177 kb_idle_timer = timer_read32(); //Mark current time, reserved for further usage;
178}
179
180void ble_task(void)
181{
182
183 if (USB_DeviceLastState != USB_DeviceState)
184 {
185 usb_state_sent = false;
186#ifdef BLE_DEBUG
187 send_str(PSTR("USB State Changed\r\n"));
188 if (USB_DeviceState == DEVICE_STATE_Unattached)
189 {
190 send_str(PSTR("USB State Unattached\r\n"));
191 }
192#endif
193 if (USB_DeviceState == DEVICE_STATE_Powered)
194 {
195#ifdef BLE_DEBUG
196 send_str(PSTR("USB State Powered\r\n"));
197#endif
198 power_recover();
199 host_set_driver(&null_driver);
200 }
201#ifdef BLE_DEBUG
202 if ((USB_DeviceState == DEVICE_STATE_Default))
203 {
204 send_str(PSTR("USB State Default\r\n"));
205 }
206 if ((USB_DeviceState == DEVICE_STATE_Addressed))
207 {
208 send_str(PSTR("USB State Addressed\r\n"));
209 }
210 if (USB_DeviceState == DEVICE_STATE_Configured)
211 {
212 send_str(PSTR("USB State Configured\r\n"));
213 }
214 if (USB_DeviceState > DEVICE_STATE_Unattached)
215 {
216 }
217 else
218 {
219 //
220 }
221#endif
222 }
223 else
224 {
225#ifdef BLE_DEBUG
226 if (!usb_state_sent)
227 {
228 if (USB_DeviceState == DEVICE_STATE_Unattached)
229 {
230 send_str(PSTR("USB State Stopped at Unattached\r\n"));
231 }
232 if (USB_DeviceState == DEVICE_STATE_Powered)
233 {
234 send_str(PSTR("USB State Stopped at Powered\r\n"));
235 }
236 if ((USB_DeviceState == DEVICE_STATE_Default))
237 {
238 send_str(PSTR("USB State Stopped at Default\r\n"));
239 }
240 if ((USB_DeviceState == DEVICE_STATE_Addressed))
241 {
242 send_str(PSTR("USB State Stopped at Addressed\r\n"));
243 }
244 if (USB_DeviceState == DEVICE_STATE_Configured)
245 {
246 send_str(PSTR("USB State Stopped at Configured\r\n"));
247 }
248 }
249#endif
250 if (USB_DeviceState == DEVICE_STATE_Unattached)
251 {
252 if (host_get_driver() && host_get_driver() != &bluefruit_driver)
253 {
254#ifdef BLE_DEBUG
255 send_str(PSTR("USB State stopped at Unattached\r\n"));
256#endif
257 ble_task_init();
258
259 force_usb = 0;
260 usb_connected = 0;
261
262 //Reinit USB to prepare for next connection.
263 USB_Init();
264 USB_Detach();
265 USB_Attach();
266
267#ifdef BLE_DEBUG
268 send_str(PSTR("Loading &bluefruit_driver\r\n"));
269#endif
270 host_set_driver(&bluefruit_driver);
271 clear_keyboard();
272 power_saving();
273 }
274 else
275 {
276 //Do nothing if USB is unattached and the driver is &bluefruit_driver
277 }
278 }
279 if (USB_DeviceState == DEVICE_STATE_Configured)
280 {
281 if (host_get_driver() && host_get_driver() != &lufa_driver)
282 {
283#ifdef BLE_DEBUG
284 send_str(PSTR("USB State stopped at Configured\r\n"));
285#endif
286 power_recover();
287
288 usb_connected = 1;
289 ble_enabled = 0;
290#ifdef BLE_DEBUG
291 send_str(PSTR("Loading &lufa_driver\r\n"));
292#endif
293 host_set_driver(&lufa_driver);
294 clear_keyboard();
295 }
296 else
297 {
298 //Do nothing if the driver is &lufa_driver
299 }
300 }
301
302 usb_state_sent = true;
303 }
304
305 USB_DeviceLastState = USB_DeviceState;
306}
307
308// Use a custom main() function because the task logic is different from the common one.
309int main(void)
310{
311#ifdef MIDI_ENABLE
312 setup_midi();
313#endif
314
315 setup_mcu();
316
317 keyboard_setup();
318
319 setup_usb();
320 sei();
321
322#if defined(MODULE_ADAFRUIT_EZKEY) || defined(MODULE_RN42)
323 serial_init();
324#endif
325
326 /* wait for USB startup to get ready for debug output */
327 uint8_t timeout = 255; // timeout when USB is not available(Bluetooth)
328 while (timeout-- && USB_DeviceState != DEVICE_STATE_Configured)
329 {
330 wait_ms(4);
331#if defined(INTERRUPT_CONTROL_ENDPOINT)
332 ;
333#else
334 USB_USBTask();
335#endif
336 }
337
338 print("\nUSB init\n");
339
340 keyboard_init();
341 host_set_driver(&lufa_driver);
342
343 backlight_disable();
344 //host_set_driver(&lufa_driver);
345 print("Keyboard initialized.\n");
346
347 //Init Hardware UART
348 usart_init();
349
350#ifdef BLE_DEBUG
351 send_str(PSTR("Keyboard has been setup up\r\n"));
352
353 if (usb_connected)
354 {
355 send_str(PSTR("usb_connected=1\r\n"));
356 }
357 else
358 {
359 send_str(PSTR("usb_connected=0\r\n"));
360 }
361#endif
362
363#ifdef SLEEP_LED_ENABLE
364 sleep_led_init();
365#endif
366
367#ifdef VIRTSER_ENABLE
368 virtser_init();
369#endif
370
371 while (1)
372 {
373 ble_task();
374 keyboard_task();
375
376#ifdef RAW_ENABLE
377 raw_hid_task();
378#endif
379
380#if defined(RGBLIGHT_ANIMATIONS) && defined(RGBLIGHT_ENABLE)
381 rgblight_task();
382#endif
383
384#if !defined(INTERRUPT_CONTROL_ENDPOINT)
385 USB_USBTask();
386#endif
387 }
388}