From ab03b5b37726fb8b39a6f6c915f8668bddd779ee Mon Sep 17 00:00:00 2001 From: arighi Date: Tue, 27 Apr 2010 13:42:09 +0000 Subject: [PATCH] lm3s1968: merge the DevelGPS example application. The purpose of this project is to implement a portable GPS locator / geocaching finder tool using the Cortex-M3 based Luminary Micro LM3S1968 evaluation board. The device proposes a user interface to configure the GPS coordinates of a target location and shows on the OLED display the direction and distance to reach the target. git-svn-id: https://src.develer.com/svnoss/bertos/trunk@3542 38d2e660-2303-0410-9eaa-f027e97ec537 --- Makefile | 1 + examples/develgps/README | 56 +++ examples/develgps/cfg/cfg_adc.h | 110 +++++ examples/develgps/cfg/cfg_afsk.h | 114 +++++ examples/develgps/cfg/cfg_ax25.h | 76 +++ examples/develgps/cfg/cfg_battfs.h | 68 +++ examples/develgps/cfg/cfg_dataflash.h | 56 +++ examples/develgps/cfg/cfg_dc_motor.h | 67 +++ examples/develgps/cfg/cfg_debug.h | 55 +++ examples/develgps/cfg/cfg_fat.h | 140 ++++++ examples/develgps/cfg/cfg_flash25.h | 52 +++ examples/develgps/cfg/cfg_formatwr.h | 67 +++ examples/develgps/cfg/cfg_gfx.h | 74 +++ examples/develgps/cfg/cfg_heap.h | 51 +++ examples/develgps/cfg/cfg_i2c.h | 90 ++++ examples/develgps/cfg/cfg_i2s.h | 75 +++ examples/develgps/cfg/cfg_ini_reader.h | 49 ++ examples/develgps/cfg/cfg_kbd.h | 59 +++ examples/develgps/cfg/cfg_kfile.h | 62 +++ examples/develgps/cfg/cfg_lcd.h | 72 +++ examples/develgps/cfg/cfg_lm75.h | 57 +++ examples/develgps/cfg/cfg_md2.h | 54 +++ examples/develgps/cfg/cfg_monitor.h | 48 ++ examples/develgps/cfg/cfg_nmea.h | 85 ++++ examples/develgps/cfg/cfg_phase.h | 56 +++ examples/develgps/cfg/cfg_pocketbus.h | 50 ++ examples/develgps/cfg/cfg_proc.h | 108 +++++ examples/develgps/cfg/cfg_pwm.h | 57 +++ examples/develgps/cfg/cfg_ramp.h | 116 +++++ examples/develgps/cfg/cfg_randpool.h | 56 +++ examples/develgps/cfg/cfg_sem.h | 48 ++ examples/develgps/cfg/cfg_ser.h | 222 +++++++++ examples/develgps/cfg/cfg_signal.h | 48 ++ examples/develgps/cfg/cfg_spi_bitbang.h | 52 +++ examples/develgps/cfg/cfg_stepper.h | 70 +++ examples/develgps/cfg/cfg_tas5706a.h | 51 +++ examples/develgps/cfg/cfg_thermo.h | 58 +++ examples/develgps/cfg/cfg_timer.h | 68 +++ examples/develgps/cfg/cfg_wdt.h | 48 ++ examples/develgps/cfg/cfg_xmodem.h | 67 +++ examples/develgps/cfg/log.h | 170 +++++++ examples/develgps/compass.c | 99 ++++ examples/develgps/compass.h | 57 +++ examples/develgps/develgps.c | 586 ++++++++++++++++++++++++ examples/develgps/develgps.mk | 84 ++++ examples/develgps/hw/hw_afsk.h | 87 ++++ examples/develgps/hw/hw_buzzer.h | 52 +++ examples/develgps/hw/hw_dataflash.c | 126 +++++ examples/develgps/hw/hw_dataflash.h | 48 ++ examples/develgps/hw/hw_dc_motor.h | 85 ++++ examples/develgps/hw/hw_ft245rl.h | 65 +++ examples/develgps/hw/hw_i2c_bitbang.h | 66 +++ examples/develgps/hw/hw_kbd.h | 66 +++ examples/develgps/hw/hw_lcd.h | 162 +++++++ examples/develgps/hw/hw_lm75.h | 49 ++ examples/develgps/hw/hw_mcp41.c | 53 +++ examples/develgps/hw/hw_mcp41.h | 75 +++ examples/develgps/hw/hw_ntc.c | 46 ++ examples/develgps/hw/hw_ntc.h | 136 ++++++ examples/develgps/hw/hw_phase.c | 46 ++ examples/develgps/hw/hw_phase.h | 80 ++++ examples/develgps/hw/hw_rit128x96.h | 128 ++++++ examples/develgps/hw/hw_sd.h | 53 +++ examples/develgps/hw/hw_ser.h | 53 +++ examples/develgps/hw/hw_sipo.h | 109 +++++ examples/develgps/hw/hw_spi.h | 115 +++++ examples/develgps/hw/hw_stepper.h | 309 +++++++++++++ examples/develgps/hw/hw_tas5706a.h | 65 +++ examples/develgps/hw/hw_thermo.h | 182 ++++++++ examples/develgps/hw/hw_tlv5618.h | 69 +++ examples/develgps/hw/hw_tmp123.h | 52 +++ examples/develgps/hw/kbd_map.h | 70 +++ examples/develgps/hw/mcp41_map.h | 59 +++ examples/develgps/hw/ntc_map.h | 61 +++ examples/develgps/hw/phase_map.h | 58 +++ examples/develgps/hw/pwm_map.h | 61 +++ examples/develgps/hw/thermo_map.h | 70 +++ examples/develgps/logo.c | 584 +++++++++++++++++++++++ 78 files changed, 7149 insertions(+) create mode 100644 examples/develgps/README create mode 100644 examples/develgps/cfg/cfg_adc.h create mode 100644 examples/develgps/cfg/cfg_afsk.h create mode 100644 examples/develgps/cfg/cfg_ax25.h create mode 100644 examples/develgps/cfg/cfg_battfs.h create mode 100644 examples/develgps/cfg/cfg_dataflash.h create mode 100644 examples/develgps/cfg/cfg_dc_motor.h create mode 100644 examples/develgps/cfg/cfg_debug.h create mode 100644 examples/develgps/cfg/cfg_fat.h create mode 100644 examples/develgps/cfg/cfg_flash25.h create mode 100644 examples/develgps/cfg/cfg_formatwr.h create mode 100644 examples/develgps/cfg/cfg_gfx.h create mode 100644 examples/develgps/cfg/cfg_heap.h create mode 100644 examples/develgps/cfg/cfg_i2c.h create mode 100644 examples/develgps/cfg/cfg_i2s.h create mode 100644 examples/develgps/cfg/cfg_ini_reader.h create mode 100644 examples/develgps/cfg/cfg_kbd.h create mode 100644 examples/develgps/cfg/cfg_kfile.h create mode 100644 examples/develgps/cfg/cfg_lcd.h create mode 100644 examples/develgps/cfg/cfg_lm75.h create mode 100644 examples/develgps/cfg/cfg_md2.h create mode 100644 examples/develgps/cfg/cfg_monitor.h create mode 100644 examples/develgps/cfg/cfg_nmea.h create mode 100644 examples/develgps/cfg/cfg_phase.h create mode 100644 examples/develgps/cfg/cfg_pocketbus.h create mode 100644 examples/develgps/cfg/cfg_proc.h create mode 100644 examples/develgps/cfg/cfg_pwm.h create mode 100644 examples/develgps/cfg/cfg_ramp.h create mode 100644 examples/develgps/cfg/cfg_randpool.h create mode 100644 examples/develgps/cfg/cfg_sem.h create mode 100644 examples/develgps/cfg/cfg_ser.h create mode 100644 examples/develgps/cfg/cfg_signal.h create mode 100644 examples/develgps/cfg/cfg_spi_bitbang.h create mode 100644 examples/develgps/cfg/cfg_stepper.h create mode 100644 examples/develgps/cfg/cfg_tas5706a.h create mode 100644 examples/develgps/cfg/cfg_thermo.h create mode 100644 examples/develgps/cfg/cfg_timer.h create mode 100644 examples/develgps/cfg/cfg_wdt.h create mode 100644 examples/develgps/cfg/cfg_xmodem.h create mode 100644 examples/develgps/cfg/log.h create mode 100644 examples/develgps/compass.c create mode 100644 examples/develgps/compass.h create mode 100644 examples/develgps/develgps.c create mode 100644 examples/develgps/develgps.mk create mode 100644 examples/develgps/hw/hw_afsk.h create mode 100644 examples/develgps/hw/hw_buzzer.h create mode 100644 examples/develgps/hw/hw_dataflash.c create mode 100644 examples/develgps/hw/hw_dataflash.h create mode 100644 examples/develgps/hw/hw_dc_motor.h create mode 100644 examples/develgps/hw/hw_ft245rl.h create mode 100644 examples/develgps/hw/hw_i2c_bitbang.h create mode 100644 examples/develgps/hw/hw_kbd.h create mode 100644 examples/develgps/hw/hw_lcd.h create mode 100644 examples/develgps/hw/hw_lm75.h create mode 100644 examples/develgps/hw/hw_mcp41.c create mode 100644 examples/develgps/hw/hw_mcp41.h create mode 100644 examples/develgps/hw/hw_ntc.c create mode 100644 examples/develgps/hw/hw_ntc.h create mode 100644 examples/develgps/hw/hw_phase.c create mode 100644 examples/develgps/hw/hw_phase.h create mode 100644 examples/develgps/hw/hw_rit128x96.h create mode 100644 examples/develgps/hw/hw_sd.h create mode 100644 examples/develgps/hw/hw_ser.h create mode 100644 examples/develgps/hw/hw_sipo.h create mode 100644 examples/develgps/hw/hw_spi.h create mode 100644 examples/develgps/hw/hw_stepper.h create mode 100644 examples/develgps/hw/hw_tas5706a.h create mode 100644 examples/develgps/hw/hw_thermo.h create mode 100644 examples/develgps/hw/hw_tlv5618.h create mode 100644 examples/develgps/hw/hw_tmp123.h create mode 100644 examples/develgps/hw/kbd_map.h create mode 100644 examples/develgps/hw/mcp41_map.h create mode 100644 examples/develgps/hw/ntc_map.h create mode 100644 examples/develgps/hw/phase_map.h create mode 100644 examples/develgps/hw/pwm_map.h create mode 100644 examples/develgps/hw/thermo_map.h create mode 100644 examples/develgps/logo.c diff --git a/Makefile b/Makefile index 4d3d7f9b..d7ec603f 100644 --- a/Makefile +++ b/Makefile @@ -18,6 +18,7 @@ include examples/demo/demo.mk #include examples/at91sam7/at91sam7s.mk #include examples/at91sam7/at91sam7x.mk #include examples/lm3s1968/lm3s1968.mk +#include examples/develgps/develgps.mk #include examples/lpc2378/lpc2378.mk #include examples/avr-kern/avr-kern.mk #include examples/triface/triface.mk diff --git a/examples/develgps/README b/examples/develgps/README new file mode 100644 index 00000000..d11f3755 --- /dev/null +++ b/examples/develgps/README @@ -0,0 +1,56 @@ += DevelGPS v0.1 = + +== Overview == + +The purpose of this project is to implement a portable GPS locator / geocaching +finder tool using the Cortex-M3 based Luminary Micro LM3S1968 evaluation board. + +The device proposes a user interface to configure the GPS coordinates of a +target location and shows on the OLED display the direction and distance to +reach the target. + +== Hardware requirements == + + - Luminary Micro LM3S1968 Evaluation Kit + - a GPS module + - a mobile phone battery + +== Software requirements == + + - BeRTOS kernel + +BeRTOS components used for this project: + - Kernel with preemptive scheduler and task priorities + - Device drivers: UART, OLED display, navigation/select pushbuttons + - NMEA parser + - GFX library (+ menu management module) + +== Implementation == + +The GPS module is connected to UART1 RX pin (UART0 is kept for debugging +purposes). The mobile phone batter is used as a power source both for the GPS +module and the LM3S1968 board. + +From the software's point of view, BeRTOS already provides the drivers to +manage all the required devices and a NMEA parser to retrieve the right +informations from the raw GPS strings: position, date & time, link quality. + +The multi-process environment and preemptive scheduler provided by BeRTOS is +exploited to create independent threads operating in producer/consumer way: + - a thread takes care of retrieving and processing NMEA string from the UART, + - a thread manages the GUI, updating the OLED display on new GPS informations + or user's input, + - a thread reports the status of the GPS receiver blinking a LED when GPS data + are correctly received. + +The GUI is organized using a main menu that allows to select: + - a form to insert the target GPS coordinates, + - a form showing a compass with target direction, distance and GPS positions + to reach the target, + - a form to show the status of the GPS receiver. + +NOTE: the distance is evaluated using the Haversine formula between the current +and target GPS position. The Haversine formula remains particularly +well-conditioned for numerical computation even at small distances, making the +device particularly useful when walking, hiking or moving at a close distance +to the target. diff --git a/examples/develgps/cfg/cfg_adc.h b/examples/develgps/cfg/cfg_adc.h new file mode 100644 index 00000000..dd65e134 --- /dev/null +++ b/examples/develgps/cfg/cfg_adc.h @@ -0,0 +1,110 @@ +/** + * \file + * + * + * \brief Configuration file for the ADC module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_ADC_H +#define CFG_ADC_H + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define ADC_LOG_LEVEL LOG_LVL_INFO + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define ADC_LOG_FORMAT LOG_FMT_VERBOSE + +/** + * Clock Frequency for ADC conversion. + * + * $WIZ$ type = "int" + * $WIZ$ supports = "at91" + */ +#define CONFIG_ADC_CLOCK 4800000UL + +/** + * Minimum time for starting up a conversion [us]. + * + * $WIZ$ type = "int" + * $WIZ$ min = 0 + * $WIZ$ supports = "at91" + */ +#define CONFIG_ADC_STARTUP_TIME 20 + +/** + * Minimum time for sample and hold [us]. + * + * $WIZ$ type = "int" + * $WIZ$ min = 0 + * $WIZ$ supports = "at91" + */ +#define CONFIG_ADC_SHTIME 834 + +/** + * ADC Voltage Reference. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "avr_adc_refs" + * $WIZ$ supports = "avr" + */ +#define CONFIG_ADC_AVR_REF ADC_AVR_AVCC + +/** + * ADC clock divisor from main crystal. + * + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ max = 128 + * $WIZ$ supports = "avr" + */ +#define CONFIG_ADC_AVR_DIVISOR 2 + +/** + * Enable ADC strobe for debugging ADC ISR. + * + * $WIZ$ type = "boolean" + */ +#define CONFIG_ADC_STROBE 0 + +#endif /* CFG_ADC_H */ diff --git a/examples/develgps/cfg/cfg_afsk.h b/examples/develgps/cfg/cfg_afsk.h new file mode 100644 index 00000000..d8bc1d56 --- /dev/null +++ b/examples/develgps/cfg/cfg_afsk.h @@ -0,0 +1,114 @@ +/** + * \file + * + * + * \brief Configuration file for AFSK1200 modem. + * + * \version $Id$ + * \author Francesco Sacchi + */ + +#ifndef CFG_AFSK_H +#define CFG_AFSK_H + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define AFSK_LOG_LEVEL LOG_LVL_WARN + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define AFSK_LOG_FORMAT LOG_FMT_TERSE + + +/** + * AFSK discriminator filter type. + * + * $WIZ$ type = "enum"; value_list = "afsk_filter_list" + */ +#define CONFIG_AFSK_FILTER AFSK_CHEBYSHEV + + +/** + * AFSK receiver buffer length. + * + * $WIZ$ type = "int" + * $WIZ$ min = 2 + */ +#define CONFIG_AFSK_RX_BUFLEN 32 + +/** + * AFSK transimtter buffer length. + * + * $WIZ$ type = "int" + * $WIZ$ min = 2 + */ +#define CONFIG_AFSK_TX_BUFLEN 32 + +/** + * AFSK DAC sample rate for modem outout. + * $WIZ$ type = "int" + * $WIZ$ min = 2400 + */ +#define CONFIG_AFSK_DAC_SAMPLERATE 9600 + +/** + * AFSK RX timeout in ms, set to -1 to disable. + * $WIZ$ type = "int" + * $WIZ$ min = -1 + */ +#define CONFIG_AFSK_RXTIMEOUT 0 + + +/** + * AFSK Preamble length in [ms], before starting transmissions. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_AFSK_PREAMBLE_LEN 300UL + + + +/** + * AFSK Trailer length in [ms], before stopping transmissions. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_AFSK_TRAILER_LEN 50UL + +#endif /* CFG_AFSK_H */ diff --git a/examples/develgps/cfg/cfg_ax25.h b/examples/develgps/cfg/cfg_ax25.h new file mode 100644 index 00000000..64f862f1 --- /dev/null +++ b/examples/develgps/cfg/cfg_ax25.h @@ -0,0 +1,76 @@ +/** + * \file + * + * + * \brief Configuration file for the AX25 protocol module. + * + * \version $Id$ + * \author Francesco Sacchi + */ + +#ifndef CFG_AX25_H +#define CFG_AX25_H + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define AX25_LOG_LEVEL LOG_LVL_WARN + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define AX25_LOG_FORMAT LOG_FMT_TERSE + +/** + * AX25 frame buffer lenght. + * + * $WIZ$ type = "int" + * $WIZ$ min = 18 + */ +#define CONFIG_AX25_FRAME_BUF_LEN 330 + + +/** + * Enable repeaters listing in AX25 frames. + * If enabled use 56 addtional bytes of RAM + * for each message received. + * + * $WIZ$ type = "boolean" + */ +#define CONFIG_AX25_RPT_LST 1 + +#endif /* CFG_AX25_H */ diff --git a/examples/develgps/cfg/cfg_battfs.h b/examples/develgps/cfg/cfg_battfs.h new file mode 100644 index 00000000..fb438a08 --- /dev/null +++ b/examples/develgps/cfg/cfg_battfs.h @@ -0,0 +1,68 @@ +/** + * \file + * + * + * \brief Configuration file for BattFS module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_BATTFS_H +#define CFG_BATTFS_H + + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define BATTFS_LOG_LEVEL LOG_LVL_INFO + +/** + * module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define BATTFS_LOG_FORMAT LOG_FMT_VERBOSE + +/** + * Set to 1 to enable free page shuffling. + * This increase memories life but makes debugging + * more difficult due to its unrepeteable state. + * $WIZ$ type = "boolean" + */ +#define CONFIG_BATTFS_SHUFFLE_FREE_PAGES 0 + + +#endif /* BATTFS */ diff --git a/examples/develgps/cfg/cfg_dataflash.h b/examples/develgps/cfg/cfg_dataflash.h new file mode 100644 index 00000000..8bd7828a --- /dev/null +++ b/examples/develgps/cfg/cfg_dataflash.h @@ -0,0 +1,56 @@ +/** + * \file + * + * + * \brief Configuration file for data flash memory module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_DATAFLASH_H +#define CFG_DATAFLASH_H + +/** + * Module logging level. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define DATAFLASH_LOG_LEVEL LOG_LVL_INFO + +/** + * Module logging format. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define DATAFLASH_LOG_FORMAT LOG_FMT_TERSE + +#endif /* CFG_DATAFLASH_H */ diff --git a/examples/develgps/cfg/cfg_dc_motor.h b/examples/develgps/cfg/cfg_dc_motor.h new file mode 100644 index 00000000..409badda --- /dev/null +++ b/examples/develgps/cfg/cfg_dc_motor.h @@ -0,0 +1,67 @@ +/** + * \file + * + * + * \brief Configuration file for DC motor module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_DC_MOTOR_H +#define CFG_DC_MOTOR_H + +/** + * Number of the DC motors to manage. + * + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_NUM_DC_MOTOR 4 + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define DC_MOTOR_LOG_LEVEL LOG_LVL_WARN + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define DC_MOTOR_LOG_FORMAT LOG_FMT_TERSE + +#endif /* CFG_DC_MOTOR_H */ diff --git a/examples/develgps/cfg/cfg_debug.h b/examples/develgps/cfg/cfg_debug.h new file mode 100644 index 00000000..f7596ca1 --- /dev/null +++ b/examples/develgps/cfg/cfg_debug.h @@ -0,0 +1,55 @@ +/** + * \file + * + * + * \brief Configuration file for Debug module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_DEBUG_H +#define CFG_DEBUG_H + +/** + * Debug console port. + * $WIZ$ type = "int"; min = 0 + */ +#define CONFIG_KDEBUG_PORT 0 + +/** + * Baudrate for the debug console. + * $WIZ$ type = "int"; min = 300 + */ +#define CONFIG_KDEBUG_BAUDRATE 115200UL + +#endif /* CFG_DEBUG_H */ diff --git a/examples/develgps/cfg/cfg_fat.h b/examples/develgps/cfg/cfg_fat.h new file mode 100644 index 00000000..d418b783 --- /dev/null +++ b/examples/develgps/cfg/cfg_fat.h @@ -0,0 +1,140 @@ +/** + * \file + * + * + * \brief Configuration file for Fat module. + * + * \version $Id$ + * + * \author Luca Ottaviano + * \author Francesco Sacchi + */ + +#ifndef CFG_FAT_H +#define CFG_FAT_H + +/** + * Use word alignment to access FAT structure. + * $WIZ$ type = "boolean" + */ +#define CONFIG_FAT_WORD_ACCESS 0 +#define _WORD_ACCESS CONFIG_FAT_WORD_ACCESS + +/** + * Enable read functions only. + * $WIZ$ type = "boolean" + */ +#define CONFIG_FAT_FS_READONLY 0 +#define _FS_READONLY CONFIG_FAT_FS_READONLY + +/** + * Minimization level to remove some functions. + * $WIZ$ type = "int"; min = 0; max = 3 + */ +#define CONFIG_FAT_FS_MINIMIZE 0 +#define _FS_MINIMIZE CONFIG_FAT_FS_MINIMIZE + +/** + * If enabled, this reduces memory consumption 512 bytes each file object by using a shared buffer. + * $WIZ$ type = "boolean" + */ +#define CONFIG_FAT_FS_TINY 1 +#define _FS_TINY CONFIG_FAT_FS_TINY + +/** + * To enable string functions, set _USE_STRFUNC to 1 or 2. + * $WIZ$ type = "int" + * $WIZ$ supports = "False" + */ +#define CONFIG_FAT_USE_STRFUNC 0 +#define _USE_STRFUNC CONFIG_FAT_USE_STRFUNC + +/** + * Enable f_mkfs function. Requires CONFIG_FAT_FS_READONLY = 0. + * $WIZ$ type = "boolean" + */ +#define CONFIG_FAT_USE_MKFS 0 +#define _USE_MKFS (CONFIG_FAT_USE_MKFS && !CONFIG_FAT_FS_READONLY) + +/** + * Enable f_forward function. Requires CONFIG_FAT_FS_TINY. + * $WIZ$ type = "boolean" + */ +#define CONFIG_FAT_USE_FORWARD 0 +#define _USE_FORWARD (CONFIG_FAT_USE_FORWARD && CONFIG_FAT_FS_TINY) + +/** + * Number of volumes (logical drives) to be used. + * $WIZ$ type = "int"; min = 1; max = 255 + */ +#define CONFIG_FAT_DRIVES 1 +#define _DRIVES CONFIG_FAT_DRIVES + +/** + * Maximum sector size to be handled. (512/1024/2048/4096). + * 512 for memory card and hard disk, 1024 for floppy disk, 2048 for MO disk + * $WIZ$ type = "int"; min = 512; max = 4096 + */ +#define CONFIG_FAT_MAX_SS 512 +#define _MAX_SS CONFIG_FAT_MAX_SS + +/** + * When _MULTI_PARTITION is set to 0, each volume is bound to the same physical + * drive number and can mount only first primaly partition. When it is set to 1, + * each volume is tied to the partitions listed in Drives[]. + * $WIZ$ type = "boolean" + * $WIZ$ supports = "False" + */ +#define CONFIG_FAT_MULTI_PARTITION 0 +#define _MULTI_PARTITION CONFIG_FAT_MULTI_PARTITION + +/** + * Specifies the OEM code page to be used on the target system. + * $WIZ$ type = "int" + */ +#define CONFIG_FAT_CODE_PAGE 850 +#define _CODE_PAGE CONFIG_FAT_CODE_PAGE + +/** + * Support for long filenames. Enable only if you have a valid Microsoft license. + * $WIZ$ type = "boolean" + */ +#define CONFIG_FAT_USE_LFN 0 +#define _USE_LFN CONFIG_FAT_USE_LFN + +/** + * Maximum Long File Name length to handle. + * $WIZ$ type = "int"; min = 8; max = 255 + */ +#define CONFIG_FAT_MAX_LFN 255 +#define _MAX_LFN CONFIG_FAT_MAX_LFN + +#endif /* CFG_FAT_H */ diff --git a/examples/develgps/cfg/cfg_flash25.h b/examples/develgps/cfg/cfg_flash25.h new file mode 100644 index 00000000..f7ff219b --- /dev/null +++ b/examples/develgps/cfg/cfg_flash25.h @@ -0,0 +1,52 @@ +/** + * \file + * + * + * \brief Configuration file for flash25 module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_FLASH25_H +#define CFG_FLASH25_H + +/** + * Eeprom memory type. + * + *$WIZ$ type = "enum" + *$WIZ$ value_list = "flash25_list" + */ +#define CONFIG_FLASH25 FLASH25_AT25F2048 + +#endif /* CFG_FALSH25_H */ + diff --git a/examples/develgps/cfg/cfg_formatwr.h b/examples/develgps/cfg/cfg_formatwr.h new file mode 100644 index 00000000..10d41b48 --- /dev/null +++ b/examples/develgps/cfg/cfg_formatwr.h @@ -0,0 +1,67 @@ +/** + * \file + * + * + * \brief Configuration file for formatted write module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_FORMATWR_H +#define CFG_FORMATWR_H + +/** + * printf()-style formatter configuration. + * $WIZ$ type = "enum"; value_list = "printf_list" + * + * \sa PRINTF_DISABLED + * \sa PRINTF_NOMODIFIERS + * \sa PRINTF_REDUCED + * \sa PRINTF_NOFLOAT + * \sa PRINTF_FULL + */ +#define CONFIG_PRINTF PRINTF_FULL + +/** + * Size of buffer to format "%" sequences in printf. + * + * Warning: no check on buffer size is done when formatting, be careful especially + * with big numbers and %f formatting. + * + * $WIZ$ type = "int" + * $WIZ$ min = 4 + */ +#define CONFIG_FRMWRI_BUFSIZE 134 + +#endif /* CFG_FORMATWR_H */ + diff --git a/examples/develgps/cfg/cfg_gfx.h b/examples/develgps/cfg/cfg_gfx.h new file mode 100644 index 00000000..e4708900 --- /dev/null +++ b/examples/develgps/cfg/cfg_gfx.h @@ -0,0 +1,74 @@ +/** + * \file + * + * + * \brief Configuration file for GFX module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_GFX_H +#define CFG_GFX_H + +/// Enable line clipping algorithm. +#define CONFIG_GFX_CLIPPING 1 + +/// Enable text rendering in bitmaps. +#define CONFIG_GFX_TEXT 1 + +/// Enable virtual coordinate system. +#define CONFIG_GFX_VCOORDS 1 + +/// Select bitmap pixel format. +#define CONFIG_BITMAP_FMT BITMAP_FMT_PLANAR_V_LSB + + +#define CONFIG_CHART_TYPE_X uint8_t ///< Type for the chart dataset +#define CONFIG_CHART_TYPE_Y uint8_t ///< Type for the chart dataset + + +/// Enable button bar behind menus +#define CONFIG_MENU_MENUBAR 0 + +/// Level Edit Timeout +#define CONFIG_LEVELEDIT_TIMEOUT 0 + +/// Menu timeout +#define CONFIG_MENU_TIMEOUT 100 + +/// Enable smooth scrolling in menus +#define CONFIG_MENU_SMOOTH 1 + + +#endif /* CFG_GFX_H */ + diff --git a/examples/develgps/cfg/cfg_heap.h b/examples/develgps/cfg/cfg_heap.h new file mode 100644 index 00000000..dc4b1fa3 --- /dev/null +++ b/examples/develgps/cfg/cfg_heap.h @@ -0,0 +1,51 @@ +/** + * \file + * + * + * \brief Configuration file for heap module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_HEAP_H +#define CFG_HEAP_H + +/** + * Enable malloc/free like API. + * $WIZ$ type = "boolean" + */ +#define CONFIG_HEAP_MALLOC 1 + +#endif /* CFG_HEAP_H */ + + diff --git a/examples/develgps/cfg/cfg_i2c.h b/examples/develgps/cfg/cfg_i2c.h new file mode 100644 index 00000000..af36e6b6 --- /dev/null +++ b/examples/develgps/cfg/cfg_i2c.h @@ -0,0 +1,90 @@ +/** + * \file + * + * + * \brief Configuration file for I2C module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_I2C_H +#define CFG_I2C_H + +/** +*Comunication frequency. +* +* $WIZ$ type = "int" +*/ +#define CONFIG_I2C_FREQ 100000UL + +/** + * I2C start timeout. + * For how many milliseconds the i2c_start + * should try to get an ACK before + * returning error. + * + * $WIZ$ type = "int" + */ +#define CONFIG_I2C_START_TIMEOUT 100 + +/** + * I2C backend the driver should use. + * + * I2C_BACKEND_BUILTIN: Use (if present) the builtin i2c hardware. + * I2C_BACKEND_BITBANG: Use the emulated bitbang driver. + * \see drv/i2c.h for more information. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "i2c_backend" + */ +#define CONFIG_I2C_BACKEND I2C_BACKEND_BUILTIN + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define I2C_LOG_LEVEL LOG_LVL_INFO + +/** + * module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define I2C_LOG_FORMAT LOG_FMT_TERSE + +#endif /* CFG_I2C_H */ + + diff --git a/examples/develgps/cfg/cfg_i2s.h b/examples/develgps/cfg/cfg_i2s.h new file mode 100644 index 00000000..52fa8848 --- /dev/null +++ b/examples/develgps/cfg/cfg_i2s.h @@ -0,0 +1,75 @@ +/** + * \file + * + * + * \brief Configuration file for I2S module. + * + * \version $Id$ + * + * \author Luca Ottaviano + */ + +#ifndef CFG_I2S_H +#define CFG_I2S_H + +/** + * Length of each play buffer. + * + * $WIZ$ type = "int" + */ +#define CONFIG_PLAY_BUF_LEN 8192 + +/** + * Sampling frequency of the audio file. + * + * $WIZ$ type = "int" + * $WIZ$ min = 32000 + * $WIZ$ max = 192000 + */ +#define CONFIG_SAMPLE_FREQ 44100UL + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define I2S_LOG_LEVEL LOG_LVL_INFO + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define I2S_LOG_FORMAT LOG_FMT_TERSE + +#endif /* CFG_I2S_H */ diff --git a/examples/develgps/cfg/cfg_ini_reader.h b/examples/develgps/cfg/cfg_ini_reader.h new file mode 100644 index 00000000..702c78ee --- /dev/null +++ b/examples/develgps/cfg/cfg_ini_reader.h @@ -0,0 +1,49 @@ +/** + * \file + * + * + * \brief Configuration file for ini reader module. + * + * \version $Id$ + * + * \author Luca Ottaviano + */ + +#ifndef CFG_INI_READER_H +#define CFG_INI_READER_H + +/** + * Maximum ini file line length (chars). + * $WIZ$ type = "int"; min = 1 + */ +#define CONFIG_INI_MAX_LINE_LEN 64 + +#endif /* CFG_INI_READER_H */ diff --git a/examples/develgps/cfg/cfg_kbd.h b/examples/develgps/cfg/cfg_kbd.h new file mode 100644 index 00000000..116f3318 --- /dev/null +++ b/examples/develgps/cfg/cfg_kbd.h @@ -0,0 +1,59 @@ +/** + * \file + * + * + * \brief Configuration file for keyboard module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_KBD_H +#define CFG_KBD_H + +/// Keyboard polling method. $WIZ$ supports = "False" +#define CONFIG_KBD_POLL KBD_POLL_SOFTINT + +/// Enable keyboard event delivery to observers. $WIZ$ type = "boolean" +#define CONFIG_KBD_OBSERVER 0 + +/// Enable key beeps. $WIZ$ type = "boolean" +#define CONFIG_KBD_BEEP 0 + +/// Enable long pression handler for keys. $WIZ$ type = "boolean" +#define CONFIG_KBD_LONGPRESS 0 + +/// Enable calling poor man's scheduler to be called inside kbd_peek. $WIZ$ type = "boolean" +#define CONFIG_KBD_SCHED 0 + +#endif /* CFG_KBD_H */ + diff --git a/examples/develgps/cfg/cfg_kfile.h b/examples/develgps/cfg/cfg_kfile.h new file mode 100644 index 00000000..1b1989c9 --- /dev/null +++ b/examples/develgps/cfg/cfg_kfile.h @@ -0,0 +1,62 @@ +/** + * \file + * + * + * \brief Configuration file for KFile interface module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_KFILE_H +#define CFG_KFILE_H + +/** + * Module logging level. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define KFILE_LOG_LEVEL LOG_LVL_INFO + +/** + * Module logging format. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define KFILE_LOG_FORMAT LOG_FMT_TERSE + +/** + * Enable the gets function with echo. + * $WIZ$ type = "boolean" + */ +#define CONFIG_KFILE_GETS 1 + +#endif /* CFG_KFILE_H */ diff --git a/examples/develgps/cfg/cfg_lcd.h b/examples/develgps/cfg/cfg_lcd.h new file mode 100644 index 00000000..903ae9aa --- /dev/null +++ b/examples/develgps/cfg/cfg_lcd.h @@ -0,0 +1,72 @@ +/** + * \file + * + * + * \brief Configuration file for lcd display module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_LCD_H +#define CFG_LCD_H + +/** + * Use 4 bit addressing mode. + * $WIZ$ type = "boolean" + */ +#define CONFIG_LCD_4BIT 0 + +/** + * Use a table to speed up LCD memory addressing. + * This will use about 100 bytes of RAM. + * $WIZ$ type = "boolean" + */ +#define CONFIG_LCD_ADDRESS_FAST 1 + +/** + * LCD setting for 32122A (AVR implementation). + * $WIZ$ type = "boolean" + * $WIZ$ supports = "avr and False" + */ +#define CONFIG_LCD_SOFTINT_REFRESH 0 + +/** + * LCD setting for 32122A (AVR implementation). + * $WIZ$ type = "boolean" + * $WIZ$ supports = "avr and False" + */ +#define CONFIG_LCD_WAIT 1 + + +#endif /* CFG_LCD_H */ + diff --git a/examples/develgps/cfg/cfg_lm75.h b/examples/develgps/cfg/cfg_lm75.h new file mode 100644 index 00000000..91b347ad --- /dev/null +++ b/examples/develgps/cfg/cfg_lm75.h @@ -0,0 +1,57 @@ +/** + * \file + * + * + * \brief Configuration file for the LM75 sensor temperature. + * + * \author Daniele Basile + */ + +#ifndef CFG_LM75_H +#define CFG_LM75_H + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define LM75_LOG_LEVEL LOG_LVL_WARN + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define LM75_LOG_FORMAT LOG_FMT_TERSE + +#endif /* CFG_AX25_H */ diff --git a/examples/develgps/cfg/cfg_md2.h b/examples/develgps/cfg/cfg_md2.h new file mode 100644 index 00000000..22ec7dbe --- /dev/null +++ b/examples/develgps/cfg/cfg_md2.h @@ -0,0 +1,54 @@ +/** + * \file + * + * + * \brief Configuration file for MD2 module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_MD2_H +#define CFG_MD2_H + +/** + * Size of block for MD2 algorithm. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + */ +#define CONFIG_MD2_BLOCK_LEN 16 + +/// Use standard permutation in MD2 algorithm. $WIZ$ type = "boolean" +#define CONFIG_MD2_STD_PERM 0 + +#endif /* CFG_MD2_H */ + diff --git a/examples/develgps/cfg/cfg_monitor.h b/examples/develgps/cfg/cfg_monitor.h new file mode 100644 index 00000000..ffe17c07 --- /dev/null +++ b/examples/develgps/cfg/cfg_monitor.h @@ -0,0 +1,48 @@ +/** + * \file + * + * + * \brief Kernel monitor configuration parameters + * + * \version $Id$ + * \author Bernie Innocenti + */ + +#ifndef CFG_MONITOR_H +#define CFG_MONITOR_H + +/** + * Process monitor. + * $WIZ$ type = "autoenabled" + */ +#define CONFIG_KERN_MONITOR 0 + +#endif /* CFG_MONITOR_H */ diff --git a/examples/develgps/cfg/cfg_nmea.h b/examples/develgps/cfg/cfg_nmea.h new file mode 100644 index 00000000..9249a9af --- /dev/null +++ b/examples/develgps/cfg/cfg_nmea.h @@ -0,0 +1,85 @@ +/** + * \file + * + * + * \brief Configuration file for NMEA module. + * + * \author Daniele Basile + */ + +#ifndef CFG_NMEA_H +#define CFG_NMEA_H + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define NMEA_LOG_LEVEL LOG_LVL_ERR + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define NMEA_LOG_FORMAT LOG_FMT_TERSE + + +/** + * Maximum number of sentence parsers supported. + * + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_NMEAP_MAX_SENTENCES 8 + +/** + * Max length of a complete sentence. The standard says 82 bytes, but its probably + * better to go at least 128 since some units don't adhere to the 82 bytes + * especially for proprietary sentences. + * + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_NMEAP_MAX_SENTENCE_LENGTH 255 + +/** + * Max tokens in one sentence. 24 is enough for any standard sentence. + * + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_NMEAP_MAX_TOKENS 24 + +#endif /* CFG_NMEA_H */ + diff --git a/examples/develgps/cfg/cfg_phase.h b/examples/develgps/cfg/cfg_phase.h new file mode 100644 index 00000000..57202930 --- /dev/null +++ b/examples/develgps/cfg/cfg_phase.h @@ -0,0 +1,56 @@ +/** + * \file + * + * + * \brief Configuration file for phase module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_PHASE_H +#define CFG_PHASE_H + +/** + * Max value of the duty cycle on triac. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_TRIAC_MAX_DUTY 100 + +/** + * Max value of the triac power. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_TRIAC_MAX_POWER 100 + +#endif /* CFG_PHASE_H */ diff --git a/examples/develgps/cfg/cfg_pocketbus.h b/examples/develgps/cfg/cfg_pocketbus.h new file mode 100644 index 00000000..687e535d --- /dev/null +++ b/examples/develgps/cfg/cfg_pocketbus.h @@ -0,0 +1,50 @@ +/** + * \file + * + * + * \brief Configuration file for pocketbus module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_POCKETBUS_H +#define CFG_POCKETBUS_H + +/** + *Buffer len for pockebus protocol. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + */ +#define CONFIG_POCKETBUS_BUFLEN 128 + +#endif /* CFG_POCKETBUS_H */ diff --git a/examples/develgps/cfg/cfg_proc.h b/examples/develgps/cfg/cfg_proc.h new file mode 100644 index 00000000..eddd615c --- /dev/null +++ b/examples/develgps/cfg/cfg_proc.h @@ -0,0 +1,108 @@ +/** + * \file + * + * + * \brief Kernel configuration parameters + * + * \version $Id$ + * \author Bernie Innocenti + */ + +#ifndef CFG_PROC_H +#define CFG_PROC_H + +/** + * Enable the multithreading kernel. + * + * $WIZ$ type = "autoenabled" + */ +#define CONFIG_KERN 1 + +/** + * Kernel interrupt supervisor. WARNING: Experimental, still incomplete! + * $WIZ$ type = "boolean" + * $WIZ$ supports = "False" + */ +#define CONFIG_KERN_IRQ 0 + +/** + * Preemptive process scheduling. + * + * $WIZ$ type = "boolean" + * $WIZ$ conditional_deps = "timer" + */ +#define CONFIG_KERN_PREEMPT 1 + +/** + * Time sharing quantum (a prime number prevents interference effects) [ms]. + * + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_KERN_QUANTUM 11 + +/** + * Priority-based scheduling policy. + * $WIZ$ type = "boolean" + */ +#define CONFIG_KERN_PRI 1 + +/** + * Dynamic memory allocation for processes. + * $WIZ$ type = "boolean" + * $WIZ$ conditional_deps = "heap" + */ +#define CONFIG_KERN_HEAP 1 + +/** + * Size of the dynamic memory pool used by processes. + * $WIZ$ type = "int" + * $WIZ$ min = 0 + */ +#define CONFIG_KERN_HEAP_SIZE 8192L + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define KERN_LOG_LEVEL LOG_LVL_ERR + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define KERN_LOG_FORMAT LOG_FMT_VERBOSE + +#endif /* CFG_PROC_H */ diff --git a/examples/develgps/cfg/cfg_pwm.h b/examples/develgps/cfg/cfg_pwm.h new file mode 100644 index 00000000..6627ee2d --- /dev/null +++ b/examples/develgps/cfg/cfg_pwm.h @@ -0,0 +1,57 @@ +/** + * \file + * + * + * \brief Configuration file for PWM module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_PWM_H +#define CFG_PWM_H + +/** + * Module logging level. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define PWM_LOG_LEVEL LOG_LVL_INFO + +/** + * Module logging format. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define PWM_LOG_FORMAT LOG_FMT_VERBOSE + +#endif /* CFG_PWM_H */ diff --git a/examples/develgps/cfg/cfg_ramp.h b/examples/develgps/cfg/cfg_ramp.h new file mode 100644 index 00000000..1aeb8a89 --- /dev/null +++ b/examples/develgps/cfg/cfg_ramp.h @@ -0,0 +1,116 @@ + /** + * \file + * + * + * \brief Configuration file Ramp algorithm module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_RAMP_H +#define CFG_RAMP_H + +/** + * Define whether the ramp will use floating point calculation within ramp_evaluate(). + * Otherwise, a less precise fixed point version will be used, which is faster on + * platforms which do no support floating point operations. + * + * \note Floating point operations will be always done within ramp_compute() to + * precalculate values, so there has to be at least a floating point emulation support. + * + * $WIZ$ type = "boolean" + */ +#define RAMP_USE_FLOATING_POINT 0 + + +#if !RAMP_USE_FLOATING_POINT + + /** + * Number of least-significant bits which are stripped away during ramp evaluation. + * This setting allows to specify larger ramps at the price of less precision. + * + * The maximum ramp size allowed is 2^(24 + RAMP_CLOCK_SHIFT_PRECISION), in clocks. + * For instance, using RAMP_CLOCK_SHIFT_PRECISION 1, and a 8x prescaler, the maximum + * length of a ramp is about 6.7 secs. Raising RAMP_CLOCK_SHIFT_PRECISION to 2 + * brings the maximum length to 13.4 secs, at the price of less precision. + * + * ramp_compute() will check that the length is below the maximum allowed through + * a runtime assertion. + * + * \note This macro is used only for the fixed-point version of the ramp. + * $WIZ$ type = "int" + * $WIZ$ min = 0 + * $WIZ$ max = 32 + */ + #define RAMP_CLOCK_SHIFT_PRECISION 2 +#endif + + +/** +* Negative pulse width for ramp. +* $WIZ$ type = "int" +* $WIZ$ min = 1 +*/ +#define RAMP_PULSE_WIDTH 50 + +/** + * Default ramp time (microsecs). + * $WIZ$ type = "int" + * $WIZ$ min = 1000 + */ +#define RAMP_DEF_TIME 6000000UL +/** + * Default ramp maxfreq (Hz). + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define RAMP_DEF_MAXFREQ 5000 +/** + * Default ramp minfreq (Hz). + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define RAMP_DEF_MINFREQ 200 +/** + * Default ramp powerrun (deciampere). + * $WIZ$ type = "int" + * $WIZ$ min = 0 + */ +#define RAMP_DEF_POWERRUN 10 +/** + * Default ramp poweridle (Hz). + * $WIZ$ type = "int" + * $WIZ$ min = 0 + */ +#define RAMP_DEF_POWERIDLE 1 + +#endif /* CFG_RAMP_H */ diff --git a/examples/develgps/cfg/cfg_randpool.h b/examples/develgps/cfg/cfg_randpool.h new file mode 100644 index 00000000..83285984 --- /dev/null +++ b/examples/develgps/cfg/cfg_randpool.h @@ -0,0 +1,56 @@ +/** + * \file + * + * + * \brief Configuration file for randpool module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_RANDPOOL_H +#define CFG_RANDPOOL_H + + +/** + * Define a size, in byte, of entropy pool. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_SIZE_ENTROPY_POOL 64 + +/// Enable timer in randpool algo. $WIZ$ type = "boolean" +#define CONFIG_RANDPOOL_TIMER 1 + +#endif /* CFG_RANDPOOL_H */ + + diff --git a/examples/develgps/cfg/cfg_sem.h b/examples/develgps/cfg/cfg_sem.h new file mode 100644 index 00000000..86ed110d --- /dev/null +++ b/examples/develgps/cfg/cfg_sem.h @@ -0,0 +1,48 @@ +/** + * \file + * + * + * \brief Kernel semaphores configuration parameters. + * + * \version $Id$ + * \author Bernie Innocenti + */ + +#ifndef CFG_SEM_H +#define CFG_SEM_H + +/** + * Re-entrant mutual exclusion primitives. + * $WIZ$ type = "autoenabled" + */ +#define CONFIG_KERN_SEMAPHORES 1 + +#endif /* CFG_SEM_H */ diff --git a/examples/develgps/cfg/cfg_ser.h b/examples/develgps/cfg/cfg_ser.h new file mode 100644 index 00000000..d14b821e --- /dev/null +++ b/examples/develgps/cfg/cfg_ser.h @@ -0,0 +1,222 @@ +/** + * \file + * + * + * \brief Configuration file for serial module. + * + * \author Daniele Basile + */ + +#ifndef CFG_SER_H +#define CFG_SER_H + +/** + * Example of setting for serial port and + * spi port. + * Edit these define for your project. + */ + +/** + * Size of the outbound FIFO buffer for port 0 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + */ +#define CONFIG_UART0_TXBUFSIZE 32 + +/** + * Size of the inbound FIFO buffer for port 0 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + */ +#define CONFIG_UART0_RXBUFSIZE 32 + +/** + * Size of the outbound FIFO buffer for port 1 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "lm3s or lpc2 or (at91 and not atmega8 and not atmega168 and not atmega32)" + */ +#define CONFIG_UART1_TXBUFSIZE 32 + +/** + * Size of the inbound FIFO buffer for port 1 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "lm3s or lpc2 or (at91 and not atmega8 and not atmega168 and not atmega32)" + */ +#define CONFIG_UART1_RXBUFSIZE 128 + +/** + * Size of the outbound FIFO buffer for port 2 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "lm3s or lpc2" + */ +#define CONFIG_UART2_TXBUFSIZE 32 + +/** + * Size of the inbound FIFO buffer for port 2 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "lm3s or lpc2" + */ +#define CONFIG_UART2_RXBUFSIZE 32 + +/** + * Size of the outbound FIFO buffer for port 3 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "lpc2" + */ +#define CONFIG_UART3_TXBUFSIZE 32 + +/** + * Size of the inbound FIFO buffer for port 3 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "lpc2" + */ +#define CONFIG_UART3_RXBUFSIZE 32 + + +/** + * Size of the outbound FIFO buffer for SPI port [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "avr" + */ +#define CONFIG_SPI_TXBUFSIZE 32 + +/** + * Size of the inbound FIFO buffer for SPI port [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "avr" + */ +#define CONFIG_SPI_RXBUFSIZE 32 + +/** + * Size of the outbound FIFO buffer for SPI port 0 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "at91" + */ +#define CONFIG_SPI0_TXBUFSIZE 32 + +/** + * Size of the inbound FIFO buffer for SPI port 0 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "at91" + */ +#define CONFIG_SPI0_RXBUFSIZE 32 + +/** + * Size of the outbound FIFO buffer for SPI port 1 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "at91" + */ +#define CONFIG_SPI1_TXBUFSIZE 32 + +/** + * Size of the inbound FIFO buffer for SPI port 1 [bytes]. + * $WIZ$ type = "int" + * $WIZ$ min = 2 + * $WIZ$ supports = "at91" + */ +#define CONFIG_SPI1_RXBUFSIZE 32 + +/** + * SPI data order. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "ser_order_bit" + * $WIZ$ supports = "avr" + */ +#define CONFIG_SPI_DATA_ORDER SER_MSB_FIRST + +/** + * SPI clock division factor. + * $WIZ$ type = "int" + * $WIZ$ supports = "avr" + */ +#define CONFIG_SPI_CLOCK_DIV 16 + +/** + * SPI clock polarity: normal low or normal high. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "ser_spi_pol" + * $WIZ$ supports = "avr" + */ +#define CONFIG_SPI_CLOCK_POL SPI_NORMAL_LOW + +/** + * SPI clock phase you can choose sample on first edge or + * sample on second clock edge. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "ser_spi_phase" + * $WIZ$ supports = "avr" + */ +#define CONFIG_SPI_CLOCK_PHASE SPI_SAMPLE_ON_FIRST_EDGE + +/** + * Default transmit timeout (ms). Set to -1 to disable timeout support. + * $WIZ$ type = "int" + * $WIZ$ min = -1 + */ +#define CONFIG_SER_TXTIMEOUT -1 + +/** + * Default receive timeout (ms). Set to -1 to disable timeout support. + * $WIZ$ type = "int" + * $WIZ$ min = -1 + */ +#define CONFIG_SER_RXTIMEOUT -1 + +/** + * Use RTS/CTS handshake. + * $WIZ$ type = "boolean" + * $WIZ$ supports = "False" + */ +#define CONFIG_SER_HWHANDSHAKE 0 + +/** + * Default baudrate for all serial ports (set to 0 to disable). + * $WIZ$ type = "int" + * $WIZ$ min = 0 + */ +#define CONFIG_SER_DEFBAUDRATE 0UL + +/// Enable strobe pin for debugging serial interrupt. $WIZ$ type = "boolean" +#define CONFIG_SER_STROBE 0 + +#endif /* CFG_SER_H */ diff --git a/examples/develgps/cfg/cfg_signal.h b/examples/develgps/cfg/cfg_signal.h new file mode 100644 index 00000000..ed85119b --- /dev/null +++ b/examples/develgps/cfg/cfg_signal.h @@ -0,0 +1,48 @@ +/** + * \file + * + * + * \brief Kernel signals configuration parameters + * + * \version $Id$ + * \author Bernie Innocenti + */ + +#ifndef CFG_SIGNAL_H +#define CFG_SIGNAL_H + +/** + * Inter-process signals. + * $WIZ$ type = "autoenabled" + */ +#define CONFIG_KERN_SIGNALS 1 + +#endif /* CFG_SIGNAL_H */ diff --git a/examples/develgps/cfg/cfg_spi_bitbang.h b/examples/develgps/cfg/cfg_spi_bitbang.h new file mode 100644 index 00000000..6e9a96bc --- /dev/null +++ b/examples/develgps/cfg/cfg_spi_bitbang.h @@ -0,0 +1,52 @@ +/** + * \file + * + * + * \brief Configuration file for SPI bitbang module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_SPI_BITBANG_H +#define CFG_SPI_BITBANG_H + +/** + * Set data order for emulated SPI. + * + * $WIZ$ type = "enum" + * $WIZ$ value_list = "ordet_bit_list" + */ +#define CONFIG_SPI_DATAORDER SPI_LSB_FIRST + +#endif /* CFG_SPI_BITBANG_H */ + diff --git a/examples/develgps/cfg/cfg_stepper.h b/examples/develgps/cfg/cfg_stepper.h new file mode 100644 index 00000000..e086065c --- /dev/null +++ b/examples/develgps/cfg/cfg_stepper.h @@ -0,0 +1,70 @@ +/** + * \file + * + * + * \brief Configuration file for stepper motor module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_STEPPER_H +#define CFG_STEPPER_H + +/** + * Module logging level. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_level" + */ +#define STEPPER_LOG_LEVEL LOG_LVL_INFO + +/** + * Module logging format. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "log_format" + */ +#define STEPPER_LOG_FORMAT LOG_FMT_TERSE + +/** + * Max number of the stepper motor. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_NUM_STEPPER_MOTORS 6 + +/** + * Max number of the timer usable on target to drive stepper motor. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_TC_STEPPER_MAX_NUM 6 + +#endif /* CFG_STEPPER_H */ diff --git a/examples/develgps/cfg/cfg_tas5706a.h b/examples/develgps/cfg/cfg_tas5706a.h new file mode 100644 index 00000000..e1112c0f --- /dev/null +++ b/examples/develgps/cfg/cfg_tas5706a.h @@ -0,0 +1,51 @@ +/** + * \file + * + * + * \brief Configuration file for the TAS5706A module. + * + * \version $Id$ + * \author Luca Ottaviano + */ + +#ifndef CFG_TAS5706A_H +#define CFG_TAS5706A_H + +/** + * Maximum output volume for TAS chip [dB]. + * + * $WIZ$ type = "int" + * $WIZ$ min = -100 + * $WIZ$ max = 24 + */ +#define CONFIG_TAS_MAX_VOL -39 + +#endif /* CFG_TAS5706A_H */ diff --git a/examples/develgps/cfg/cfg_thermo.h b/examples/develgps/cfg/cfg_thermo.h new file mode 100644 index 00000000..e68c6371 --- /dev/null +++ b/examples/develgps/cfg/cfg_thermo.h @@ -0,0 +1,58 @@ +/** + * \file + * + * + * \brief Configuration file for thermo module. + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef CFG_THERMO_H +#define CFG_THERMO_H + +/** + * Interval at which thermo control is performed [ms]. + * + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_THERMO_INTERVAL_MS 100 + +/** + * Number of different samples we interpolate over to get the hifi temperature. + * + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_THERMO_HIFI_NUM_SAMPLES 10 + +#endif /* CFG_THERMO_H */ diff --git a/examples/develgps/cfg/cfg_timer.h b/examples/develgps/cfg/cfg_timer.h new file mode 100644 index 00000000..1cff78b8 --- /dev/null +++ b/examples/develgps/cfg/cfg_timer.h @@ -0,0 +1,68 @@ +/** + * \file + * + * + * \brief Configuration file for timer module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_TIMER_H +#define CFG_TIMER_H + +/** + * Hardware timer selection for drv/timer.c. + * $WIZ$ type = "enum" + * $WIZ$ value_list = "timer_select" + */ +#define CONFIG_TIMER TIMER_DEFAULT + +/** + * Debug timer interrupt using a strobe pin. + * $WIZ$ type = "boolean" + */ +#define CONFIG_TIMER_STROBE 0 + +/** + * Enable asynchronous timers. + * $WIZ$ type = "boolean" + */ +#define CONFIG_TIMER_EVENTS 1 + +/** + * Support hi-res timer_usleep(). + * $WIZ$ type = "boolean" + */ +#define CONFIG_TIMER_UDELAY 1 + +#endif /* CFG_TIMER_H */ diff --git a/examples/develgps/cfg/cfg_wdt.h b/examples/develgps/cfg/cfg_wdt.h new file mode 100644 index 00000000..9f4caae9 --- /dev/null +++ b/examples/develgps/cfg/cfg_wdt.h @@ -0,0 +1,48 @@ +/** + * \file + * + * + * \brief Configuration file for watchdog module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_WDT_H +#define CFG_WDT_H + +/// Enable watchdog timer. $WIZ$ type = "autoenabled" +#define CONFIG_WATCHDOG 0 + +#endif /* CFG_WDT_H */ + + diff --git a/examples/develgps/cfg/cfg_xmodem.h b/examples/develgps/cfg/cfg_xmodem.h new file mode 100644 index 00000000..eb8897f4 --- /dev/null +++ b/examples/develgps/cfg/cfg_xmodem.h @@ -0,0 +1,67 @@ +/** + * \file + * + * + * \brief Configuration file for xmodem module. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef CFG_XMODEM_H +#define CFG_XMODEM_H + +/// Enable Rx. $WIZ$ type = "boolean" +#define CONFIG_XMODEM_RECV 1 + +/// Enable TX. $WIZ$ type = "boolean" +#define CONFIG_XMODEM_SEND 1 + +/// Allow a Rx/Tx of 1Kbyte block. $WIZ$ type = "boolean" +#define CONFIG_XMODEM_1KCRC 1 + +/** + * Max retries before giving up. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_XMODEM_MAXRETRIES 15 + +/** + * Max retries before switching to BCC. + * $WIZ$ type = "int" + * $WIZ$ min = 1 + */ +#define CONFIG_XMODEM_MAXCRCRETRIES 7 + +#endif /* CFG_XMODEM_H */ + diff --git a/examples/develgps/cfg/log.h b/examples/develgps/cfg/log.h new file mode 100644 index 00000000..b6649620 --- /dev/null +++ b/examples/develgps/cfg/log.h @@ -0,0 +1,170 @@ +/** + * \file + * + * + * \brief Logging system module. + * + * This module implement a simple interface to use the multi level logging system. + * The log message have the priority order, like this: + * + * - error message (highest) + * - warning message + * - info message (lowest) + * + * With this priority system we can log only the message that have egual or major + * priority than log level that you has been configurate. Further you can have a + * differ log level for each module that you want. To do this you just need to + * define LOG_LEVEL in cfg of select module. + * When you set a log level, the system logs only the message that have priority + * egual or major that you have define, but the other logs function are not include + * at compile time, so all used logs function are linked, but the other no. + * + * To use logging system you should include this module in your drive and use + * a LOG_ERROR, LOG_WARNING and LOG_INFO macros to set the level log of the message. + * Then you should define a LOG_LEVEL and LOG_VERBOSE costant in your + * \c cfg/cfg_\.h using the follow policy: + * + * - in your file \c cfg/cfg_\.h, you define the logging + * level and verbosity mode for your specific module: + * + * \code + * /// Module logging level. + * #define _LOG_LEVEL LOG_LVL_INFO + * + * /// Module logging format. + * #define _LOG_FORMAT LOG_FMT_VERBOSE + * \endcode + * + * - then, in the module that you use a logging macros you should define + * a LOG_LEVEL and LOG_FORMAT using the previous value that you have define + * in cfg_.h header. After this you should include the cfg/log.h + * module: + * + * \code + * // Define log settings for cfg/log.h. + * #define LOG_LEVEL _LOG_LEVEL + * #define LOG_FORMAT _LOG_FORMAT + * #include + * \endcode + * + * if you include a log.h module without define the LOG_LEVEL and LOG_VERBOSE + * macros, the module use the default setting (see below). + * + * WARNING: when use the log.h module, and you want to set a your log level + * make sure to include this module after a \c cfg_.h, because the + * LOG_LEVEL and LOG_VERBOSE macros must be defined before to include log module, + * otherwise the log module use a default settings. + * + * \version $Id$ + * \author Daniele Basile + * + * $WIZ$ + */ + +#ifndef CFG_LOG_H +#define CFG_LOG_H + +#include + + +// Use a default setting if nobody defined a log level +#ifndef LOG_LEVEL +#define LOG_LEVEL LOG_LVL_WARN +#endif + +// Use a default setting if nobody defined a log format +#ifndef LOG_FORMAT +#define LOG_FORMAT LOG_FMT_TERSE +#endif + +/** + * \name Logging level definition + * + * When you choose a log level messages you choose + * also which print function are linked. + * If you choose a low level of log you link all log function (error, warning and info), + * but if choose a hight level you link only that have the priority egual or hight. + * The priority level go from error (highest) to info (lowest) (see cfg/debug.h + * for more detail). + * + * $WIZ$ log_level = "LOG_LVL_NONE", "LOG_LVL_ERR", "LOG_LVL_WARN", "LOG_LVL_INFO" + * } + */ +#define LOG_LVL_NONE 0 +#define LOG_LVL_ERR 1 +#define LOG_LVL_WARN 2 +#define LOG_LVL_INFO 3 + +/** + * \name Logging format + * + * There are two logging format: terse and verbose. The latter prepends + * function names and line number information to each log entry. + * + * $WIZ$ log_format = "LOG_FMT_VERBOSE", "LOG_FMT_TERSE" + */ +#define LOG_FMT_VERBOSE 1 +#define LOG_FMT_TERSE 0 + +#if LOG_FORMAT == LOG_FMT_VERBOSE + #define LOG_PRINT(str_level, str,...) kprintf("%s():%d:%s: " str, __func__, __LINE__, str_level, ## __VA_ARGS__) +#elif LOG_FORMAT == LOG_FMT_TERSE + #define LOG_PRINT(str_level, str,...) kprintf("%s: " str, str_level, ## __VA_ARGS__) +#else + #error No LOG_FORMAT defined +#endif + +#if LOG_LEVEL >= LOG_LVL_ERR + #define LOG_ERR(str,...) LOG_PRINT("ERR", str, ## __VA_ARGS__) + #define LOG_ERRB(x) x +#else + INLINE void LOG_ERR(UNUSED_ARG(const char *, fmt), ...) { /* nop */ } + #define LOG_ERRB(x) /* Nothing */ +#endif + +#if LOG_LEVEL >= LOG_LVL_WARN + #define LOG_WARN(str,...) LOG_PRINT("WARN", str, ## __VA_ARGS__) + #define LOG_WARNB(x) x +#else + INLINE void LOG_WARN(UNUSED_ARG(const char *, fmt), ...) { /* nop */ } + #define LOG_WARNB(x) /* Nothing */ +#endif + +#if LOG_LEVEL >= LOG_LVL_INFO + #define LOG_INFO(str,...) LOG_PRINT("INFO", str, ## __VA_ARGS__) + #define LOG_INFOB(x) x +#else + INLINE void LOG_INFO(UNUSED_ARG(const char *, fmt), ...) { /* nop */ } + #define LOG_INFOB(x) /* Nothing */ +#endif + + +#endif /* CFG_LOG_H */ diff --git a/examples/develgps/compass.c b/examples/develgps/compass.c new file mode 100644 index 00000000..e1edcfba --- /dev/null +++ b/examples/develgps/compass.c @@ -0,0 +1,99 @@ +/** + * \file + * + * + * \brief DevelGPS: compass routines. + * + * \author Andrea Righi + */ + +#include +#include +#include +#include "compass.h" + +static const char *_compass_heading[] = +{ + "N", "NNE", "NE", "ENE", + "E", "ESE", "SE", "SSE", + "S", "SSW", "SW", "WSW", + "W", "WNW", "NW", "NNW", +}; + +/** + * Use the Haversine formula to calculate great-circle distances between the + * two points. + * + * The Haversine formula remains particularly well-conditioned for numerical + * computation even at small distances, unlike calculations based on the + * spherical law of cosines. + */ +float distance(float lat1, float lon1, float lat2, float lon2) +{ + const float PLANET_RADIUS = 6371000; + float d_lat = deg2rad(lat2 - lat1); + float d_lon = deg2rad(lon2 - lon1); + + float a = sin(d_lat / 2) * sin(d_lat / 2) + + cos(deg2rad(lat1)) * cos(deg2rad(lat2)) * + sin(d_lon / 2) * sin(d_lon / 2); + float c = 2 * atan2(sqrt(a), sqrt(1 - a)); + + return PLANET_RADIUS * c; +} + +/** + * Evaluate the bearing (also known as forward azimuth) using spherical law + * coordinates. + * + * The bearing is a straight line along a great-circle arc from the start point + * to the destination point. + */ +int bearing(float lat1, float lon1, float lat2, float lon2) +{ + float res; + + res = rad2deg(atan2(sin(deg2rad(lon2 - lon1)) * + cos(deg2rad(lat2)), cos(deg2rad(lat1)) * + sin(deg2rad(lat2)) - sin(deg2rad(lat1)) * + cos(deg2rad(lat2)) * cos(deg2rad(lon2) - + deg2rad(lon1)))); + return ((int)res + 360) % 360; +} + +const char *compass_heading(int bearing) +{ + ASSERT(bearing >= 0 && bearing < 360); + /* + * bearing / 22.5 + */ + return _compass_heading[(bearing << 4) / 360]; +} diff --git a/examples/develgps/compass.h b/examples/develgps/compass.h new file mode 100644 index 00000000..f78fda30 --- /dev/null +++ b/examples/develgps/compass.h @@ -0,0 +1,57 @@ +/** + * \file + * + * + * \brief DevelGPS: compass definitions. + * + * \author Andrea Righi + */ + +#ifndef COMPASS_H +#define COMPASS_H + +#define PI 3.14159265358979323846 + +INLINE float deg2rad(float deg) +{ + return deg * PI / 180; +} + +INLINE float rad2deg(float rad) +{ + return rad * 180 / PI; +} + +float distance(float lat1, float lon1, float lat2, float lon2); +int bearing(float lat1, float lon1, float lat2, float lon2); +const char *compass_heading(int bearing); + +#endif /* COMPASS_H */ diff --git a/examples/develgps/develgps.c b/examples/develgps/develgps.c new file mode 100644 index 00000000..8a46e183 --- /dev/null +++ b/examples/develgps/develgps.c @@ -0,0 +1,586 @@ +/** + * \file + * + * + * \brief DevelGPS. + * + * A portable GPS locator / geocaching finder using the Cortex-M3 based + * Luminary Micro LM3S1968 evaluation board. + * + * \author Andrea Righi + */ + +#include + +#include +#include +#include +#include +#include + +#include +#include + +#include + +#include +#include +#include /* BM_PLOT() */ +#include +#include + +#include "compass.h" + +/* OLED/GUI stuff */ +#include "logo.c" +#define KEY_MASK (K_UP | K_DOWN | K_LEFT | K_RIGHT | K_OK) +extern Font font_gohu; +static uint8_t raster[RAST_SIZE(LCD_WIDTH, LCD_HEIGHT)]; +static Bitmap lcd_bitmap; + +#define SCRSVR_TIME 60000 +static ticks_t scrsvr_timestamp; +static bool is_lcd_off; + +/* Serial and NMEA stuff */ +static Serial ser_port; +static nmeap_context_t nmea; +static NmeaGga gga; +static NmeaRmc rmc; +static NmeaVtg vtg; +static bool nmea_update; + +static long prev_b; +static long lat, lon; +static long target_lat, target_lon; + +/* Storage stuff */ +#define GPS_POS_MAGIC 0xdeadbeef +static FlashLM3S flash; + +static void flash_load_target(void) +{ + uint32_t magic; + + kfile_seek(&flash.fd, -FLASH_PAGE_SIZE_BYTES, KSM_SEEK_END); + kfile_read(&flash.fd, &magic, sizeof(magic)); + if (magic == GPS_POS_MAGIC) + { + kfile_read(&flash.fd, &target_lat, sizeof(target_lat)); + kfile_read(&flash.fd, &target_lon, sizeof(target_lon)); + } +} + +static void flash_save_target(void) +{ + const uint32_t magic = GPS_POS_MAGIC; + + kfile_seek(&flash.fd, -FLASH_PAGE_SIZE_BYTES, KSM_SEEK_END); + kfile_write(&flash.fd, &magic, sizeof(magic)); + kfile_write(&flash.fd, &target_lat, sizeof(target_lat)); + kfile_write(&flash.fd, &target_lon, sizeof(target_lon)); + kfile_flush(&flash.fd); +} + +/* Status LED management */ +static void led_init(void) +{ + SYSCTL_RCGC2_R = SYSCTL_RCGC2_GPIOG; + (void)SYSCTL_RCGC2_R; + GPIO_PORTG_DIR_R = 0x04; + GPIO_PORTG_DEN_R = 0x04; +} + +INLINE void led_on(void) +{ + GPIO_PORTG_DATA_R |= 0x04; +} + +INLINE void led_off(void) +{ + GPIO_PORTG_DATA_R &= ~0x04; +} + +/* Display management */ +INLINE void video_off(void) +{ + unsigned long delta = + (long)ticks_to_ms(timer_clock_unlocked()) - + (long)scrsvr_timestamp; + + if (!is_lcd_off && delta > SCRSVR_TIME) + { + rit128x96_off(); + is_lcd_off = true; + } +} + +INLINE void video_on(void) +{ + if (is_lcd_off) + { + rit128x96_on(); + is_lcd_off = false; + } + scrsvr_timestamp = ticks_to_ms(timer_clock_unlocked()); +} + +INLINE void repaint(Bitmap *bm) +{ + rit128x96_blitBitmap(bm); +} + +INLINE keymask_t keypad_peek(void) +{ + keymask_t key = kbd_peek(); + + if (key & KEY_MASK) + { + if (is_lcd_off) + key = 0; + video_on(); + } + return key; +} + +/* Status LED thread */ +static void NORETURN led_process(void) +{ + while (1) + { + video_off(); + if (!nmea_update) + { + timer_delay(1000); + continue; + } + led_on(); + timer_delay(100); + led_off(); + nmea_update = false; + } +} + +/* NMEA parser */ +static void nmea_callback(nmeap_context_t *context, void *data, void *user_data) +{ + (void)context; + (void)data; + (void)user_data; + + lat = (long)gga.latitude; + lon = (long)gga.longitude; + + nmea_update = true; +} + +static void NORETURN ser_process(void) +{ + while (1) + { + nmea_poll(&nmea, &ser_port.fd); + kfile_clearerr(&ser_port.fd); + } +} + +/* Target position screen */ +static void target(Bitmap *bm) +{ + const long STEP = 10000000, + MAX_LAT = 90000000, MIN_LAT = -90000000, + MAX_LON = 180000000, MIN_LON = -180000000; + long step = STEP, target; + int row = 0, pos = 1; + keymask_t key; + + gfx_bitmapClear(bm); + video_on(); + text_xprintf(bm, 0, 0, + STYLEF_UNDERLINE | TEXT_CENTER | TEXT_FILL, + "Target position"); + while (1) + { + if (!is_lcd_off) + { + text_xprintf(bm, 3, 0, TEXT_FILL, + "Lat: %02ld.%06ld %c %s", + ABS(target_lat) / 1000000L, + ABS(target_lat) % 1000000, + target_lat >= 0 ? 'N' : 'S', + row == 0 ? "<-" : ""); + text_xprintf(bm, row ? 4 : 6, 0, + TEXT_FILL | TEXT_CENTER, " "); + text_xprintf(bm, row ? 6 : 4, 0, + TEXT_FILL, "%*c", + (step < 1000000L) ? + pos + 7 : pos + 6, '^'); + text_xprintf(bm, 5, 0, TEXT_FILL, + "Lon: %03ld.%06ld %c %s", + ABS(target_lon) / 1000000L, + ABS(target_lon) % 1000000L, + target_lon >= 0 ? 'E' : 'W', + row == 1 ? "<-" : ""); + repaint(bm); + } + key = keypad_peek(); + if (key & K_UP) + { + if (row == 0) + { + target = target_lat + step; + if (target <= MAX_LAT) + { + if (target_lat < 0 && target > 0) + target_lat = ABS(target_lat) + + step; + else + target_lat = target; + } + } + else + { + target = target_lon + step; + if (target <= MAX_LON) + { + if (target_lon < 0 && target > 0) + target_lon = ABS(target_lon) + + step; + else + target_lon = target; + } + } + } + else if (key & K_DOWN) + { + if (row == 0) + { + target = target_lat - step; + if (target >= MIN_LAT) + { + if (target_lat > 0 && target < 0) + target_lat = -ABS(target_lat) - + step; + else + target_lat = target; + } + } + else + { + target = target_lon - step; + if (target >= MIN_LON) + { + if (target_lon > 0 && target < 0) + target_lon = -ABS(target_lon) - + step; + else + target_lon = target; + } + } + } + else if (key & K_LEFT) + { + if (step < STEP) + { + step *= 10; + pos--; + } + } + else if (key & K_RIGHT) + { + if (step >= 10) + { + step /= 10; + pos++; + } + } + else if (key & K_OK) + { + if (row++ == 1) + break; + /* Move to longigude */ + } + cpu_relax(); + } + flash_save_target(); +} + +/* Compass management */ +static void draw_compass(Bitmap *bm) +{ + const int R = LCD_HEIGHT / 3, R_SMALL = 10; + long x, y, x1, y1, x2, y2, d; + int i; + + d = distance(lat / 1E6, lon / 1E6, target_lat / 1E6, target_lon / 1E6); + + x = (long)((float)R * (1 + sin(deg2rad((float)prev_b)))); + y = (long)((float)R * (1 - cos(deg2rad((float)prev_b)))); + + x1 = R - R_SMALL + (long)((float)R_SMALL * + (1 + sin(deg2rad((float)prev_b - 120.0)))); + y1 = R - R_SMALL + (long)((float)R_SMALL * + (1 - cos(deg2rad((float)prev_b - 120.0)))); + x2 = R - R_SMALL + (long)((float)R_SMALL * + (1 + sin(deg2rad((float)prev_b + 120.0)))); + y2 = R - R_SMALL + (long)((float)R_SMALL * + (1 - cos(deg2rad((float)prev_b + 120.0)))); + + gfx_bitmapClear(bm); + /* Print direction heading and degrees */ + text_xprintf(bm, 0, 5, 0, "%s", "N"); + text_xprintf(bm, 0, 0, TEXT_RIGHT, "%s", compass_heading(prev_b)); + text_xprintf(bm, 1, 0, TEXT_RIGHT, "%ld deg.", prev_b); + /* Print distance */ + text_xprintf(bm, 2, 0, TEXT_RIGHT, "%ld %s", + d >= 1000 ? d / 1000 : d, + d >= 1000 ? "Km" : "m"); + /* Print current and target position */ + text_xprintf(bm, 6, 0, TEXT_FILL, "%02ld.%06ld%c%03ld.%06ld%c", + ABS(lat) / 1000000L, + ABS(lat) % 1000000, + lat >= 0 ? 'N' : 'S', + ABS(lon) / 1000000L, + ABS(lon) % 1000000L, + lon >= 0 ? 'E' : 'W'); + text_xprintf(bm, 7, 0, TEXT_FILL, "%02ld.%06ld%c%03ld.%06ld%c", + ABS(target_lat) / 1000000L, + ABS(target_lat) % 1000000, + target_lat >= 0 ? 'N' : 'S', + ABS(target_lon) / 1000000L, + ABS(target_lon) % 1000000L, + target_lon >= 0 ? 'E' : 'W'); + /* Draw the circle */ + for (i = 0; i < 360; i++) + BM_PLOT(bm, + (long)((float)R * (1 + sin(deg2rad((float)i)))), + (long)((float)R * (1 - cos(deg2rad((float)i))))); + /* Draw the needle */ + gfx_rectFill(bm, R - 2, R - 2, R + 2, R + 2); + gfx_line(bm, R, R, x1, y1); + gfx_line(bm, R, R, x2, y2); + gfx_line(bm, x1, y1, x, y); + gfx_line(bm, x2, y2, x, y); + + repaint(bm); +} + +static void compass(Bitmap *bm) +{ + long b, inc; + + video_on(); + while (1) + { + if (!is_lcd_off) + { + b = bearing(lat / 1E6, lon / 1E6, + target_lat / 1E6, target_lon / 1E6); + inc = ABS(b - prev_b) < 360 - ABS(b - prev_b) ? 1 : -1; + /* Compass animation */ + if (b < prev_b) + inc = -inc; + while (prev_b != b) + { + prev_b = (prev_b + inc) % 360; + if (prev_b < 0) + prev_b = 359; + if (!(prev_b % 5)) + draw_compass(bm); + if (keypad_peek() & KEY_MASK) + return; + } + draw_compass(bm); + } + cpu_relax(); + if (keypad_peek() & KEY_MASK) + return; + } +} + +/* GPS receiver status */ +static const char *gps_fix[] = +{ + "invalid", + "GPS", + "DGPS", + "PPS", + "RTK", + "float-RTK", + "estimated", + "manual", + "simulation", +}; + +static void gps_data(Bitmap *bm) +{ + struct tm tm; + char buf[32]; + + video_on(); + gfx_bitmapClear(bm); + while (1) + { + if (!is_lcd_off) + { + if (!rmc.time) + { + text_xprintf(bm, 3, 0, + TEXT_CENTER | TEXT_FILL, "No GPS data"); + } + else + { + gmtime_r(&rmc.time, &tm); + + text_xprintf(bm, 0, 0, TEXT_FILL, + "Lat. %ld.%06ld%c", + ABS(lat) / 1000000L, + ABS(lat) % 1000000, + lat >= 0 ? 'N' : 'S'); + text_xprintf(bm, 1, 0, TEXT_FILL, + "Lon. %ld.%06ld%c", + ABS(lon) / 1000000L, + ABS(lon) % 1000000L, + lon >= 0 ? 'E' : 'W'); + text_xprintf(bm, 2, 0, TEXT_FILL, + "Alt. %d", gga.altitude); + text_xprintf(bm, 3, 0, TEXT_FILL, + "Speed: %d", vtg.km_speed); + if (gga.quality < countof(gps_fix)) + text_xprintf(bm, 4, 0, TEXT_FILL, + "Fix: %s", + gps_fix[gga.quality]); + else + text_xprintf(bm, 4, 0, TEXT_FILL, + "Fix: %d", gga.quality); + text_xprintf(bm, 5, 0, TEXT_FILL, + "Satellites: %d", + gga.satellites); + strftime(buf, sizeof(buf), + "Date: %Y-%m-%d %a", &tm); + text_xprintf(bm, 6, 0, TEXT_FILL, "%s", buf); + strftime(buf, sizeof(buf), + "Time: %H:%M:%S (UTC)", &tm); + text_xprintf(bm, 7, 0, TEXT_FILL, "%s", buf); + } + repaint(bm); + } + if (keypad_peek() & KEY_MASK) + break; + cpu_relax(); + } +} + +/* BeRTOS screen */ +static void about(Bitmap *bm) +{ + gfx_bitmapClear(bm); + video_on(); + text_xprintf(bm, 7, 0, + STYLEF_UNDERLINE | TEXT_CENTER | TEXT_FILL, + "http://www.bertos.org"); + repaint(bm); + if (!is_lcd_off) + { + const uint8_t *p = &logo[BITMAP_HEADER_SIZE]; + uint8_t h = logo[BITMAP_HEIGHT_OFFSET]; + uint8_t w = logo[BITMAP_WIDTH_OFFSET]; + uint8_t r; + + for (r = 0; r < h; r++) + { + rit128x96_blitRaw(p, + (128 - w) / 2, 70 - r, w, 1); + p += w / 2; + } + } + while (!(keypad_peek() & KEY_MASK)) + cpu_relax(); +} + +static struct MenuItem main_items[] = +{ + {(const_iptr_t)"Target", 0, (MenuHook)target, (iptr_t)&lcd_bitmap}, + {(const_iptr_t)"Compass", 0, (MenuHook)compass, (iptr_t)&lcd_bitmap}, + {(const_iptr_t)"GPS data", 0, (MenuHook)gps_data, (iptr_t)&lcd_bitmap}, + {(const_iptr_t)"About...", 0, (MenuHook)about, (iptr_t)&lcd_bitmap}, + {(const_iptr_t)0, 0, NULL, (iptr_t)NULL} +}; + +static struct Menu main_menu = +{ + main_items, "DevelGPS v0.1", MF_STICKY | MF_SAVESEL, &lcd_bitmap, 0 +}; + +static void init(void) +{ + IRQ_ENABLE; + + kdbg_init(); + timer_init(); + proc_init(); + + scrsvr_timestamp = ticks_to_ms(timer_clock_unlocked()); + led_init(); + + flash_lm3sInit(&flash); + flash_load_target(); + + ser_init(&ser_port, SER_UART1); + ser_setbaudrate(&ser_port, 38400); + + nmeap_init(&nmea, NULL); + nmeap_addParser(&nmea, "GPGGA", nmea_gpgga, nmea_callback, &gga); + nmeap_addParser(&nmea, "GPRMC", nmea_gprmc, nmea_callback, &rmc); + nmeap_addParser(&nmea, "GPVTG", nmea_gpvtg, nmea_callback, &vtg); + + rit128x96_init(); + gfx_bitmapInit(&lcd_bitmap, raster, LCD_WIDTH, LCD_HEIGHT); + gfx_setFont(&lcd_bitmap, &font_gohu); + repaint(&lcd_bitmap); + + kbd_init(); +} + +int main(void) +{ + init(); + + proc_new(led_process, NULL, KERN_MINSTACKSIZE * 2, NULL); + proc_new(ser_process, NULL, KERN_MINSTACKSIZE * 2, NULL); + + while (1) + { + iptr_t res = menu_handle(&main_menu); + if (res != MENU_TIMEOUT) + video_on(); + cpu_relax(); + } +} diff --git a/examples/develgps/develgps.mk b/examples/develgps/develgps.mk new file mode 100644 index 00000000..7b8299ed --- /dev/null +++ b/examples/develgps/develgps.mk @@ -0,0 +1,84 @@ +# +# Copyright 2010 Develer S.r.l. (http://www.develer.com/) +# All rights reserved. +# +# Author: Andrea Righi +# + +# Set to 1 for debug builds +develgps_DEBUG = 0 + +include bertos/fonts/fonts.mk + +# Our target application +TRG += develgps + +develgps_CSRC = \ + examples/develgps/develgps.c \ + examples/develgps/logo.c \ + examples/develgps/compass.c \ + bertos/gfx/bitmap.c \ + bertos/gfx/line.c \ + bertos/gfx/win.c \ + bertos/gfx/text.c \ + bertos/gfx/text_format.c \ + bertos/gui/menu.c \ + bertos/fonts/gohu.c \ + bertos/fonts/luBS14.c \ + bertos/icons/logo.c \ + bertos/mware/formatwr.c \ + bertos/mware/hex.c \ + bertos/mware/sprintf.c \ + bertos/mware/event.c \ + bertos/struct/heap.c \ + bertos/drv/timer.c \ + bertos/drv/ser.c \ + bertos/drv/kbd.c \ + bertos/drv/lcd_rit128x96.c \ + bertos/kern/kfile.c \ + bertos/kern/monitor.c \ + bertos/kern/proc.c \ + bertos/kern/signal.c \ + bertos/net/nmea.c \ + bertos/net/nmeap/src/nmeap01.c \ + bertos/cpu/cortex-m3/drv/flash_lm3s.c \ + bertos/cpu/cortex-m3/drv/gpio_lm3s.c \ + bertos/cpu/cortex-m3/drv/clock_lm3s.c \ + bertos/cpu/cortex-m3/drv/ser_lm3s.c \ + bertos/cpu/cortex-m3/drv/kdebug_lm3s.c \ + bertos/cpu/cortex-m3/drv/ssi_lm3s.c \ + bertos/cpu/cortex-m3/drv/timer_cm3.c \ + bertos/cpu/cortex-m3/drv/irq_cm3.c \ + bertos/cpu/cortex-m3/hw/switch_ctx_cm3.c \ + bertos/cpu/cortex-m3/hw/init_lm3s.c + +develgps_CPPASRC = \ + bertos/cpu/cortex-m3/hw/vectors_cm3.S \ + bertos/cpu/cortex-m3/hw/crt_cm3.S \ + # + +# This is an hosted application +develgps_PREFIX = arm-none-eabi- + +develgps_CPPAFLAGS = -mthumb -mno-thumb-interwork +develgps_CPPFLAGS = -D'ARCH=0' -D__ARM_LM3S1968__ -D'CPU_FREQ=(50000000L)' -D'WIZ_AUTOGEN' -mthumb -mno-thumb-interwork -Iexamples/develgps -Ibertos/cpu/cortex-m3 -fno-strict-aliasing -fwrapv +develgps_LDFLAGS = -nostartfiles -T bertos/cpu/cortex-m3/scripts/lm3s1968_rom.ld -Wl,--no-warn-mismatch -mthumb -mno-thumb-interwork + +develgps_CPU = cortex-m3 + +develgps_PROGRAMMER_CPU = lm3s1968 +develgps_PROGRAMMER_TYPE = lm3s1968 +develgps_FLASH_SCRIPT = bertos/prg_scripts/arm/flash-cortex.sh +develgps_STOPFLASH_SCRIPT = bertos/prg_scripts/arm/stopopenocd.sh +develgps_DEBUG_SCRIPT = bertos/prg_scripts/arm/debug-cortex.sh +develgps_STOPDEBUG_SCRIPT = bertos/prg_scripts/arm/stopopenocd.sh + +ifeq ($(develgps_DEBUG),0) + # Production options + develgps_CFLAGS += -O2 -fomit-frame-pointer + develgps_CXXFLAGS += -O2 -fomit-frame-pointer +else + # Debug options + develgps_CPPAFLAGS += -g -gdwarf-2 + develgps_CPPFLAGS += -O0 -g3 -gdwarf-2 -fverbose-asm +endif diff --git a/examples/develgps/hw/hw_afsk.h b/examples/develgps/hw/hw_afsk.h new file mode 100644 index 00000000..ec9b8be2 --- /dev/null +++ b/examples/develgps/hw/hw_afsk.h @@ -0,0 +1,87 @@ +/** + * \file + * + * + * \brief AFSK modem hardware-specific definitions. + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef HW_AFSK_H +#define HW_AFSK_H + +#include "cfg/cfg_arch.h" + +#warning TODO:This is an example implementation, you must implement it! + +/** + * Initialize the specified channel of the ADC for AFSK needs. + * The adc should be configured to have a continuos stream of convertions. + * For every convertion there must be an ISR that read the sample + * and call afsk_adc_isr(), passing the context and the sample. + * + * \param ch channel to be used for AFSK demodulation. + * \param ctx AFSK context (\see Afsk). This parameter must be saved and + * passed back to afsk_adc_isr() for every convertion. + */ +#define AFSK_ADC_INIT(ch, ctx) do { (void)ch, (void)ctx; } while (0) + +#define AFSK_STROBE_INIT() do { /* Implement me */ } while (0) +#define AFSK_STROBE_ON() do { /* Implement me */ } while (0) +#define AFSK_STROBE_OFF() do { /* Implement me */ } while (0) + +/** + * Initialize the specified channel of the DAC for AFSK needs. + * The DAC has to be configured in order to call an ISR for every sample sent. + * The DAC doesn't have to start the IRQ immediatly but have to wait + * the AFSK driver to call AFSK_DAC_IRQ_START(). + * The ISR must then call afsk_dac_isr() passing the AFSK context. + * \param ch DAC channel to be used for AFSK modulation. + * \param ctx AFSK context (\see Afsk). This parameter must be saved and + * passed back to afsk_dac_isr() for every convertion. + */ +#define AFSK_DAC_INIT(ch, ctx) do { (void)ch, (void)ctx; } while (0) + +/** + * Start DAC convertions on channel \a ch. + * \param ch DAC channel. + */ +#define AFSK_DAC_IRQ_START(ch) do { (void)ch; /* Implement me */ } while (0) + +/** + * Stop DAC convertions on channel \a ch. + * \param ch DAC channel. + */ +#define AFSK_DAC_IRQ_STOP(ch) do { (void)ch; /* Implement me */ } while (0) + +#endif /* HW_AFSK_H */ diff --git a/examples/develgps/hw/hw_buzzer.h b/examples/develgps/hw/hw_buzzer.h new file mode 100644 index 00000000..858ecbfb --- /dev/null +++ b/examples/develgps/hw/hw_buzzer.h @@ -0,0 +1,52 @@ +/** + * \file + * + * + * \brief Buzzer hardware-specific definitions + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef HW_BUZZER_H +#define HW_BUZZER_H + +#warning TODO:This is an example implementation, you must implement it! + +#define BUZZER_BIT 1 +#define IS_BUZZER_ON 0 +#define BUZZER_HW_INIT do { /* Implement me! */ } while (0) +#define BUZZER_ON do { /* Implement me! */ } while (0) +#define BUZZER_OFF do { /* Implement me! */ } while (0) + +#endif /* HW_BUZZER_H */ diff --git a/examples/develgps/hw/hw_dataflash.c b/examples/develgps/hw/hw_dataflash.c new file mode 100644 index 00000000..844dd922 --- /dev/null +++ b/examples/develgps/hw/hw_dataflash.c @@ -0,0 +1,126 @@ +/** + * \file + * + * + * \brief Dataflash HW control routines. + * + * \version $Id$ + * \author Francesco Sacchi + */ + +#include "hw/hw_dataflash.h" + +#include +#include +#include + +#warning TODO:This is an example implementation, you must implement it! + +MOD_DEFINE(hw_dataflash); + +/** + * Data flash init function. + * + * This function provide to initialize all that + * needs to drive a dataflash memory. + * Generaly needs to init pins to drive a CS line + * and reset line. + */ +void dataflash_hw_init(void) +{ + + //Disable CS line (remove if not needed) + dataflash_hw_setCS(false); + + /* + * Put here your code! + * + * Note: + * - if you drive manualy CS line, here init a CS pin + * - if you use a dedicated reset line, here init a reset pin + */ + + MOD_INIT(hw_dataflash); +} + +/** + * Chip Select drive. + * + * This function enable or disable a CS line. + * You must implement this function comply to a dataflash + * memory datasheet to allow the drive to enable a memory + * when \p enable flag is true, and disable it when is false. + */ +void dataflash_hw_setCS(bool enable) +{ + if (enable) + { + /* + * Put here your code to enable + * dataflash memory + */ + } + else + { + /* + * Put here your code to disable + * dataflash memory + */ + } +} + +/** + * Reset data flash memory. + * + * This function provide to send reset signal to + * dataflash memory. You must impement it comly to a dataflash + * memory datasheet to allow the drive to set a reset pin + * when \p enable flag is true, and disable it when is false. + * + */ +void dataflash_hw_setReset(bool enable) +{ + if (enable) + { + /* + * Put here your code to set reset of + * dataflash memory + */ + } + else + { + /* + * Put here your code to clear reset of + * dataflash memory + */ + } +} + diff --git a/examples/develgps/hw/hw_dataflash.h b/examples/develgps/hw/hw_dataflash.h new file mode 100644 index 00000000..5254446b --- /dev/null +++ b/examples/develgps/hw/hw_dataflash.h @@ -0,0 +1,48 @@ +/** + * \file + * + * + * \brief Dataflash HW control routines (interface). + * + * \version $Id$ + * \author Francesco Sacchi + */ + +#ifndef HW_DATAFLASH_H +#define HW_DATAFLASH_H + +#include + +void dataflash_hw_init(void); +void dataflash_hw_setCS(bool enable); +void dataflash_hw_setReset(bool enable); + +#endif /* HW_DATAFLASH_H */ diff --git a/examples/develgps/hw/hw_dc_motor.h b/examples/develgps/hw/hw_dc_motor.h new file mode 100644 index 00000000..8b8dd4b4 --- /dev/null +++ b/examples/develgps/hw/hw_dc_motor.h @@ -0,0 +1,85 @@ +/** + * \file + * + * + * \brief DC motor hardware-specific definitions + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef HW_DC_MOTOR_H +#define HW_DC_MOTOR_H + +typedef enum MotorDCMap +{ + + /* Put here motor dc declaration */ + MOTOR_DC_CNT + +} MotorDCMap; + +/* + * Init all pin and device to manage dc motor. + */ +#define MOTOR_DC_INIT() \ + do { \ + /* Implement me! */ \ + } while (0) + + +/* + * Enable DC motor. + */ +#define DC_MOTOR_ENABLE(dev) \ + do { \ + /* Implement me! */ \ + } while (0) + +/* + * Disable DC motor. + */ +#define DC_MOTOR_DISABLE(dev) \ + do { \ + /* Implement me! */ \ + } while (0) + +/* + * Set direction for DC motor. + */ +#define DC_MOTOR_SET_DIR(dev, dir) \ + do { \ + /* Implement me! */ \ + } while (0) + + +#endif /* HW_DC_MOTOR_H */ diff --git a/examples/develgps/hw/hw_ft245rl.h b/examples/develgps/hw/hw_ft245rl.h new file mode 100644 index 00000000..cc0c8193 --- /dev/null +++ b/examples/develgps/hw/hw_ft245rl.h @@ -0,0 +1,65 @@ +/** + * \file + * + * + * \brief FT245RL USB interface hardware-specific definitions + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef HW_FT245RL_H +#define HW_FT245RL_H + +#warning TODO:This is an example implementation, you must implement it! + +#define FT245RL_DATA_IN() /* Implement me! */ +#define FT245RL_DATA_OUT() /* Implement me! */ +#define WR_HI /* Implement me! */ +#define WR_LO /* Implement me! */ + +#define RD_HI /* Implement me! */ +#define RD_LO /* Implement me! */ + +#define FT245RL_INIT() \ +do \ +{ \ + /* Implement me! */ \ +} while(0) + +#define FT245RL_DATA_RDY() (/* Implement me! */ false) +#define FT245RL_GETDATA() ({/* Implement me! */ (0);}) +#define FT245RL_TX_ALLOWED() (/* Implement me! */ false) +#define FT245RL_SETDATA(data) do {/* Implement me! */ (void)((data)); } while(0) + +#endif /* HW_FT245RL_H */ + diff --git a/examples/develgps/hw/hw_i2c_bitbang.h b/examples/develgps/hw/hw_i2c_bitbang.h new file mode 100644 index 00000000..4822af7c --- /dev/null +++ b/examples/develgps/hw/hw_i2c_bitbang.h @@ -0,0 +1,66 @@ +/** + * \file + * + * + * \brief Macro for I2C bitbang operation. + * + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef HW_I2C_BITBANG_H +#define HW_I2C_BITBANG_H + +#warning TODO:This is an example implementation, you must implement it! + +#define SDA_HI do { /* Implement me:Set SDA High by setting SDA pin as input */ } while (0) +#define SDA_LO do { /* Implement me:Set SDA Low by setting SDA pin as open collector output */ } while (0) +#define SCL_HI do { /* Implement me:Set SCL High by setting SCL pin as input */ } while (0) +#define SCL_LO do { /* Implement me:Set SCL Low by setting SCL pin as open collector output */ } while (0) + + +#define SCL_IN (true) /* Implement me: read SDA pin state */ +#define SDA_IN (true) /* Implement me: read SCL pin state */ + +/** + * This macro should set SDA and SCL lines as input. + */ +#define I2C_BITBANG_HW_INIT do { /* Implement me! */ } while (0) + +/** + * Half bit delay routine used to generate the correct timings. + */ +#define I2C_HALFBIT_DELAY() do { /* Implement me! */ } while (0) + +#endif /* HW_I2C_BITBANG_H */ diff --git a/examples/develgps/hw/hw_kbd.h b/examples/develgps/hw/hw_kbd.h new file mode 100644 index 00000000..10562f79 --- /dev/null +++ b/examples/develgps/hw/hw_kbd.h @@ -0,0 +1,66 @@ +/** + * \file + * + * + * \brief LM3S1968 keypad: hardware-specific definitions + * + * \author Andrea Righi + */ + +#ifndef HW_KBD_H +#define HW_KBD_H + +#include /* BV() */ +#include /* GPIO_PORTG_BASE */ +#include /* lm3s_gpioPinConfig() / lm3s_gpioPinRead() */ +#include "hw/kbd_map.h" + +#define K_RPT_MASK (K_UP | K_DOWN | K_LEFT | K_RIGHT | K_OK) + +#define KBD_HW_INIT \ + do { \ + lm3s_gpioPinConfig(GPIO_PORTG_BASE, \ + K_RPT_MASK, \ + GPIO_DIR_MODE_IN, \ + GPIO_STRENGTH_2MA, \ + GPIO_PIN_TYPE_STD_WPU); \ + } while (0) + +/** + * Read the keyboard ports and return the mask of depressed keys. + */ +INLINE keymask_t kbd_readkeys(void) +{ + return ~lm3s_gpioPinRead(GPIO_PORTG_BASE, + K_UP | K_DOWN | K_LEFT | K_RIGHT | K_OK); +} + +#endif /* HW_KBD_H */ diff --git a/examples/develgps/hw/hw_lcd.h b/examples/develgps/hw/hw_lcd.h new file mode 100644 index 00000000..21b64d4e --- /dev/null +++ b/examples/develgps/hw/hw_lcd.h @@ -0,0 +1,162 @@ +/** + * \file + * + * + * \brief LCD low-level hardware macros + * + * \version $Id$ + * + * \author Bernie Innocenti + * \author Stefano Fedrigo + * + */ + +#ifndef HW_LCD_H +#define HW_LCD_H + +#include "cfg/cfg_lcd.h" /* CONFIG_LCD_4BIT */ +#include /* BV() */ +#include + +#include +#include +#include + +#warning TODO:This is an example implementation, you must implement it! + +/** + * \name LCD I/O pins/ports + * @{ + */ +#define LCD_RS /* Implement me! */ +#define LCD_RW /* Implement me! */ +#define LCD_E /* Implement me! */ +#define LCD_DB0 /* Implement me! */ +#define LCD_DB1 /* Implement me! */ +#define LCD_DB2 /* Implement me! */ +#define LCD_DB3 /* Implement me! */ +#define LCD_DB4 /* Implement me! */ +#define LCD_DB5 /* Implement me! */ +#define LCD_DB6 /* Implement me! */ +#define LCD_DB7 /* Implement me! */ +/*@}*/ + +/** + * \name DB high nibble (DB[4-7]) + * @{ + */ + +#if CONFIG_LCD_4BIT + #define LCD_MASK (LCD_DB7 | LCD_DB6 | LCD_DB5 | LCD_DB4) + #define LCD_SHIFT 4 +#else + #define LCD_MASK (uint8_t)0xff + #define LCD_SHIFT 0 +#endif +/*@}*/ + +/** + * \name LCD bus control macros + * @{ + */ +#define LCD_CLR_RS /* Implement me! */ +#define LCD_SET_RS /* Implement me! */ +#define LCD_CLR_RD /* Implement me! */ +#define LCD_SET_RD /* Implement me! */ +#define LCD_CLR_E /* Implement me! */ +#define LCD_SET_E /* Implement me! */ + +/* Enter command mode */ +#define LCD_SET_COMMAND() /* Implement me! */ + +/* Enter data mode */ +#define LCD_SET_DATA() /* Implement me! */ + +#if CONFIG_LCD_4BIT + #define LCD_WRITE_H(x) ((void)x)/* Implement me! */ + #define LCD_WRITE_L(x) ((void)x)/* Implement me! */ + #define LCD_READ_H ( 0 /* Implement me! */ ) + #define LCD_READ_L ( 0 /* Implement me! */ ) +#else + #define LCD_WRITE(x) ((void)x)/* Implement me! */ + #define LCD_READ (0 /* Implement me! */ ) +#endif +/*@}*/ + +/** Set data bus direction to output (write to display) */ +#define LCD_DB_OUT /* Implement me! */ + +/** Set data bus direction to input (read from display) */ +#define LCD_DB_IN /* Implement me! */ + +/** Delay for write (Enable pulse width, 220ns) */ +#define LCD_DELAY_WRITE \ + do { \ + NOP; \ + NOP; \ + NOP; \ + NOP; \ + NOP; \ + } while (0) + +/** Delay for read (Data ouput delay time, 120ns) */ +#define LCD_DELAY_READ \ + do { \ + NOP; \ + NOP; \ + NOP; \ + NOP; \ + } while (0) + + +INLINE void lcd_bus_init(void) +{ + cpu_flags_t flags; + IRQ_SAVE_DISABLE(flags); + + /* + * Here set bus pin! + * to init a lcd device. + * + */ + + /* + * Data bus is in output state most of the time: + * LCD r/w functions assume it is left in output state + */ + LCD_DB_OUT; + + + IRQ_RESTORE(flags); +} + +#endif /* HW_LCD_H */ diff --git a/examples/develgps/hw/hw_lm75.h b/examples/develgps/hw/hw_lm75.h new file mode 100644 index 00000000..290dae09 --- /dev/null +++ b/examples/develgps/hw/hw_lm75.h @@ -0,0 +1,49 @@ +/** + * \file + * + * + * \brief Hardware macro definition. + * + * \author Daniele Basile + */ + +#ifndef HW_LM75_H +#define HW_LM75_H + +#warning TODO:This is an example implentation, you must implement it! + +#define LM75_HW_INIT() \ + do { \ + /* Pin init */\ + } while (0) + +#endif /* HW_LM75_H */ + diff --git a/examples/develgps/hw/hw_mcp41.c b/examples/develgps/hw/hw_mcp41.c new file mode 100644 index 00000000..dc2a051c --- /dev/null +++ b/examples/develgps/hw/hw_mcp41.c @@ -0,0 +1,53 @@ +/** + * \file + * + * + * \brief MCP41 hardware-specific definitions + * + * \version $Id$ + * \author Francesco Sacchi + */ + +#include "hw/hw_mcp41.h" + +#include +#include + +#warning TODO:This is an example implementation, you must implement it! + +const uint16_t mcp41_ports[MCP41_CNT] = +{ + 0, /* add here mcp41 ports */ +}; +const uint8_t mcp41_pins [MCP41_CNT] = +{ + 0, /* add here mcp41 ports */ +}; + diff --git a/examples/develgps/hw/hw_mcp41.h b/examples/develgps/hw/hw_mcp41.h new file mode 100644 index 00000000..645b6dac --- /dev/null +++ b/examples/develgps/hw/hw_mcp41.h @@ -0,0 +1,75 @@ +/** + * \file + * + * + * \brief MCP41 hardware-specific definitions + * + * \version $Id$ + * \author Francesco Sacchi + */ + +#ifndef HW_MCP41_H +#define HW_MCP41_H + +#include "hw/mcp41_map.h" + +#include + + +#warning TODO:This is an example implementation, you must implement it! + + +INLINE void SET_MCP41_DDR(Mcp41Dev dev) +{ + /* Implement me! */ + //Warning: this funtions is like avr target name, + //fix it to comply for all target. + + //Only for test remove when implement this function + (void)dev; +} + +INLINE void MCP41_ON(Mcp41Dev i) +{ + /* Implement me! */ + + //Only for test remove when implement this function + (void)i; +} + +INLINE void MCP41_OFF(Mcp41Dev i) +{ + /* Implement me! */ + + //Only for test remove when implement this function + (void)i; +} + +#endif /* HW_MCP41_H */ diff --git a/examples/develgps/hw/hw_ntc.c b/examples/develgps/hw/hw_ntc.c new file mode 100644 index 00000000..b8c56914 --- /dev/null +++ b/examples/develgps/hw/hw_ntc.c @@ -0,0 +1,46 @@ +/** + * \file + * + * + * \brief NTC hardware-specific definition + * + * \version $Id: hw_ntc.h 1359 2008-05-26 09:42:37Z asterix $ + * \author Lorenzo Berni + * + */ + +#include +#include "hw/ntc_map.h" + +const res_t NTC_RSER[NTC_CNT]; +const res_t NTC_RPAR[NTC_CNT]; +const amp_t NTC_AMP[NTC_CNT]; +const NtcHwInfo* NTC_INFO[NTC_CNT]; diff --git a/examples/develgps/hw/hw_ntc.h b/examples/develgps/hw/hw_ntc.h new file mode 100644 index 00000000..49152a45 --- /dev/null +++ b/examples/develgps/hw/hw_ntc.h @@ -0,0 +1,136 @@ +/** + * \file + * + * + * \brief NTC hardware-specific definition + * + * \version $Id$ + * \author Francesco Sacchi + * + * A NTC acts as a variable resistor, whose resistance changes as a + * function of the temperature it measures. To sample it correctly, it is + * usually parallelized and serialized with two fixed resistor. The following diagram shows + * what is the exact disposition of the components, as handled by this + * library: + * + *
+ *                 o Vref
+ *                 |
+ *                 |                               o Vref
+ *                 |                               |
+ *               -----                             |
+ *              |     |                        ---------
+ *              | Rser|                       |         |
+ *              |     |                       |         |
+ *               -----     -----              |   ADC   |
+ *                 | Vp   |     |             |         |
+ *      -----------|------| Amp |-------------|         |
+ *     |           |      |     |      Vadc   |         |
+ *   -----       -----     -----               ---------
+ *  |     |     |     |
+ *  | NTC |     | Rpar|
+ *  |     |     |     |
+ *   -----       -----
+ *     |           |
+ *     |           |
+ *   -----       -----
+ *    ---         ---
+ *
+ * Amp is an amplifier that amplify of AMP times the signal. + * If we indicate Rp as the parallel of NTC with Rpar, ADCBITS as the bits of the ad converter + * and ADCVAL as the result from the adc convertion (Not Vadc but just the value read + * from the adc register), after various calculation, the expression of Rp is: + * + *
+ *
+ *            ADCVAL * Rser
+ * Rp = ------------------------
+ *         ADCBITS
+ *	2         * AMP - ADCVAL
+ *
+ * + * And after that NTC obvisiously is: + *
+ *        Rpar * Rp
+ * NTC = ----------
+ *        Rpar - Rp
+ *
+ * + * + * The function ntc_hw_read() compute the resistence using these formulas above. + */ + +#ifndef HW_NTC_H +#define HW_NTC_H + +#include "ntc_map.h" + +#include + +#include +#include + +#warning TODO:This is an example implementation, you must implement it! + +extern const res_t NTC_RSER[NTC_CNT]; +extern const res_t NTC_RPAR[NTC_CNT]; +extern const amp_t NTC_AMP[NTC_CNT]; +extern const NtcHwInfo* NTC_INFO[NTC_CNT]; + + +/*! + * Read the resistence of ntc device \a dev. + * Return the result in res_t type. + */ +INLINE res_t ntc_hw_read(NtcDev dev) +{ + ASSERT(dev < NTC_CNT); + // See above for formula explanation. + adcread_t adcval = adc_read((uint16_t)dev); + float rp = (adcval * NTC_RSER[dev] ) / ((1 << adc_bits()) * NTC_AMP[dev] - adcval); + + //kprintf("Rp[%f], Rntc[%f]\n", rp/100, ((NTC_RPAR[dev] * rp) / (NTC_RPAR[dev] - rp)) / 100.0); + + return ( (NTC_RPAR[dev] * rp) / (NTC_RPAR[dev] - rp) ); +} + + +/*! + * Return the info (aka the table) associated with ntc device \a dev. + */ +INLINE const NtcHwInfo* ntc_hw_getInfo(NtcDev dev) +{ + return NTC_INFO[dev]; +} + +#define NTC_HW_INIT do { /* Implement me! */ } while(0) + +#endif /* HW_NTC_H */ diff --git a/examples/develgps/hw/hw_phase.c b/examples/develgps/hw/hw_phase.c new file mode 100644 index 00000000..54509ef3 --- /dev/null +++ b/examples/develgps/hw/hw_phase.c @@ -0,0 +1,46 @@ +/** + * \file + * + * + * \brief Phase control hardware-specific definitions + * + * \version $Id$ + * \author Francesco Sacchi + */ + +#ifndef HW_PHASE_H +#define HW_PHASE_H + +#include "hw/hw_phase.h" + +#warning TODO:This is an example implementation, you must implement it! + +#endif /* HW_PHASE_H */ diff --git a/examples/develgps/hw/hw_phase.h b/examples/develgps/hw/hw_phase.h new file mode 100644 index 00000000..7649e702 --- /dev/null +++ b/examples/develgps/hw/hw_phase.h @@ -0,0 +1,80 @@ +/** + * \file + * + * + * \brief Phase control hardware-specific definitions + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef HW_PHASE_H +#define HW_PHASE_H + +#include "hw/phase_map.h" + +#include + +#warning TODO:This is an example implementation, you must implement it! + +#define PHASE_HW_INIT do { /* Implement me! */ }while (0) + +INLINE void TRIAC_OFF(TriacDev i) +{ + /* Implement me! */ + + //Only for test remove when implement this function + (void)i; +} + + +INLINE void TRIAC_ON(TriacDev i) +{ + /* Implement me! */ + + //Only for test remove when implement this function + (void)i; +} + +INLINE void SET_TRIAC_DDR(TriacDev i) +{ + /* Implement me! */ + + //Only for test remove when implement this function + (void)i; +} + +void zerocross_isr(void); +#define DEFINE_ZEROCROSS_ISR() void zerocross_isr(void) + + +#endif /* HW_PHASE_H */ diff --git a/examples/develgps/hw/hw_rit128x96.h b/examples/develgps/hw/hw_rit128x96.h new file mode 100644 index 00000000..7ccdeb1d --- /dev/null +++ b/examples/develgps/hw/hw_rit128x96.h @@ -0,0 +1,128 @@ +/** + * \file + * + * + * \brief LM3S1986: OLED-RIT-128x96 (P14201) low-level hardware macros + * + * \author Andrea Righi + */ + +#ifndef HW_RIT128x96_H +#define HW_RIT128x96_H + +#include "cfg/macros.h" /* BV() */ +#include "cfg/debug.h" + +#include +#include +#include + +#include +#include +#include + +/** + * \name LCD I/O pins/ports + * @{ + */ +/* OLED Data/Command control pin */ +#define GPIO_OLEDDC_PIN BV(2) + +/* OLED enable pin */ +#define GPIO_OLEDEN_PIN BV(3) +/*@}*/ + +/** + * \name LCD bus control macros + * @{ + */ +/* Enter command mode */ +#define LCD_SET_COMMAND() \ + lm3s_gpioPinWrite(GPIO_PORTH_BASE, GPIO_OLEDDC_PIN, 0) + +/* Enter data mode */ +#define LCD_SET_DATA() \ + lm3s_gpioPinWrite(GPIO_PORTH_BASE, GPIO_OLEDDC_PIN, GPIO_OLEDDC_PIN) + +/* Send data to the display */ +#define LCD_WRITE(x) \ + { \ + uint32_t _x; \ + while (!lm3s_ssiWriteFrameNonBlocking(SSI0_BASE, x)); \ + /* Dummy read to drain the FIFO */ \ + while (!lm3s_ssiReadFrameNonBlocking(SSI0_BASE, &_x)); \ + } +/*@}*/ + +INLINE void lcd_bus_init(void) +{ + uint32_t dummy; + + /* Enable the peripheral clock */ + SYSCTL_RCGC1_R |= SYSCTL_RCGC1_SSI0; + SYSCTL_RCGC2_R |= SYSCTL_RCGC2_GPIOA; + SYSCTL_RCGC2_R |= SYSCTL_RCGC2_GPIOH; + lm3s_busyWait(512); + + /* Configure the SSI0CLK and SSIOTX pins for SSI operation. */ + lm3s_gpioPinConfig(GPIO_PORTA_BASE, BV(2) | BV(3) | BV(5), + GPIO_DIR_MODE_HW, GPIO_STRENGTH_8MA, GPIO_PIN_TYPE_STD_WPU); + /* + * Configure the GPIO port pin used as a D/C# signal (data/command + * control) for OLED device, and the port pin used to enable power to + * the OLED panel. + */ + lm3s_gpioPinConfig(GPIO_PORTH_BASE, GPIO_OLEDDC_PIN | GPIO_OLEDEN_PIN, + GPIO_DIR_MODE_OUT, GPIO_STRENGTH_8MA, GPIO_PIN_TYPE_STD); + lm3s_gpioPinWrite(GPIO_PORTH_BASE, GPIO_OLEDDC_PIN | GPIO_OLEDEN_PIN, + GPIO_OLEDDC_PIN | GPIO_OLEDEN_PIN); + + /* Configure the SSI0 port for master mode */ + lm3s_ssiOpen(SSI0_BASE, SSI_FRF_MOTO_MODE_2, + SSI_MODE_MASTER, CPU_FREQ / 2, 8); + /* + * Configure the GPIO port pin used as a D/Cn signal for OLED device, + * and the port pin used to enable power to the OLED panel. + */ + lm3s_gpioPinConfig(GPIO_PORTA_BASE, GPIO_OLEDEN_PIN, + GPIO_DIR_MODE_HW, GPIO_STRENGTH_8MA, GPIO_PIN_TYPE_STD_WPU); + + /* Drain the SSI RX FIFO */ + while (lm3s_ssiReadFrameNonBlocking(SSI0_BASE, &dummy)); +} + +/* + * XXX: menu stuff requires lcd_blitBimap() function to be defined. + * Find a better way to do this. + */ +#define rit128x96_blitBitmap lcd_blitBitmap + +#endif /* HW_RIT128x96_H */ diff --git a/examples/develgps/hw/hw_sd.h b/examples/develgps/hw/hw_sd.h new file mode 100644 index 00000000..d15b5506 --- /dev/null +++ b/examples/develgps/hw/hw_sd.h @@ -0,0 +1,53 @@ +/** + * \file + * + * + * \brief SD driver hardware-specific definitions. + * + * \version $Id$ + * + * \author Luca Ottaviano + */ + +#ifndef HW_SD_H +#define HW_SD_H + +#warning FIXME: This is an example implementation, you must implement it + +#define SD_CS_INIT() do { /* implement me */} while(0) +#define SD_CS_ON() do { /* implement me */} while(0) +#define SD_CS_OFF() do { /* implement me */} while(0) + +#define SD_PIN_INIT() do { /* implement me */} while(0) +#define SD_CARD_PRESENT() true /* implement me */ +#define SD_WRITE_PROTECT() false /* implement me */ + +#endif /* HW_SD_H */ diff --git a/examples/develgps/hw/hw_ser.h b/examples/develgps/hw/hw_ser.h new file mode 100644 index 00000000..2489c433 --- /dev/null +++ b/examples/develgps/hw/hw_ser.h @@ -0,0 +1,53 @@ +/** + * \file + * + * + * \brief Serial hardware-specific definitions + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef HW_SER_H +#define HW_SER_H + +#include "cfg/cfg_ser.h" + +#if CONFIG_SER_STROBE + #warning FIXME: this is an example implementation, you must implement it + + #define SER_STROBE_INIT do { /* implement me */ } while (0) + #define SER_STROBE_ON do { /* implement me */ } while (0) + #define SER_STROBE_OFF do { /* implement me */ } while (0) +#endif + +#endif /* HW_SER_H */ diff --git a/examples/develgps/hw/hw_sipo.h b/examples/develgps/hw/hw_sipo.h new file mode 100644 index 00000000..3371c2c0 --- /dev/null +++ b/examples/develgps/hw/hw_sipo.h @@ -0,0 +1,109 @@ +/** + * \file + * + * + * \brief Macro for HW_SIPO_H + * + * + * \version $Id$ + * + * \author Andrea Grandi + * \author Daniele Basile + */ + +#ifndef HW_SIPO_H +#define HW_SIPO_H + +/** + * Map sipo connection on board. + */ +typedef enum SipoMap +{ + SIPO_CNT +} SipoMap; + +/** + * Define generic macro to set pins logic level + */ +#define SIPO_SET_LEVEL_LOW(dev) do { /* Implement me! */ } while (0) +#define SIPO_SET_LEVEL_HIGH(dev) do { /* Implement me! */ } while (0) + + +/** + * Generate one low pulse on select line. + */ +#define PULSE_LOW(dev) do { /* Implement me! */ } while (0) + +/** + * Generate one hight pulse on select line. + */ +#define PULSE_HIGH(dev) do { /* Implement me! */ } while (0) + + +/** + * Define the procedure to drive serial input in sipo device (SI). + */ +#define SIPO_SI_HIGH() do { /* Implement me! */ } while (0) +#define SIPO_SI_LOW() do { /* Implement me! */ } while (0) + +/** + * Drive clock to shift SI data into latch. + */ +#define SIPO_SI_CLOCK(clk_pol) \ + do { \ + (void)clk_pol; \ + /* Implement me! */ \ + } while (0) + +/** + * Do everything needed in order to load dato into sipo. + */ +#define SIPO_LOAD(device, load_pol) do { /* Implement me! */ } while (0) + +/** + * Enable the shift register output. + */ +#define SIPO_ENABLE() do { /* Implement me! */ } while (0) + +/** + * Set polarity for Load, Clk, SI signals. + */ +#define SIPO_SET_LD_LEVEL(device, load_pol) do { /* Implement me! */ } while (0) +#define SIPO_SET_CLK_LEVEL(clock_pol) do { /* Implement me! */ } while (0) +#define SIPO_SET_SI_LEVEL() do { /* Implement me! */ } while (0) + +/** + * Do anything that needed to init sipo pins. + */ +#define SIPO_INIT_PIN() do { /* Implement me! */ } while (0) + +#endif /* HW_SIPO_H */ diff --git a/examples/develgps/hw/hw_spi.h b/examples/develgps/hw/hw_spi.h new file mode 100644 index 00000000..04e4893a --- /dev/null +++ b/examples/develgps/hw/hw_spi.h @@ -0,0 +1,115 @@ +/** + * \file + * + * + * \brief Hardware macro definition. + * + * + * \version $Id$ + * \author Daniele Basile + */ + +#ifndef HW_SPI_H +#define HW_SPI_H + +#warning TODO:This is an example implentation, you must implement it! + +#include + +/** + * SPI pin definition. + * + * \note CS is assert when level + * is low. + * + * \{ + */ +#define CS /* pin */ ///Connect to CS pin of Flash memory. +#define SCK /* pin */ ///Connect to SCK pin of Flash memory. +#define MOSI /* pin */ ///Connect to SI pin of Flash memory. +#define MISO /* pin */ ///Connect to SO pin of Flash memory. +#define SPI_PORT /* pin */ ///Micro pin PORT register. +#define SPI_PIN /* pin */ ///Micro pin PIN register. +#define SPI_DDR /* pin */ ///Micro pin DDR register. +/*\}*/ + +/** + * Pin logic level. + * + * \{ + */ +#define MOSI_LOW() do { /* Implement me! */ } while(0) +#define MOSI_HIGH() do { /* Implement me! */ } while(0) +#define MISO_HIGH() do { /* Implement me! */ } while(0) +#define SCK_LOW() do { /* Implement me! */ } while(0) +#define SCK_HIGH() do { /* Implement me! */ } while(0) +#define CS_LOW() do { /* Implement me! */ } while(0) +#define CS_HIGH() do { /* Implement me! */ } while(0) +/*\}*/ + +/** + * SPI pin commands. + * + * \{ + */ +#define CS_ENABLE() CS_LOW() +#define CS_DISABLE() CS_HIGH() +#define SS_ACTIVE() CS_LOW() +#define SS_INACTIVE() CS_HIGH() +#define SCK_INACTIVE() SCK_LOW() +#define SCK_ACTIVE() SCK_HIGH() +#define CS_OUT() do { /* Implement me! */ } while(0) +#define MOSI_IN() do { /* Implement me! */ } while(0) +#define MOSI_OUT() do { /* Implement me! */ } while(0) +#define IS_MISO_HIGH() (false /* Implement me! */ ) +#define MISO_IN() do { /* Implement me! */ } while(0) +#define MISO_OUT() do { /* Implement me! */ } while(0) +#define SCK_OUT() do { /* Implement me! */ } while(0) + +#define SCK_PULSE()\ + do {\ + SCK_HIGH();\ + SCK_LOW();\ + } while (0) +/*\}*/ + + +#define SPI_HW_INIT() \ + CS_DISABLE();\ + MOSI_LOW();\ + SCK_LOW();\ + MISO_IN();\ + MOSI_OUT();\ + SCK_OUT();\ + CS_OUT(); + +#endif /* HW_SPI_H */ + diff --git a/examples/develgps/hw/hw_stepper.h b/examples/develgps/hw/hw_stepper.h new file mode 100644 index 00000000..13141124 --- /dev/null +++ b/examples/develgps/hw/hw_stepper.h @@ -0,0 +1,309 @@ +/** + * \file + * + * + * \brief Stepper hardware-specific definitions + * + * \version $Id$ + * + * \author Daniele Basile + */ + + +#ifndef HW_STEPPER_H +#define HW_STEPPER_H + +#include + +#include + +#include + +#warning TODO:This is an example implentation, you must implement it! + +#define STEPPER_STROBE_INIT \ +do { \ + /* put init code for strobe */ \ +} while (0) + + +#define STEPPER_STROBE_ON do { /* Implement me! */ } while(0) +#define STEPPER_STROBE_OFF do { /* Implement me! */ } while(0) + +/** + * CPU clock frequency is divided by 2^STEPPER_PRESCALER_LOG2 to + * obtain stepper clock. + */ +#define STEPPER_PRESCALER_LOG2 1 + +/** + * Stepper timer clock frequency. + */ +#define STEPPER_CLOCK ((CPU_FREQ) >> STEPPER_PRESCALER_LOG2) + +/** + * us delay to reset a stepper motor. + * This is the time neccessary to reset + * the stepper controll chip. (see datasheet for more detail). + */ +#define STEPPER_RESET_DELAY 1 + +/* + * Pins define for each stepper + */ +#define STEPPER_1_CW_CCW_PIN 0 +#define STEPPER_1_HALF_FULL_PIN 0 +#define STEPPER_1_CONTROL_PIN 0 +#define STEPPER_1_ENABLE_PIN 0 +#define STEPPER_1_RESET_PIN 0 + +/* put here other stepper motor */ + +#define STEPPER_1_SET do { /* Implement me! */ } while(0) +/* add here the set for other stepper motor */ + +#define STEPPER_1_CLEAR do { /* Implement me! */ } while(0) +/* add here the clear for other stepper motor */ + +/* + * Generic macro definition + */ + +/* + * Stepper init macro + */ +#define STEPPER_PIN_INIT_MACRO(port, index) do { \ + /* Add here init pin code */ \ + } while (0) + +/* + * Stepper commands macros + */ +#define STEPPER_SET_CW(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_CCW(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_HALF(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_FULL(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_CONTROL_LOW(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_CONTROL_HIGHT(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_ENABLE(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_DISABLE(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_RESET_ENABLE(index) do { /* Implement me! */ } while (0) +#define STEPPER_SET_RESET_DISABLE(index) do { /* Implement me! */ } while (0) + + +/* + * Reset stepper macro + */ + +#define STEPPER_RESET_MACRO(index) do { \ + STEPPER_SET_RESET_ENABLE(index); \ + timer_udelay(STEPPER_RESET_DELAY); \ + STEPPER_SET_RESET_DISABLE(index); \ + } while (0) + +/* + * Set half or full step macro + */ +#define STEPPER_SET_STEP_MODE_MACRO(index, flag) do { \ + if (flag) \ + STEPPER_SET_HALF(index); \ + else \ + STEPPER_SET_FULL(index); \ + } while (0) + +/* + * Set control status macro + */ +#warning TODO: This macro is not implemented (see below) + +#define STEPPER_SET_CONTROL_BIT_MACRO(index, flag) do { \ + /* if (flag) */ \ + /* WARNING This macros not implemented */ \ + /* else */ \ + /* WARNING This macros not implemented */ \ + } while (0) + +/* + * Set current power macro + */ +#warning TODO: This macro is not implemented (see below) + +#define STEPPER_SET_POWER_CURRENT_MACRO(index, flag) do { \ + /* if (flag) */ \ + /* WARNING This macrois not implemented */ \ + /* else */ \ + /* WARNING This macrois not implemented */ \ + } while (0) + +/* + * Set rotation of stepper motor + * - dir = 1: positive rotation + * - dir = 0: no motor moviment + * - dir = -1: negative rotation + * + */ +#define STEPPER_SET_DIRECTION_MACRO(index, dir) do { \ + switch (dir) \ + { \ + case 1: \ + STEPPER_SET_CW(index); \ + break; \ + case -1: \ + STEPPER_SET_CCW(index); \ + break; \ + case 0: \ + break; \ + } \ + } while (0) + + +/* + * Define macros for manage low level of stepper. + */ + +#define STEPPER_INIT() do { \ + STEPPER_PIN_INIT_MACRO(A, 1); \ + /* Add here code for other stepper motor */ \ + } while (0) + + +/* + * Enable select stepper motor + */ +#define STEPPER_ENABLE(index) do { \ + switch (index) \ + { \ + case 1: \ + STEPPER_SET_ENABLE(1); \ + break; \ + /* Add here code for other stepper motor */ \ + } \ + } while (0) + +/* + * Enable all stepper connect to micro + */ +#define STEPPER_ENABLE_ALL() do { \ + STEPPER_SET_ENABLE(1); \ + /* Add here code for other stepper motor */ \ + } while (0) + +/* + * Disable select stepper motor + */ +#define STEPPER_DISABLE(index) do { \ + switch (index) \ + { \ + case 1: \ + STEPPER_SET_DISABLE(1); \ + break; \ + /* Add here code for other stepper motor */ \ + } \ + } while (0) + +/* + * Disable all stepper connect to micro + */ +#define STEPPER_DISABLE_ALL() do { \ + STEPPER_SET_DISABLE(1); \ + /* Add here code for other stepper motor */ \ + } while (0) + +/* + * Reset selected stepper motor + */ +#define STEPPER_RESET(index) do { \ + switch (index) \ + { \ + case 1: \ + STEPPER_RESET_MACRO(1); \ + break; \ + /* Add here code for other stepper motor */ \ + } \ + } while (0) + +/* + * Reset all stepper motor + */ +#define STEPPER_RESET_ALL() do { \ + STEPPER_RESET_MACRO(1) \ + /* Add here code for other stepper motor */ \ + } while (0) + +// Set half/full step macros +#define STEPPER_SET_HALF_STEP(index, flag) do { \ + switch (index) \ + { \ + case 1: \ + STEPPER_SET_STEP_MODE_MACRO(1, flag); \ + break; \ + /* Add here code for other stepper motor */ \ + } \ + } while (0) + + +// Control status +#define STEPPER_SET_CONTROL_BIT(index, flag) do { \ + switch (index) \ + { \ + case 1: \ + STEPPER_SET_CONTROL_BIT_MACRO(1, flag); \ + break; \ + /* Add here code for other stepper motor */ \ + } \ + } while (0) + + +// Set stepper power current +#define STEPPER_SET_POWER_CURRENT(index, flag) do { \ + switch (index) \ + { \ + case 1: \ + STEPPER_SET_POWER_CURRENT_MACRO(1, flag); \ + break; \ + /* Add here code for other stepper motor */ \ + } \ + } while (0) + +// Set rotation dirction of stepper motor +#define STEPPER_SET_DIRECTION(index, dir) do { \ + switch (index) \ + { \ + case 1: \ + STEPPER_SET_DIRECTION_MACRO(1, dir); \ + break; \ + /* Add here code for other stepper motor */ \ + } \ + } while (0) + +#endif /* HW_STEPPER_H */ + + diff --git a/examples/develgps/hw/hw_tas5706a.h b/examples/develgps/hw/hw_tas5706a.h new file mode 100644 index 00000000..d1e1a2e6 --- /dev/null +++ b/examples/develgps/hw/hw_tas5706a.h @@ -0,0 +1,65 @@ +/** + * \file + * + * + * \brief HW pin handling. + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef HW_TAS5706A_H +#define HW_TAS5706A_H + +#include + +#warning FIXME: This is an example implementation, you must implement it + +#define TAS5706A_SETPOWERDOWN(val) do { (void) val; /* implement me */ } while (0) +#define TAS5706A_SETRESET(val) do { (void) val; /* implement me */ } while (0) +#define TAS5706A_SETMUTE(val) do { (void) val; /* implement me */ } while (0) + +#define TAS5706A_PIN_INIT() \ + do { \ + TAS5706A_SETPOWERDOWN(true); \ + TAS5706A_SETRESET(true); \ + TAS5706A_SETMUTE(true); \ + /* complete me */ \ + } while (0) + +#define TAS5706A_MCLK_INIT() \ + do { \ + /* implement me */ \ + } while(0) + + +#endif /* HW_TAS5706A_H */ diff --git a/examples/develgps/hw/hw_thermo.h b/examples/develgps/hw/hw_thermo.h new file mode 100644 index 00000000..bbfc9dde --- /dev/null +++ b/examples/develgps/hw/hw_thermo.h @@ -0,0 +1,182 @@ +/** + * \file + * + * + * \brief thermo hardware-specific control functions. + * + * \version $Id$ + * \author Francesco Sacchi + * + */ + +#ifndef HW_THERMO_H +#define HW_THERMO_H + +#include "thermo_map.h" +#include "ntc_map.h" + +#include +#include + +#include +#include + +#warning TODO:This is an example implentation, you must implement it! + +/*! + * This function should return the temperature set tolerance. + */ +INLINE deg_t thermo_hw_tolerance(ThermoDev dev) +{ + ASSERT(dev < THERMO_CNT); + + switch (dev) + { + case THERMO_TEST: + /* Put here convertion function to temperature size */ + break; + + /* Put here your thermo device */ + + default: + ASSERT(0); + } + + return 0; +} + + +/*! + * This function should return the timeout for reaching the + * target temperature. + */ +INLINE ticks_t thermo_hw_timeout(ThermoDev dev) +{ + ASSERT(dev < THERMO_CNT); + + switch (dev) + { + case THERMO_TEST: + /* return ms_to_ticks(60000); */ + break; + + /* Put here a time out for select thermo device */ + + default: + ASSERT(0); + } + + return 0; +} + + + +/*! + * Read the temperature of the hw device \a dev. + */ +INLINE deg_t thermo_hw_read(ThermoDev dev) +{ + return ntc_read(dev); +} + + +/*! + * Turns off a specific device. + * This function is usefull to handle errors. + */ +INLINE void thermo_hw_off(ThermoDev dev) +{ + ASSERT(dev < THERMO_CNT); + + switch (dev) + { + case THERMO_TEST: + phase_setPower(TRIAC_TEST, 0); + break; + + /* Put here a thermo device to turn off */ + + default: + ASSERT(0); + } + +} + + +/*! + * Based on the current temperature \a cur_temp and the target temperature \a target, this function turns on and off specific + * triac channel and handles the freezer alarm. + * It may use also PID control for thermo-regolations. + */ +INLINE void thermo_hw_set(ThermoDev dev, deg_t target, deg_t cur_temp) +{ + ASSERT(dev < THERMO_CNT); + + deg_t dist = target - cur_temp; + //kprintf("dev[%d], dist[%d]\n", dev, dist); + + switch(dev) + { + case THERMO_TEST: + if (dist > 0) + { + /* phase_setPower(TRIAC_TEST, dist * PID_TEST_K); */ + } + else + { + /* phase_setPower(TRIAC_TEST, 0); */ + } + break; + + /* Put here an other thermo device */ + + default: + ASSERT(0); + } +} + + +#define THERMO_HW_INIT _thermo_hw_init() + +/*! + * Init hw associated with thermo-control. + */ +INLINE void _thermo_hw_init(void) +{ + ASSERT(phase_initialized); + ASSERT(ntc_initialized); + + phase_setPower(TRIAC_TEST, 0); + + /* Add here the other thermo device */ +} + +#endif /* HW_THERMO_H */ diff --git a/examples/develgps/hw/hw_tlv5618.h b/examples/develgps/hw/hw_tlv5618.h new file mode 100644 index 00000000..4a2b4202 --- /dev/null +++ b/examples/develgps/hw/hw_tlv5618.h @@ -0,0 +1,69 @@ +/** + * \file + * + * + * \brief TLV5816 DAC hardware-specific definitions + * + * + * \author Francesco Sacchi + */ + +#ifndef HW_TLV5816_H +#define HW_TLV5816_H + +#warning TODO:This is an example implementation, you must implement it! + +#define TLV5618_CSINIT(pin) \ +do \ +{ \ + (void)pin; \ + /* Implement me! */ \ + TLV5618_CSHIGH(pin); \ +} while(0) + +#define TLV5618_CSLOW(pin) \ +do \ +{ \ + (void)pin; \ + /* Implement me! */ \ +} while(0) + + +#define TLV5618_CSHIGH(pin) \ +do \ +{ \ + (void)pin; \ + /* Implement me! */ \ +} while(0) + + +#endif /* HW_TLV5816_H */ + diff --git a/examples/develgps/hw/hw_tmp123.h b/examples/develgps/hw/hw_tmp123.h new file mode 100644 index 00000000..adb18588 --- /dev/null +++ b/examples/develgps/hw/hw_tmp123.h @@ -0,0 +1,52 @@ +/** + * \file + * + * + * \brief Hardware macro definition. + * + * \author Daniele Basile + */ + +#ifndef HW_TMP123_H +#define HW_TMP123_H + +#warning TODO:This is an example implentation, you must implement it! + +#define TMP123_HW_CS_EN() /* Implement me! */ +#define TMP123_HW_CS_DIS() /* Implement me! */ + +#define TMP123_HW_INIT() \ + do { \ + /* Pin init */\ + } while (0) + +#endif /* HW_TMP123_H */ + diff --git a/examples/develgps/hw/kbd_map.h b/examples/develgps/hw/kbd_map.h new file mode 100644 index 00000000..20b95ea0 --- /dev/null +++ b/examples/develgps/hw/kbd_map.h @@ -0,0 +1,70 @@ +/** + * \file + * + * + * \brief Keyboard map definitions. + * + * \version $Id$ + * + * \author Francesco Sacchi + * \author Stefano Fedrigo + */ + +#ifndef HW_KBD_MAP_H +#define HW_KBD_MAP_H + +#include + +/** + * Type for keyboard mask. + */ +typedef uint16_t keymask_t; + +/** + * \name Keycodes. + */ +/*@{*/ +#define K_UP BV(3) +#define K_DOWN BV(4) +#define K_LEFT BV(5) +#define K_RIGHT BV(6) +#define K_OK BV(7) +#define K_CANCEL BV(8) + +#define K_REPEAT BV(13) /**< This is a repeated keyevent. */ +#define K_TIMEOUT BV(14) /**< Fake key event for timeouts. */ +#define K_LONG BV(15) +/*@}*/ + +#define K_LNG_MASK 0 + +#endif /* HW_KBD_MAP_H */ diff --git a/examples/develgps/hw/mcp41_map.h b/examples/develgps/hw/mcp41_map.h new file mode 100644 index 00000000..6646391c --- /dev/null +++ b/examples/develgps/hw/mcp41_map.h @@ -0,0 +1,59 @@ +/** + * \file + * + * + * \brief MCP41 digital potentiometer map definitions. + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef MCP41_MAP_H +#define MCP41_MAP_H + +#warning TODO:This is an example implentation, you must implement it! + +/** \name Enum for mcp41 pot evices. + * \{ + * + */ +typedef enum Mcp41Dev +{ + MCP41_LED, + + /* put here other mcp41 device */ + + MCP41_CNT, +} Mcp41Dev; +/* \} */ + +#endif /* MCP41_MAP_H */ diff --git a/examples/develgps/hw/ntc_map.h b/examples/develgps/hw/ntc_map.h new file mode 100644 index 00000000..505f1c31 --- /dev/null +++ b/examples/develgps/hw/ntc_map.h @@ -0,0 +1,61 @@ +/** + * \file + * + * + * \brief NTC map definitions. + * + * \version $Id$ + * + * \author Giovanni Bajo + * \author Francesco Sacchi + */ + +#ifndef NTC_MAP_H +#define NTC_MAP_H + +#include + +#warning TODO:This is an example implentation, you must implement it! + +/*! \name Enum for ntc devices. + * \{ + */ +typedef enum NtcDev +{ + NTC_TEST, + + /* Put here your thermo device */ + + NTC_CNT +} NtcDev; +/* \} */ + +#endif /* NTC_MAP_H */ diff --git a/examples/develgps/hw/phase_map.h b/examples/develgps/hw/phase_map.h new file mode 100644 index 00000000..7436e5e8 --- /dev/null +++ b/examples/develgps/hw/phase_map.h @@ -0,0 +1,58 @@ +/** + * \file + * + * + * \brief Triac map definitions. + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef PHASE_MAP_H +#define PHASE_MAP_H + +#warning TODO:This is an example implentation, you must implement it! + +/*! \name Enum for triac devices. + * \{ + */ +typedef enum TriacDev +{ + TRIAC_TEST, + + /* Put here other triac device */ + + TRIAC_CNT +} TriacDev; +/* \} */ + +#endif /* PHASE_MAP_H */ diff --git a/examples/develgps/hw/pwm_map.h b/examples/develgps/hw/pwm_map.h new file mode 100644 index 00000000..723da2f1 --- /dev/null +++ b/examples/develgps/hw/pwm_map.h @@ -0,0 +1,61 @@ +/** + * \file + * + * + * + * \brief PWM map device. + * + * \version $Id$ + * + * \author Daniele Basile + */ + +#ifndef HW_PWM_MAP_H +#define HW_PWM_MAP_H + +#warning TODO:This is an example implentation, you must implement it! + +typedef enum +{ + PWM_CH0 = 0, + PWM_CH1, + PWM_CH2, + PWM_CH3, + +/* + * add other PWM channel or + * change above. + */ + + PWM_CNT +} PwmDev; + +#endif /* HW_PWM_MAP_H */ diff --git a/examples/develgps/hw/thermo_map.h b/examples/develgps/hw/thermo_map.h new file mode 100644 index 00000000..4376076a --- /dev/null +++ b/examples/develgps/hw/thermo_map.h @@ -0,0 +1,70 @@ +/** + * \file + * + * + * \brief Thermo regulation control map definitions. + * + * \version $Id$ + * + * \author Francesco Sacchi + */ + +#ifndef THERMO_MAP_H +#define THERMO_MAP_H + +#include +#include + +#warning TODO:This is an example implentation, you must implement it! + +typedef uint8_t thermostatus_t; + +#define THERMO_OFF 0 +#define THERMO_HEATING BV(0) +#define THERMO_FREEZING BV(1) +#define THERMO_TGT_REACH BV(2) +#define THERMOERRF_NTCSHORT BV(3) +#define THERMOERRF_NTCOPEN BV(4) +#define THERMOERRF_TIMEOUT BV(5) +#define THERMO_ACTIVE BV(6) + +#define THERMO_ERRMASK (THERMOERRF_NTCSHORT | THERMOERRF_NTCOPEN | THERMOERRF_TIMEOUT) + +typedef enum ThermoDev +{ + THERMO_TEST, + + /* Put here your thermo device */ + + THERMO_CNT, +} ThermoDev; + +#endif /* THERMO_MAP_H */ diff --git a/examples/develgps/logo.c b/examples/develgps/logo.c new file mode 100644 index 00000000..42fbd38b --- /dev/null +++ b/examples/develgps/logo.c @@ -0,0 +1,584 @@ +/** + * \file + * + * + * \brief BeRTOS logo: PC bitmap, Windows 3.x format, 120 x 70 x 4 + * + * \author Andrea Righi + */ + +#define BITMAP_HEADER_SIZE 0x76 +#define BITMAP_WIDTH_OFFSET 0x12 +#define BITMAP_HEIGHT_OFFSET 0x16 + +/* BeRTOS logo */ +static const unsigned char logo[] = { + 0x42, 0x4d, 0xde, 0x10, 0x00, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x76, 0x00, 0x00, 0x00, 0x28, 0x00, + 0x00, 0x00, 0x78, 0x00, 0x00, 0x00, 0x46, 0x00, + 0x00, 0x00, 0x01, 0x00, 0x04, 0x00, 0x00, 0x00, + 0x00, 0x00, 0x68, 0x10, 0x00, 0x00, 0x13, 0x0b, + 0x00, 0x00, 0x13, 0x0b, 0x00, 0x00, 0x10, 0x00, + 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x26, 0x26, + 0x26, 0x00, 0x32, 0x32, 0x32, 0x00, 0x3e, 0x3e, + 0x3e, 0x00, 0x4e, 0x4e, 0x4e, 0x00, 0x5c, 0x5c, + 0x5c, 0x00, 0x68, 0x68, 0x68, 0x00, 0x7d, 0x7d, + 0x7d, 0x00, 0x82, 0x82, 0x82, 0x00, 0x93, 0x93, + 0x93, 0x00, 0xa3, 0xa3, 0xa3, 0x00, 0xb3, 0xb3, + 0xb3, 0x00, 0xbf, 0xbf, 0xbf, 0x00, 0xce, 0xce, + 0xce, 0x00, 0xdd, 0xdd, 0xdd, 0x00, 0xeb, 0xeb, + 0xeb, 0x00, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xeb, 0x98, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x89, + 0xbe, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x98, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x82, 0x41, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x89, 0xcf, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xed, 0xcb, 0x98, 0x98, 0x88, 0x26, 0x77, 0x18, + 0x88, 0x88, 0x99, 0xab, 0xde, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0x16, 0x68, 0x81, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0x45, 0x45, 0x84, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xf5, 0x15, 0x67, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xf6, 0x45, 0x97, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x15, 0x16, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x61, 0x31, 0x1a, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xf1, 0x1c, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x17, 0x64, 0xcf, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0x91, 0x15, 0x55, + 0x52, 0x10, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x17, 0x60, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x67, 0x77, 0x1e, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x01, 0x25, 0x55, 0x55, 0x55, 0x54, 0x10, 0x9f, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf5, + 0x78, 0x62, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x17, 0x77, 0x71, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf6, 0x11, 0x55, 0x66, 0x55, 0x55, + 0x55, 0x55, 0x55, 0x21, 0x3f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xe1, 0x69, 0x71, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xf1, 0x66, 0x74, 0xcf, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xe5, 0x13, 0x55, + 0x66, 0x66, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, + 0x31, 0x08, 0xff, 0xff, 0xff, 0xff, 0xff, 0x26, + 0x87, 0x57, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xfa, 0x37, 0x77, 0x1f, 0xff, 0xff, 0xff, 0xff, + 0x71, 0x14, 0x56, 0x66, 0x66, 0x66, 0x66, 0x55, + 0x55, 0x55, 0x55, 0x55, 0x55, 0x52, 0x12, 0xff, + 0xff, 0xff, 0xff, 0x07, 0x97, 0x1f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0x17, 0x67, 0x0f, + 0xff, 0xff, 0xfe, 0x40, 0x35, 0x56, 0x77, 0x77, + 0x77, 0x66, 0x66, 0x66, 0x66, 0x66, 0x55, 0x55, + 0x55, 0x55, 0x53, 0x10, 0xcf, 0xff, 0xff, 0x26, + 0x96, 0x2f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0x17, 0x67, 0x1f, 0xff, 0xe1, 0x11, 0x22, + 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, + 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, + 0x21, 0x11, 0xff, 0x36, 0x96, 0x8f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0x17, 0x77, 0x14, + 0x55, 0x61, 0x77, 0x77, 0x77, 0x77, 0x77, 0x77, + 0x77, 0x77, 0x77, 0x77, 0x77, 0x77, 0x77, 0x77, + 0x77, 0x77, 0x77, 0x77, 0x77, 0x73, 0xff, 0x27, + 0x86, 0x2f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xfc, 0x18, 0x77, 0x11, 0x11, 0x11, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, 0x99, + 0x99, 0x94, 0xfe, 0x07, 0x67, 0x1e, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xd1, 0x68, 0x75, 0x31, + 0x11, 0x11, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0xa5, 0x11, 0x16, + 0x78, 0x71, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe4, + 0x27, 0x96, 0x60, 0xfa, 0x11, 0x11, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x83, 0x11, 0xe1, 0x76, 0x77, 0x01, 0x34, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xe1, 0x36, 0x79, 0x67, 0x29, 0xff, + 0x11, 0x11, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x82, 0x1a, 0xf4, + 0x77, 0x67, 0x77, 0x77, 0x2f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x46, 0x89, + 0x86, 0x67, 0x5f, 0xff, 0xf1, 0x11, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x63, 0x68, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x21, 0x11, + 0x78, 0x80, 0x4f, 0xff, 0x17, 0x77, 0x67, 0x77, + 0x1f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x16, 0x66, 0x61, 0x1e, 0xff, 0xff, + 0xff, 0xf1, 0x88, 0x88, 0x88, 0x86, 0xbf, 0xff, + 0xff, 0xb1, 0x88, 0x88, 0x88, 0x88, 0xaa, 0xaa, + 0x88, 0x1f, 0xff, 0xdc, 0xfe, 0x11, 0xff, 0xff, + 0xfd, 0x11, 0x66, 0x63, 0x1f, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, 0x32, + 0x8e, 0xff, 0xff, 0xff, 0xff, 0xf1, 0x88, 0x88, + 0x88, 0x59, 0xfb, 0x67, 0x77, 0x6d, 0x58, 0x88, + 0x88, 0x8a, 0xaa, 0xaa, 0x83, 0xff, 0x67, 0x77, + 0x76, 0xf1, 0xff, 0xff, 0xff, 0xff, 0x86, 0x8d, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xf0, 0x88, 0x88, 0x88, 0x6f, 0x77, 0x76, + 0x88, 0x76, 0x78, 0x88, 0x88, 0x9a, 0xaa, 0xaa, + 0x1f, 0xf6, 0x66, 0x89, 0x97, 0x71, 0x77, 0x77, + 0x77, 0x6f, 0xf6, 0x77, 0x77, 0x77, 0x7f, 0xf8, + 0x88, 0xff, 0xff, 0x88, 0x8f, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xfd, 0x88, 0x88, 0x88, 0x88, 0x8f, + 0xfc, 0x88, 0x88, 0x88, 0x88, 0xaf, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xfa, 0x88, 0x88, + 0x81, 0xff, 0x76, 0x89, 0x86, 0x89, 0x61, 0x88, + 0x88, 0xaa, 0xaa, 0xaa, 0xff, 0x97, 0x69, 0x95, + 0x37, 0x73, 0x77, 0x77, 0x77, 0x7e, 0xf7, 0x77, + 0x77, 0x77, 0x6f, 0xf8, 0x88, 0xff, 0xfc, 0x88, + 0x9f, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0x88, 0x88, 0x88, 0x8b, 0xf8, 0x88, 0x88, 0x88, + 0x88, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x88, 0x88, 0x89, 0xf9, 0x78, 0x92, + 0x11, 0x11, 0x86, 0x88, 0x88, 0xaa, 0xaa, 0xaa, + 0xff, 0x67, 0x98, 0x11, 0x11, 0x16, 0x66, 0x66, + 0x77, 0x7e, 0xf7, 0x76, 0xee, 0x97, 0x6f, 0xf8, + 0x88, 0xff, 0xf8, 0x88, 0xff, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0x88, 0x88, 0x88, 0x8b, + 0xf8, 0x88, 0x88, 0x88, 0x88, 0x8f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x78, 0x88, + 0x7f, 0xf6, 0x69, 0x21, 0x11, 0x11, 0x36, 0x68, + 0x88, 0xaa, 0xaa, 0xa8, 0xfd, 0x66, 0x91, 0x11, + 0x11, 0x17, 0xff, 0xff, 0x77, 0x7e, 0xf7, 0x76, + 0xff, 0x97, 0x6f, 0xf8, 0x88, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xf8, 0x88, 0xff, 0xff, + 0x88, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x28, 0x88, 0x5f, 0xf6, 0x79, 0x11, + 0x11, 0x11, 0x18, 0x48, 0x88, 0xaa, 0xaa, 0xa6, + 0xfb, 0x77, 0x21, 0x11, 0x11, 0x07, 0xff, 0xff, + 0x77, 0x7e, 0xf7, 0x76, 0xff, 0x96, 0x6f, 0xf8, + 0x88, 0xff, 0xd8, 0x88, 0xff, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8b, + 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x08, 0x88, + 0x7f, 0xf6, 0x77, 0x11, 0xf9, 0xa3, 0x16, 0x68, + 0x88, 0xaa, 0xaa, 0xaa, 0xfd, 0x67, 0x11, 0x1f, + 0xf6, 0x57, 0xff, 0xff, 0x77, 0x7e, 0xf7, 0x76, + 0xff, 0xff, 0xff, 0xf8, 0x88, 0xff, 0x88, 0x8c, + 0xff, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xf8, 0x88, 0xff, 0xff, + 0x88, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xa6, 0x88, 0x89, 0xf8, 0x69, 0x11, + 0xcf, 0xff, 0x16, 0x88, 0x88, 0xaa, 0xaa, 0xaa, + 0xff, 0x66, 0x21, 0x1d, 0xf1, 0x77, 0xff, 0xff, + 0x77, 0x7e, 0xf7, 0x76, 0x66, 0x66, 0x7f, 0xf8, + 0x88, 0xff, 0x88, 0x8f, 0xff, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8b, + 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf0, 0x88, + 0x81, 0xff, 0x78, 0x11, 0xff, 0xff, 0x01, 0x88, + 0x88, 0xaa, 0xaa, 0xaa, 0x2f, 0x97, 0x91, 0x1f, + 0xe1, 0x67, 0xff, 0xff, 0x77, 0x7e, 0xf7, 0x77, + 0x66, 0x67, 0x6f, 0xf8, 0x88, 0xff, 0x88, 0x8f, + 0xff, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xff, 0xff, 0xff, 0xf9, + 0x88, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf2, 0x88, 0x88, 0x6f, 0x66, 0x91, + 0xef, 0xff, 0x38, 0x88, 0x88, 0x9a, 0xaa, 0xaa, + 0x6c, 0xf6, 0x67, 0x1e, 0x36, 0x77, 0xff, 0xff, + 0x77, 0x7e, 0xf7, 0x76, 0xff, 0x97, 0x6f, 0xf8, + 0x88, 0xf9, 0x88, 0xef, 0xff, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8b, + 0xff, 0xff, 0xff, 0x88, 0x88, 0xcf, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x28, + 0x88, 0x5a, 0xf7, 0x68, 0x1f, 0xff, 0x58, 0x88, + 0x88, 0x8a, 0xaa, 0xaa, 0xa3, 0xcf, 0x66, 0x83, + 0x17, 0x77, 0xff, 0xf8, 0x77, 0x6f, 0xf7, 0x76, + 0xff, 0x97, 0x6f, 0xf8, 0x88, 0xf8, 0x88, 0xff, + 0xff, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xff, 0xff, 0xf8, 0x88, + 0x8b, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0x08, 0x88, 0x86, 0xaf, 0xfb, + 0x8c, 0x91, 0x88, 0x88, 0x88, 0x8a, 0xaa, 0xaa, + 0xaa, 0x82, 0xff, 0xdd, 0xc7, 0x77, 0x66, 0x67, + 0x76, 0xff, 0xf7, 0x76, 0xff, 0x97, 0x6f, 0xf8, + 0x88, 0xf8, 0x88, 0x88, 0xef, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8b, + 0xff, 0xff, 0x88, 0x88, 0xdf, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xe1, + 0x88, 0x88, 0x71, 0x15, 0x11, 0x78, 0x88, 0x88, + 0x88, 0x8a, 0xaa, 0xaa, 0xaa, 0xaa, 0x52, 0x11, + 0xf7, 0x77, 0x77, 0x77, 0x6e, 0xff, 0xf7, 0x76, + 0xdd, 0x97, 0x6f, 0xf8, 0x88, 0xf8, 0x88, 0x88, + 0x9f, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xff, 0xfd, 0x88, 0x88, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xfb, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0x8a, 0xaa, 0xaa, + 0xaa, 0xaa, 0xaa, 0x38, 0xf7, 0x77, 0xff, 0xf8, + 0x77, 0x6f, 0xf7, 0x77, 0x77, 0x77, 0x6f, 0xf8, + 0x88, 0xff, 0xff, 0x88, 0x9f, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8b, + 0xff, 0x88, 0x88, 0xef, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0x18, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x88, 0x9a, 0xaa, 0xaa, 0xaa, 0xaa, 0xa8, 0x0f, + 0xf7, 0x77, 0xff, 0xff, 0x77, 0x6e, 0xfe, 0x88, + 0x88, 0x88, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, + 0x9f, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xf8, 0x88, 0x8f, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x54, 0x88, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x88, 0xaa, 0xaa, 0xaa, + 0xaa, 0xaa, 0x91, 0xff, 0xf7, 0x77, 0xff, 0xff, + 0x77, 0x6f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, + 0x88, 0xff, 0xff, 0x88, 0x9f, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8b, + 0xf8, 0x88, 0xff, 0xff, 0xaa, 0xaf, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xf1, 0x78, 0x88, 0x88, 0x88, 0x88, 0x88, 0x88, + 0x89, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0x1b, 0xff, + 0xf7, 0x77, 0xff, 0xff, 0x77, 0x6f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, + 0x9f, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xf8, 0x88, 0xff, 0xff, + 0x88, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0x08, 0x88, 0x88, + 0x88, 0x88, 0x88, 0x88, 0x9a, 0xaa, 0xaa, 0xaa, + 0xaa, 0xa8, 0x6f, 0xff, 0xf7, 0x77, 0xff, 0xff, + 0x77, 0x6f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, + 0x88, 0xff, 0xff, 0x88, 0x9f, 0xff, 0xf9, 0x88, + 0xef, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8b, + 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xf1, 0x88, 0x88, 0x88, 0x88, 0x88, 0x89, + 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, 0x81, 0xff, 0xff, + 0xf7, 0x77, 0xff, 0xff, 0x77, 0x6f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xf8, 0x88, 0xff, 0xff, 0x88, + 0x9f, 0xff, 0xf9, 0x88, 0xef, 0xff, 0xf8, 0x88, + 0xff, 0xff, 0x88, 0x8b, 0xf8, 0x88, 0xff, 0xff, + 0x88, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x18, 0x88, + 0x88, 0x88, 0x88, 0xaa, 0xaa, 0xaa, 0xaa, 0xaa, + 0x87, 0x1f, 0xff, 0xff, 0xf7, 0x77, 0xff, 0xff, + 0x77, 0x6f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, + 0x88, 0xee, 0xee, 0x88, 0x9f, 0xcc, 0xc9, 0x88, + 0xcc, 0xcc, 0xf8, 0x88, 0xee, 0xee, 0x88, 0x8b, + 0xf8, 0x88, 0xff, 0xff, 0x88, 0x8f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf1, 0x28, 0x88, 0x9a, 0xaa, 0xaa, + 0xaa, 0xaa, 0xa9, 0x88, 0x1c, 0xff, 0xff, 0xff, + 0xf7, 0x77, 0x77, 0x77, 0x77, 0x6f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xf8, 0x88, 0x88, 0x88, 0x88, + 0xaf, 0x88, 0x88, 0x88, 0x88, 0x88, 0xf8, 0x88, + 0x88, 0x88, 0x88, 0x8b, 0xf8, 0x88, 0x88, 0x88, + 0x88, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xa0, + 0x88, 0x88, 0x99, 0xaa, 0x99, 0x98, 0x88, 0x50, + 0xff, 0xff, 0xff, 0xff, 0xf6, 0x66, 0x66, 0x66, + 0x66, 0x6f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf8, + 0x88, 0x88, 0x88, 0x88, 0xff, 0x88, 0x88, 0x88, + 0x88, 0x88, 0xfc, 0x88, 0x88, 0x88, 0x88, 0x8f, + 0xfb, 0x88, 0x88, 0x88, 0x88, 0xaf, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0x11, 0x78, 0x88, 0x88, + 0x88, 0x88, 0x31, 0x4f, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0x60, 0x13, 0x55, 0x42, 0x10, 0xbf, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfd, 0x19, + 0xbf, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xb6, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xf1, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x11, 0x2b, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xa4, 0xec, + 0x5f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf1, 0xdf, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x0a, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xf0, 0x37, 0x15, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x08, 0x11, + 0x23, 0x9f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x48, 0x19, 0x19, 0x1f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x78, 0x1a, + 0x1a, 0x0f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0x18, 0x1a, 0x1a, 0x2f, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x54, 0xa9, + 0xa1, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xfc, 0xaf, 0xf8, 0x11, 0x1f, 0xfa, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xae, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xaf, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfa, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfa, 0xcf, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xfd, 0xaf, 0xff, 0xfd, 0xff, 0xff, + 0xff, 0x8f, 0xff, 0xca, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xf8, 0xff, 0xfa, 0xff, 0xf8, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xcc, 0xff, 0xfa, + 0xff, 0xf9, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0x8f, 0xff, 0xfa, 0xff, 0xff, 0xaf, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xfe, 0x8f, 0xff, 0xfa, + 0xff, 0xff, 0x8f, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xf8, 0xef, 0xff, 0xfa, 0xff, 0xff, 0xe7, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xfa, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xfa, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, +}; -- 2.25.1