Multi Module Board Definition Updates (#133)

This commit is contained in:
Ben Lye 2017-12-20 11:31:20 +00:00 committed by GitHub
parent 835cc3d0a2
commit b3eccf55ba
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
149 changed files with 2540 additions and 4467 deletions

View File

@ -20,7 +20,15 @@ multiatmega328p.build.f_cpu=16000000L
multiatmega328p.build.core=arduino:arduino multiatmega328p.build.core=arduino:arduino
multiatmega328p.build.variant=arduino:eightanaloginputs multiatmega328p.build.variant=arduino:eightanaloginputs
multiatmega328p.build.extra_flags=-Wl,--relax multiatmega328p.build.extra_flags=-Wl,--relax
multiatmega328p.build.board=MULTI_AVR multiatmega328p.build.board=MULTI_AVR=102
multiatmega328p.board.compiler.c.flags=-c -g -Os {compiler.warning_flags} -std=gnu11 -ffunction-sections -fdata-sections -MMD -flto -fno-fat-lto-objects
multiatmega328p.board.compiler.c.elf.flags=-Os -g -flto -fuse-linker-plugin -Wl,--gc-sections
multiatmega328p.board.compiler.S.flags=-c -g -x assembler-with-cpp -flto -MMD
multiatmega328p.board.recipe.output.save_file=multi-avr.hex
multiatmega328p.board.tools.avrdude.config.path={path}/etc/avrdude.conf
multiatmega328p.board.tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" {erase.verbose} -p{build.mcu} -c{protocol} {program.extra_params} -e -Ulock:w:{bootloader.unlock_bits}:m -Uefuse:w:{bootloader.extended_fuses}:m -Uhfuse:w:{bootloader.high_fuses}:m -Ulfuse:w:{bootloader.low_fuses}:m
multiatmega328p.board.tools.avrdude.bootloader.pattern="{cmd.path}" "-C{config.path}" {bootloader.verbose} -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{runtime.platform.path}/bootloaders/{bootloader.file}:i" -Ulock:w:{bootloader.lock_bits}:m
multiatmega328p.bootloader.tool=arduino:avrdude multiatmega328p.bootloader.tool=arduino:avrdude
multiatmega328p.bootloader.low_fuses=0xFF multiatmega328p.bootloader.low_fuses=0xFF
@ -29,17 +37,48 @@ multiatmega328p.bootloader.unlock_bits=0x3F
multiatmega328p.bootloader.lock_bits=0x0F multiatmega328p.bootloader.lock_bits=0x0F
multiatmega328p.menu.bootloader.none=No bootloader multiatmega328p.menu.bootloader.none=No bootloader
multiatmega328p.menu.bootloader.none.build.board=MULTI_NO_BOOT multiatmega328p.menu.bootloader.none.build.board=MULTI_NO_BOOT=102
multiatmega328p.menu.bootloader.none.upload.maximum_size=32768 multiatmega328p.menu.bootloader.none.upload.maximum_size=32768
multiatmega328p.menu.bootloader.none.bootloader.file=Multi4in1/AtmegaMultiEmpty.hex multiatmega328p.menu.bootloader.none.bootloader.file=Multi4in1/AtmegaMultiEmpty.hex
multiatmega328p.menu.bootloader.none.bootloader.high_fuses=0xD7 multiatmega328p.menu.bootloader.none.bootloader.high_fuses=0xD7
multiatmega328p.menu.bootloader.optiboot=Flash from TX multiatmega328p.menu.bootloader.optiboot=Flash from TX
multiatmega328p.menu.bootloader.optiboot.build.board=MULTI_FLASH_FROM_TX multiatmega328p.menu.bootloader.optiboot.build.board=MULTI_FLASH_FROM_TX=102
multiatmega328p.menu.bootloader.optiboot.upload.maximum_size=32256 multiatmega328p.menu.bootloader.optiboot.upload.maximum_size=32256
multiatmega328p.menu.bootloader.optiboot.bootloader.file=Multi4in1/AtmegaMultiBoot.hex multiatmega328p.menu.bootloader.optiboot.bootloader.file=Multi4in1/AtmegaMultiBoot.hex
multiatmega328p.menu.bootloader.optiboot.bootloader.high_fuses=0xD6 multiatmega328p.menu.bootloader.optiboot.bootloader.high_fuses=0xD6
############################################################## ##############################################################
##############################################################
## Multi 4-in-1 (OrangeRX)
## --------------------------------------------------
multixmega32d4.name=Multi 4-in-1 (OrangeRX)
multixmega32d4.build.board=MULTI_ORANGERX=102
multixmega32d4.build.mcu=atxmega32d4
multixmega32d4.build.f_cpu=32000000L
multixmega32d4.build.core=xmega
multixmega32d4.build.variant=xmega32d4
multixmega32d4.upload.tool=arduino:avrdude
multixmega32d4.upload.protocol=avrispmkii
multixmega32d4.upload.maximum_size=32768
multixmega32d4.upload.speed=57600
multixmega32d4.bootloader.tool=arduino:avrdude
multixmega32d4.bootloader.file=Multi4in1/OrangeMultiBoot.hex
multixmega32d4.bootloader.lock_bits=0xFF
multixmega32d4.board.compiler.c.flags=-c -g -Os {compiler.warning_flags} -std=gnu11 -ffunction-sections -fdata-sections -MMD -flto
multixmega32d4.board.compiler.c.elf.flags=-Os -flto -Wl,--gc-sections
multixmega32d4.board.compiler.S.flags=-c -g -x assembler-with-cpp -flto
multixmega32d4.board.recipe.output.save_file=multi-orx.hex
multixmega32d4.board.tools.avrdude.config.path={runtime.platform.path}/avrdude_xmega.conf
multixmega32d4.board.tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" {erase.verbose} -p{build.mcu} -c{protocol} {program.extra_params} -e -Ulock:w:{bootloader.unlock_bits}:m -Ufuse1:w:{bootloader.fuse1}:m -Ufuse2:w:{bootloader.fuse2}:m -Ufuse4:w:{bootloader.fuse4}:m -Ufuse5:w:{bootloader.fuse5}:m
multixmega32d4.board.tools.avrdude.bootloader.pattern="{cmd.path}" "-C{config.path}" {bootloader.verbose} -p{build.mcu} -c{protocol} {program.extra_params} "-Uboot:w:{runtime.platform.path}/bootloaders/{bootloader.file}:i" -Ulock:w:{bootloader.lock_bits}:m
##############################################################

View File

@ -0,0 +1,47 @@
:108000001F92CDB7DEB7CFD01124809178009FEFBB
:1080100090937800837099F088EA91E680936808DD
:108020009093690880E180934C0880914C0884FF0C
:10803000FCCF109240088091680682FD8FD082E0CC
:1080400080936106C12CD12C97D0813479F494D0DF
:10805000898399D08981823811F485E005C08138FF
:1080600011F484E001C083E080D075C0823411F443
:1080700084E103C0853419F485E08CD06CC085356B
:1080800059F47AD0C82E78D0D12CD82A8D2D881FBB
:108090008827881F8BBF5EC0863521F484E07AD0A4
:1080A00080E0E2CF843641F567D066D0F82E64D008
:1080B000C601DCD000E010E25FD0F80181938F01AF
:1080C000FE12FACF60D0D7FC46C0CBD0C601DAD0C2
:1080D000760100E010E2F801619171918F01C70112
:1080E000DBD0F2E0EF0EF11C011581E2180799F7E1
:1080F000C601E0D0B6D02FC08437C1F43DD03CD00B
:10810000F82E3AD040D0F601EC2CEF0C8F010F5F27
:108110001F4F84912AD0E01207C0EFEFCE1ADE0A7B
:10812000FA94CF0CD11C17C0F801F0CF853739F481
:108130002AD08EE11AD085E918D082E495CF813516
:1081400049F421D080E111D08091A10886FFFCCFB5
:1081500005D001C018D080E108D076CFE0E0F0E093
:1081600084918F3F09F0099408959091A10895FF9B
:10817000FCCF8093A00808958091A10887FFFCCFD1
:108180008091A0080895F8DF803211F085E1EDDFDD
:1081900084E1EBCFCF93C82FEFDFC150E9F7CF9148
:1081A000F2CFA895089583EC8093520080915000FF
:1081B0008860809350008091510083FFFCCF82EC57
:1081C0008093550080915000806180935000809191
:1081D000510084FFFCCF88ED84BF1092400084BF23
:1081E00024E02093400087E08093A20087E88093FA
:1081F0008301109241081092420810924308109295
:10820000440810924608109247088FEF9FEF809322
:1082100066089093670810926008109261088BE0DE
:1082200080934008209365062093620688E180933E
:10823000720698E0909345069093410692E29093DF
:10824000A6081092A7088093A4088091A3088F7CA9
:1082500080618093A30883E08093A5088091A008A3
:1082600008958091CF0187FDFCCF08958F939F9350
:1082700082E2E0ECF1E08287FF91EF918DE984BF2B
:10828000E8950895FC0186E28093CA0188ED84BFD9
:1082900081E08093CB0108950F921F92FC01062E7E
:1082A000172E83E28093CA018DE984BFE8951F9061
:1082B0000F900895FC018EE28093CA018DE984BF7E
:0482C000E8950895A0
:040000030000800079
:00000001FF

View File

@ -1,16 +1,8 @@
## Save hex ## Override some platform.txt settings to create a .bin instead of a .hex file
recipe.output.tmp_file={build.project_name}.hex ## The two lines below can be uncommented to have the compiler create a .bin file instead of a .hex file
recipe.output.save_file=multi-avr.hex #compiler.elf2hex.flags=-O binary -R .eeprom
#recipe.objcopy.hex.pattern="{compiler.path}{compiler.elf2hex.cmd}" {compiler.elf2hex.flags} {compiler.elf2hex.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.bin"
## Copy hex ## Make a .bin version of the .hex file
# Make a copy of the compiled binary with the version number in the file name ## The line below can be uncommented to have a .bin file made as well as the .hex file
recipe.hooks.objcopy.postobjcopy.01.pattern.windows="{runtime.platform.path}/tools/win/do_version.bat" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} #recipe.hooks.objcopy.postobjcopy.00.pattern.windows="{compiler.path}{compiler.objcopy.cmd}" -I ihex "{build.path}/{build.project_name}.hex" -O binary "{build.path}/{build.project_name}.bin"
recipe.hooks.objcopy.postobjcopy.01.pattern.linux="{runtime.platform.path}/tools/linux/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.linux64="{runtime.platform.path}/tools/linux64/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.macosx="{runtime.platform.path}/tools/macosx/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
# If we're exporting the hex file, rename it with the version number
recipe.hooks.savehex.postsavehex.01.pattern.windows="{runtime.platform.path}/tools/win/do_version.bat" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.linux="{runtime.platform.path}/tools/linux/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.linux64="{runtime.platform.path}/tools/linux64/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.macosx="{runtime.platform.path}/tools/macosx/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT

View File

@ -1,7 +1,139 @@
# #
# Customized for the Atmega328p and OrangeRX (XMEGA) multi 4-in-1 boards.
# Both are AVR boards but need different compiler and upload flags and parameters.
# #
# For more info: # For more info:
# https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5---3rd-party-Hardware-specification # https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5---3rd-party-Hardware-specification
name=Multi 4-in-1 AVR name=Multi 4-in-1 AVR
version=1.0.0 version=1.0.2
compiler.warning_flags=-w
compiler.warning_flags.none=-w
compiler.warning_flags.default=
compiler.warning_flags.more=-Wall
compiler.warning_flags.all=-Wall -Wextra
# Default "compiler.path" is correct, change only if you want to override the initial value
compiler.path={runtime.tools.avr-gcc.path}/bin/
compiler.c.cmd=avr-gcc
compiler.c.flags={board.compiler.c.flags}
compiler.c.elf.flags={compiler.warning_flags} {board.compiler.c.elf.flags}
compiler.c.elf.cmd=avr-gcc
compiler.S.flags={board.compiler.S.flags}
compiler.cpp.cmd=avr-g++
compiler.cpp.flags=-c -g -Os {compiler.warning_flags} -std=gnu++11 -fpermissive -fno-exceptions -ffunction-sections -fdata-sections -fno-threadsafe-statics -MMD -flto
compiler.ar.cmd=avr-gcc-ar
compiler.ar.flags=rcs
compiler.objcopy.cmd=avr-objcopy
compiler.objcopy.eep.flags=-O ihex -j .eeprom --set-section-flags=.eeprom=alloc,load --no-change-warnings --change-section-lma .eeprom=0
compiler.elf2hex.flags=-O ihex -R .eeprom
compiler.elf2hex.cmd=avr-objcopy
compiler.ldflags=
compiler.size.cmd=avr-size
# This can be overridden in boards.txt
build.extra_flags=
# These can be overridden in platform.local.txt
compiler.c.extra_flags=
compiler.c.elf.extra_flags=
compiler.S.extra_flags=
compiler.cpp.extra_flags=
compiler.ar.extra_flags=
compiler.objcopy.eep.extra_flags=
compiler.elf2hex.extra_flags=
# AVR compile patterns
# --------------------
## Compile c files
recipe.c.o.pattern="{compiler.path}{compiler.c.cmd}" {compiler.c.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.c.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{object_file}"
## Compile c++ files
recipe.cpp.o.pattern="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.cpp.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{object_file}"
## Compile S files
recipe.S.o.pattern="{compiler.path}{compiler.c.cmd}" {compiler.S.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.S.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{object_file}"
## Create archives
# archive_file_path is needed for backwards compatibility with IDE 1.6.5 or older, IDE 1.6.6 or newer overrides this value
archive_file_path={build.path}/{archive_file}
recipe.ar.pattern="{compiler.path}{compiler.ar.cmd}" {compiler.ar.flags} {compiler.ar.extra_flags} "{archive_file_path}" "{object_file}"
## Combine gc-sections, archives, and objects
recipe.c.combine.pattern="{compiler.path}{compiler.c.elf.cmd}" {compiler.c.elf.flags} -mmcu={build.mcu} {compiler.c.elf.extra_flags} -o "{build.path}/{build.project_name}.elf" {object_files} "{build.path}/{archive_file}" "-L{build.path}" -lm
## Create output files (.eep and .hex)
recipe.objcopy.eep.pattern="{compiler.path}{compiler.objcopy.cmd}" {compiler.objcopy.eep.flags} {compiler.objcopy.eep.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.eep"
recipe.objcopy.hex.pattern="{compiler.path}{compiler.elf2hex.cmd}" {compiler.elf2hex.flags} {compiler.elf2hex.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.hex"
## Save hex
recipe.output.tmp_file={build.project_name}.hex
recipe.output.save_file={board.recipe.output.save_file}
## Compute size
recipe.size.pattern="{compiler.path}{compiler.size.cmd}" -A "{build.path}/{build.project_name}.elf"
recipe.size.regex=^(?:\.text|\.data|\.bootloader)\s+([0-9]+).*
recipe.size.regex.data=^(?:\.data|\.bss|\.noinit)\s+([0-9]+).*
recipe.size.regex.eeprom=^(?:\.eeprom)\s+([0-9]+).*
## Preprocessor
preproc.includes.flags=-w -x c++ -M -MG -MP
recipe.preproc.includes="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} {preproc.includes.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.cpp.extra_flags} {build.extra_flags} {includes} "{source_file}"
preproc.macros.flags=-w -x c++ -E -CC
recipe.preproc.macros="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} {preproc.macros.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.cpp.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{preprocessed_file_path}"
## Post objcopy recipes
# Make a copy of the compiled binary with the version number in the file name
recipe.hooks.objcopy.postobjcopy.01.pattern.windows="{runtime.platform.path}/tools/win/do_version.bat" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.linux="{runtime.platform.path}/tools/linux/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.linux64="{runtime.platform.path}/tools/linux64/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.macosx="{runtime.platform.path}/tools/macosx/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
## Post savehex (export compiled binary) recipes
# If we're exporting the hex file, rename it with the version number
recipe.hooks.savehex.postsavehex.01.pattern.windows="{runtime.platform.path}/tools/win/do_version.bat" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.linux="{runtime.platform.path}/tools/linux/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.linux64="{runtime.platform.path}/tools/linux64/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.macosx="{runtime.platform.path}/tools/macosx/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
# AVR Uploader/Programmers tools
# ------------------------------
tools.avrdude.path={runtime.tools.avrdude.path}
tools.avrdude.cmd.path={path}/bin/avrdude
tools.avrdude.config.path={board.tools.avrdude.config.path}
tools.avrdude.upload.params.verbose=-v
tools.avrdude.upload.params.quiet=-q -q
# tools.avrdude.upload.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value
tools.avrdude.upload.verify=
tools.avrdude.upload.params.noverify=-V
tools.avrdude.upload.pattern="{cmd.path}" "-C{config.path}" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} "-P{serial.port}" -b{upload.speed} -D "-Uflash:w:{build.path}/{build.project_name}.hex:i"
tools.avrdude.program.params.verbose=-v
tools.avrdude.program.params.quiet=-q -q
# tools.avrdude.program.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value
tools.avrdude.program.verify=
tools.avrdude.program.params.noverify=-V
tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} {program.verify} -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.hex:i"
tools.avrdude.erase.params.verbose=-v
tools.avrdude.erase.params.quiet=-q -q
tools.avrdude.erase.pattern={board.tools.avrdude.erase.pattern}
tools.avrdude.bootloader.params.verbose=-v
tools.avrdude.bootloader.params.quiet=-q -q
tools.avrdude.bootloader.pattern={board.tools.avrdude.bootloader.pattern}
tools.avrdude_remote.upload.pattern=/usr/bin/run-avrdude /tmp/sketch.hex {upload.verbose} -p{build.mcu}
# USB Default Flags
# Default blank usb manufacturer will be filled in at compile time
# - from numeric vendor ID, set to Unknown otherwise
build.usb_manufacturer="Unknown"
build.usb_flags=-DUSB_VID={build.vid} -DUSB_PID={build.pid} '-DUSB_MANUFACTURER={build.usb_manufacturer}' '-DUSB_PRODUCT={build.usb_product}'

View File

@ -6,7 +6,31 @@ SKETCH_PATH=$3
MULTI_BOARD=$4 MULTI_BOARD=$4
EXPORT_FLAG=$5 EXPORT_FLAG=$5
IFS== read MULTI_BOARD BOARD_VERSION <<< "$MULTI_BOARD"
case "$MULTI_BOARD" in
MULTI_NO_BOOT)
MULTI_TYPE=avr MULTI_TYPE=avr
;;
MULTI_FLASH_FROM_TX)
MULTI_TYPE=avr
;;
MULTI_STM32_NO_BOOT)
MULTI_TYPE=stm
;;
MULTI_STM32_FLASH_FROM_TX)
MULTI_TYPE=stm
;;
MULTI_ORANGERX)
MULTI_TYPE=orx
;;
esac
#echo "Build Path: $BUILD_PATH"
#echo "Sketch Path: $SKETCH_PATH"
#echo "Project Name: $PROJECT_NAME"
#echo "Multi Board: $MULTI_BOARD"
#echo "Multi Board Type: $MULTI_TYPE"
if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then
MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}') MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')

View File

@ -6,7 +6,31 @@ SKETCH_PATH=$3
MULTI_BOARD=$4 MULTI_BOARD=$4
EXPORT_FLAG=$5 EXPORT_FLAG=$5
IFS== read MULTI_BOARD BOARD_VERSION <<< "$MULTI_BOARD"
case "$MULTI_BOARD" in
MULTI_NO_BOOT)
MULTI_TYPE=avr MULTI_TYPE=avr
;;
MULTI_FLASH_FROM_TX)
MULTI_TYPE=avr
;;
MULTI_STM32_NO_BOOT)
MULTI_TYPE=stm
;;
MULTI_STM32_FLASH_FROM_TX)
MULTI_TYPE=stm
;;
MULTI_ORANGERX)
MULTI_TYPE=orx
;;
esac
#echo "Build Path: $BUILD_PATH"
#echo "Sketch Path: $SKETCH_PATH"
#echo "Project Name: $PROJECT_NAME"
#echo "Multi Board: $MULTI_BOARD"
#echo "Multi Board Type: $MULTI_TYPE"
if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then
MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}') MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')

View File

@ -6,7 +6,31 @@ SKETCH_PATH=$3
MULTI_BOARD=$4 MULTI_BOARD=$4
EXPORT_FLAG=$5 EXPORT_FLAG=$5
IFS== read MULTI_BOARD BOARD_VERSION <<< "$MULTI_BOARD"
case "$MULTI_BOARD" in
MULTI_NO_BOOT)
MULTI_TYPE=avr MULTI_TYPE=avr
;;
MULTI_FLASH_FROM_TX)
MULTI_TYPE=avr
;;
MULTI_STM32_NO_BOOT)
MULTI_TYPE=stm
;;
MULTI_STM32_FLASH_FROM_TX)
MULTI_TYPE=stm
;;
MULTI_ORANGERX)
MULTI_TYPE=orx
;;
esac
#echo "Build Path: $BUILD_PATH"
#echo "Sketch Path: $SKETCH_PATH"
#echo "Project Name: $PROJECT_NAME"
#echo "Multi Board: $MULTI_BOARD"
#echo "Multi Board Type: $MULTI_TYPE"
if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then
MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}') MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')

View File

@ -7,31 +7,43 @@ SET BUILD_PATH=%1
SET PROJECT_NAME=%2 SET PROJECT_NAME=%2
SET SKETCH_PATH=%3 SET SKETCH_PATH=%3
SET MULTI_BOARD=%4 SET MULTI_BOARD=%4
SET EXPORT_FLAG=%5 SET BOARD_VERSION=%5
SET EXPORT_FLAG=%6
REM Remove double-quotes from the paths REM Remove double-quotes from the paths
SET BUILD_PATH=%BUILD_PATH:"=% SET BUILD_PATH=%BUILD_PATH:"=%
SET SKETCH_PATH=%SKETCH_PATH:"=% SET SKETCH_PATH=%SKETCH_PATH:"=%
IF %MULTI_BOARD%==MULTI_NO_BOOT SET MULTI_TYPE=avr
IF %MULTI_BOARD%==MULTI_FLASH_FROM_TX SET MULTI_TYPE=avr
IF %MULTI_BOARD%==MULTI_STM32_NO_BOOT SET MULTI_TYPE=stm
IF %MULTI_BOARD%==MULTI_STM32_FLASH_FROM_TX SET MULTI_TYPE=stm
IF %MULTI_BOARD%==MULTI_ORANGERX SET MULTI_TYPE=orx
IF DEFINED DEBUG ( IF DEFINED DEBUG (
ECHO.
ECHO Sketch Path: %SKETCH_PATH% ECHO Sketch Path: %SKETCH_PATH%
ECHO Multi board: %MULTI_BOARD% ECHO Multi Board: %MULTI_BOARD%
ECHO Multi Board Type: %MULTI_TYPE%
ECHO.
) )
SET MULTI_TYPE=avr IF EXIST "%BUILD_PATH%\sketch\Multiprotocol.h" (
IF DEFINED DEBUG ECHO Getting Multi firmware version from "%BUILD_PATH%\sketch\Multiprotocol.h"
IF EXIST "%1\sketch\Multiprotocol.h" ( FOR /F "tokens=* usebackq" %%A in (`%SystemRoot%\system32\findstr.exe /C:"#define VERSION_MAJOR" "%BUILD_PATH%\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%A") do SET MAJOR_VERSION=%%i
REM ECHO Getting Multi-MODULE firmware version from "%1\sketch\Multiprotocol.h" FOR /F "tokens=* usebackq" %%B in (`%SystemRoot%\system32\findstr.exe /C:"#define VERSION_MINOR" "%BUILD_PATH%\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%B") do SET MINOR_VERSION=%%i
FOR /F "tokens=* usebackq skip=2" %%A in (`find "#define VERSION_MAJOR" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%A") do SET MAJOR_VERSION=%%i FOR /F "tokens=* usebackq" %%C in (`%SystemRoot%\system32\findstr.exe /C:"#define VERSION_REVISION" "%BUILD_PATH%\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%C") do SET REVISION_VERSION=%%i
FOR /F "tokens=* usebackq skip=2" %%B in (`find "#define VERSION_MINOR" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%B") do SET MINOR_VERSION=%%i FOR /F "tokens=* usebackq" %%D in (`%SystemRoot%\system32\findstr.exe /C:"#define VERSION_PATCH_LEVEL" "%BUILD_PATH%\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%D") do SET PATCH_VERSION=%%i
FOR /F "tokens=* usebackq skip=2" %%C in (`find "#define VERSION_REVISION" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%C") do SET REVISION_VERSION=%%i
FOR /F "tokens=* usebackq skip=2" %%D in (`find "#define VERSION_PATCH_LEVEL" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%D") do SET PATCH_VERSION=%%i
SET MULTI_VER=!MAJOR_VERSION!.!MINOR_VERSION!.!REVISION_VERSION!.!PATCH_VERSION! SET MULTI_VER=!MAJOR_VERSION!.!MINOR_VERSION!.!REVISION_VERSION!.!PATCH_VERSION!
) ELSE ( ) ELSE (
SET MULTI_VER= SET MULTI_VER=
) )
IF DEFINED DEBUG ECHO Multi-MODULE firmware version: %MULTI_VER% IF DEFINED DEBUG (
ECHO.
ECHO Multi Firmware Version: %MULTI_VER%
ECHO.
)
REM Copy the compiled file to the sketch folder with the version number in the file name REM Copy the compiled file to the sketch folder with the version number in the file name
IF EXIST "%BUILD_PATH%\%PROJECT_NAME%.hex" ( IF EXIST "%BUILD_PATH%\%PROJECT_NAME%.hex" (

View File

@ -0,0 +1,26 @@
#!/bin/bash
AVR_VERSION=$(grep "^version=[0-9].[0-9].[0-9]" "avr/platform.txt" | awk -F = '{ print $2 }')
STM_VERSION=$(grep "^version=[0-9].[0-9].[0-9]" "stm32/platform.txt" | awk -F = '{ print $2 }')
echo
echo "AVR Version: $AVR_VERSION"
echo "Creating archive 'package_multi_4in1_avr_board_v$AVR_VERSION.tar.gz'"
tar -czf ../Archives/package_multi_4in1_avr_board_v$AVR_VERSION.tar.gz --transform s/avr/package_multi_4in1_avr_board_v$AVR_VERSION/ avr/*
sleep 1s
echo
echo "Package: package_multi_4in1_avr_board_v$AVR_VERSION.tar.gz"
echo "SHA256: `(sha256sum ../Archives/package_multi_4in1_avr_board_v$AVR_VERSION.tar.gz | awk -v N=1 '{print $N}')`"
echo "Size: `(ls -al ../Archives/package_multi_4in1_avr_board_v$AVR_VERSION.tar.gz | awk -v N=5 '{print $N}')`"
echo
echo "STM Version: $STM_VERSION"
echo "Creating archive 'package_multi_4in1_stm32_board_v$STM_VERSION.tar.gz'"
tar -czf ../Archives/package_multi_4in1_stm32_board_v$STM_VERSION.tar.gz --transform s/stm32/package_multi_4in1_stm32_board_v$STM_VERSION/ stm32/*
sleep 1s
echo
echo "Package: package_multi_4in1_stm_board_v$STM_VERSION.tar.gz"
echo "SHA256: `(sha256sum ../Archives/package_multi_4in1_stm32_board_v$STM_VERSION.tar.gz | awk -v N=1 '{print $N}')`"
echo "Size: `(ls -al ../Archives/package_multi_4in1_stm32_board_v$STM_VERSION.tar.gz | awk -v N=5 '{print $N}')`"
echo
echo Done
echo

View File

@ -1,19 +0,0 @@
# See: https://github.com/arduino/Arduino/wiki/Arduino-IDE-1.5---3rd-party-Hardware-specification
# See: http://code.google.com/p/arduino/wiki/Platforms
##############################################################
##############################################################
## Multi 4-in-1 (OrangeRX)
## --------------------------------------------------
multixmega32d4.name=Multi 4-in-1 (OrangeRX)
multixmega32d4.build.board=MULTI_ORANGERX
multixmega32d4.upload.protocol=arduino
multixmega32d4.upload.maximum_size=32768
multixmega32d4.upload.speed=115200
multixmega32d4.build.mcu=atxmega32d4
multixmega32d4.build.f_cpu=32000000L
multixmega32d4.build.core=xmega
multixmega32d4.build.variant=xmega32d4
##############################################################

View File

@ -1,25 +0,0 @@
## Save hex
recipe.output.tmp_file={build.project_name}.hex
recipe.output.save_file=multi-orx.hex
## Override some platform.txt settings to create a .bin instead of a .hex file
## The two lines below can be uncommented to have the compiler create a .bin file instead of a .hex file
#compiler.elf2hex.flags=-O binary -R .eeprom
#recipe.objcopy.hex.pattern="{compiler.path}{compiler.elf2hex.cmd}" {compiler.elf2hex.flags} {compiler.elf2hex.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.bin"
## Make a .bin version of the .hex file
## The line below can be uncommented to have a .bin file made as well as the .hex file
#recipe.hooks.objcopy.postobjcopy.00.pattern.windows="{compiler.path}{compiler.objcopy.cmd}" -I ihex "{build.path}/{build.project_name}.hex" -O binary "{build.path}/{build.project_name}.bin"
## Copy hex
# Make a copy of the compiled binary with the version number in the file name
recipe.hooks.objcopy.postobjcopy.01.pattern.windows="{runtime.platform.path}/tools/win/do_version.bat" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.linux="{runtime.platform.path}/tools/linux/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.linux64="{runtime.platform.path}/tools/linux64/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
recipe.hooks.objcopy.postobjcopy.01.pattern.macosx="{runtime.platform.path}/tools/macosx/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board}
# If we're exporting the hex file, rename it with the version number
recipe.hooks.savehex.postsavehex.01.pattern.windows="{runtime.platform.path}/tools/win/do_version.bat" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.linux="{runtime.platform.path}/tools/linux/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.linux64="{runtime.platform.path}/tools/linux64/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT
recipe.hooks.savehex.postsavehex.01.pattern.macosx="{runtime.platform.path}/tools/macosx/do_version" "{build.path}" "{build.project_name}" "{build.source.path}" {build.board} EXPORT

View File

@ -1,124 +0,0 @@
name=Multi 4-in-1 OrangeRX
version=1.0.1
# this was borrowed from the installed version of 'platform.txt'
# XMEGA compile variables
# ---------------------
compiler.warning_flags=-w
compiler.warning_flags.none=-w
compiler.warning_flags.default=
compiler.warning_flags.more=-Wall
compiler.warning_flags.all=-Wall -Wextra
# Default "compiler.path" is correct, change only if you want to override the initial value
compiler.path={runtime.tools.avr-gcc.path}/bin/
compiler.c.cmd=avr-gcc
compiler.c.flags=-c -g -Os {compiler.warning_flags} -std=gnu11 -ffunction-sections -fdata-sections -MMD -flto
compiler.c.elf.flags={compiler.warning_flags} -Os -flto -Wl,--gc-sections
compiler.c.elf.cmd=avr-gcc
compiler.S.flags=-c -g -x assembler-with-cpp -flto
compiler.cpp.cmd=avr-g++
compiler.cpp.flags=-c -g -Os {compiler.warning_flags} -std=gnu++11 -fpermissive -fno-exceptions -ffunction-sections -fdata-sections -fno-threadsafe-statics -MMD -flto
compiler.ar.cmd=avr-gcc-ar
compiler.ar.flags=rcs
compiler.objcopy.cmd=avr-objcopy
compiler.objcopy.eep.flags=-O ihex -j .eeprom --set-section-flags=.eeprom=alloc,load --no-change-warnings --change-section-lma .eeprom=0
compiler.elf2hex.flags=-O ihex -R .eeprom
compiler.elf2hex.cmd=avr-objcopy
compiler.ldflags=
compiler.size.cmd=avr-size
# This can be overridden in boards.txt
build.extra_flags=
# These can be overridden in platform.local.txt
compiler.c.extra_flags=
compiler.c.elf.extra_flags=
compiler.S.extra_flags=
compiler.cpp.extra_flags=
compiler.ar.extra_flags=
compiler.objcopy.eep.extra_flags=
compiler.elf2hex.extra_flags=
# XMEGA compile patterns
# --------------------
## Compile c files
recipe.c.o.pattern="{compiler.path}{compiler.c.cmd}" {compiler.c.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.c.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{object_file}"
## Compile c++ files
recipe.cpp.o.pattern="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.cpp.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{object_file}"
## Compile S files
recipe.S.o.pattern="{compiler.path}{compiler.c.cmd}" {compiler.S.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.S.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{object_file}"
## Create archives
# archive_file_path is needed for backwards compatibility with IDE 1.6.5 or older, IDE 1.6.6 or newer overrides this value
archive_file_path={build.path}/{archive_file}
recipe.ar.pattern="{compiler.path}{compiler.ar.cmd}" {compiler.ar.flags} {compiler.ar.extra_flags} "{archive_file_path}" "{object_file}"
## Combine gc-sections, archives, and objects
recipe.c.combine.pattern="{compiler.path}{compiler.c.elf.cmd}" {compiler.c.elf.flags} -mmcu={build.mcu} {compiler.c.elf.extra_flags} -o "{build.path}/{build.project_name}.elf" {object_files} "{build.path}/{archive_file}" "-L{build.path}" -lm
## Create output files (.eep and .hex)
recipe.objcopy.eep.pattern="{compiler.path}{compiler.objcopy.cmd}" {compiler.objcopy.eep.flags} {compiler.objcopy.eep.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.eep"
recipe.objcopy.hex.pattern="{compiler.path}{compiler.elf2hex.cmd}" {compiler.elf2hex.flags} {compiler.elf2hex.extra_flags} "{build.path}/{build.project_name}.elf" "{build.path}/{build.project_name}.hex"
## Save hex
recipe.output.tmp_file={build.project_name}.hex
recipe.output.save_file={build.project_name}.{build.variant}.hex
## Compute size
recipe.size.pattern="{compiler.path}{compiler.size.cmd}" -A "{build.path}/{build.project_name}.elf"
recipe.size.regex=^(?:\.text|\.data|\.bootloader)\s+([0-9]+).*
recipe.size.regex.data=^(?:\.data|\.bss|\.noinit)\s+([0-9]+).*
recipe.size.regex.eeprom=^(?:\.eeprom)\s+([0-9]+).*
## Preprocessor
preproc.includes.flags=-w -x c++ -M -MG -MP
recipe.preproc.includes="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} {preproc.includes.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.cpp.extra_flags} {build.extra_flags} {includes} "{source_file}"
preproc.macros.flags=-w -x c++ -E -CC
recipe.preproc.macros="{compiler.path}{compiler.cpp.cmd}" {compiler.cpp.flags} {preproc.macros.flags} -mmcu={build.mcu} -DF_CPU={build.f_cpu} -DARDUINO={runtime.ide.version} -DARDUINO_{build.board} -DARDUINO_ARCH_{build.arch} {compiler.cpp.extra_flags} {build.extra_flags} {includes} "{source_file}" -o "{preprocessed_file_path}"
# XMEGA Uploader/Programmers tools
# ------------------------------
tools.avrdude.path={runtime.tools.avrdude.path}
tools.avrdude.cmd.path={path}/bin/avrdude
# NOTE: change to avrdude.conf path - using the one specified by this hardware package
# THIS is a LOT 'nicer' than overwriting the system file. Some packages actually do that...
tools.avrdude.config.path={runtime.platform.path}/avrdude.conf
tools.avrdude.upload.params.verbose=-v
tools.avrdude.upload.params.quiet=-q -q
# tools.avrdude.upload.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value
tools.avrdude.upload.verify=
tools.avrdude.upload.params.noverify=-V
tools.avrdude.upload.pattern="{cmd.path}" "-C{config.path}" {upload.verbose} {upload.verify} -p{build.mcu} -c{upload.protocol} -P{serial.port} -b{upload.speed} -D "-Uflash:w:{build.path}/{build.project_name}.hex:i"
tools.avrdude.program.params.verbose=-v
tools.avrdude.program.params.quiet=-q -q
# tools.avrdude.program.verify is needed for backwards compatibility with IDE 1.6.8 or older, IDE 1.6.9 or newer overrides this value
tools.avrdude.program.verify=
tools.avrdude.program.params.noverify=-V
tools.avrdude.program.pattern="{cmd.path}" "-C{config.path}" {program.verbose} {program.verify} -p{build.mcu} -c{protocol} {program.extra_params} "-Uflash:w:{build.path}/{build.project_name}.hex:i"
tools.avrdude.erase.params.verbose=-v
tools.avrdude.erase.params.quiet=-q -q
tools.avrdude.erase.pattern="{cmd.path}" "-C{config.path}" {erase.verbose} -p{build.mcu} -c{protocol} {program.extra_params} -e -Ulock:w:{bootloader.unlock_bits}:m -Ufuse1:w:{bootloader.fuse1}:m -Ufuse2:w:{bootloader.fuse2}:m -Ufuse4:w:{bootloader.fuse4}:m -Ufuse5:w:{bootloader.fuse5}:m
tools.avrdude.bootloader.params.verbose=-v
tools.avrdude.bootloader.params.quiet=-q -q
tools.avrdude.bootloader.pattern="{cmd.path}" "-C{config.path}" {bootloader.verbose} -p{build.mcu} -c{protocol} {program.extra_params} "-Uboot:w:{runtime.platform.path}/bootloaders/{bootloader.file}:i" -Ulock:w:{bootloader.lock_bits}:m
tools.avrdude_remote.upload.pattern=/usr/bin/run-avrdude /tmp/sketch.hex {upload.verbose} -p{build.mcu}
# USB Default Flags
# Default blank usb manufacturer will be filled in at compile time
# - from numeric vendor ID, set to Unknown otherwise
build.usb_manufacturer="Unknown"
build.usb_flags=-DUSB_VID={build.vid} -DUSB_PID={build.pid} '-DUSB_MANUFACTURER={build.usb_manufacturer}' '-DUSB_PRODUCT={build.usb_product}'

View File

@ -1,47 +0,0 @@
#!/bin/bash
BUILD_PATH=$1
PROJECT_NAME=$2
SKETCH_PATH=$3
MULTI_BOARD=$4
EXPORT_FLAG=$5
MULTI_TYPE=orx
if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then
MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
MINOR_VERSION=$(grep "VERSION_MINOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
REVISION_VERSION=$(grep "VERSION_REVISION" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
PATCH_VERSION=$(grep "VERSION_PATCH" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
MULTI_VERSION=$MAJOR_VERSION.$MINOR_VERSION.$REVISION_VERSION.$PATCH_VERSION
else
MULTI_VERSION=
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.hex" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.hex" "$BUILD_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.hex"
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.bin" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.bin" "$BUILD_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.bin"
fi
if [ $# -eq 5 ]; then
if [ $EXPORT_FLAG == "EXPORT" ]; then
if [ -e "$BUILD_PATH/$PROJECT_NAME.hex" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.hex" "$SKETCH_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.hex"
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.bin" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.bin" "$SKETCH_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.bin"
fi
if [ -e "$SKETCH_PATH/multi-$MULTI_TYPE.hex" ]; then
rm "$SKETCH_PATH/multi-$MULTI_TYPE.hex"
fi
if [ -e "$SKETCH_PATH/multi-$MULTI_TYPE.bin" ]; then
rm "$SKETCH_PATH/multi-$MULTI_TYPE.bin"
fi
fi
fi

View File

@ -1,47 +0,0 @@
#!/bin/bash
BUILD_PATH=$1
PROJECT_NAME=$2
SKETCH_PATH=$3
MULTI_BOARD=$4
EXPORT_FLAG=$5
MULTI_TYPE=orx
if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then
MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
MINOR_VERSION=$(grep "VERSION_MINOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
REVISION_VERSION=$(grep "VERSION_REVISION" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
PATCH_VERSION=$(grep "VERSION_PATCH" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
MULTI_VERSION=$MAJOR_VERSION.$MINOR_VERSION.$REVISION_VERSION.$PATCH_VERSION
else
MULTI_VERSION=
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.hex" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.hex" "$BUILD_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.hex"
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.bin" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.bin" "$BUILD_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.bin"
fi
if [ $# -eq 5 ]; then
if [ $EXPORT_FLAG == "EXPORT" ]; then
if [ -e "$BUILD_PATH/$PROJECT_NAME.hex" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.hex" "$SKETCH_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.hex"
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.bin" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.bin" "$SKETCH_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.bin"
fi
if [ -e "$SKETCH_PATH/multi-$MULTI_TYPE.hex" ]; then
rm "$SKETCH_PATH/multi-$MULTI_TYPE.hex"
fi
if [ -e "$SKETCH_PATH/multi-$MULTI_TYPE.bin" ]; then
rm "$SKETCH_PATH/multi-$MULTI_TYPE.bin"
fi
fi
fi

View File

@ -1,47 +0,0 @@
#!/bin/bash
BUILD_PATH=$1
PROJECT_NAME=$2
SKETCH_PATH=$3
MULTI_BOARD=$4
EXPORT_FLAG=$5
MULTI_TYPE=orx
if [ -e "$BUILD_PATH/sketch/Multiprotocol.h" ]; then
MAJOR_VERSION=$(grep "VERSION_MAJOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
MINOR_VERSION=$(grep "VERSION_MINOR" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
REVISION_VERSION=$(grep "VERSION_REVISION" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
PATCH_VERSION=$(grep "VERSION_PATCH" "$BUILD_PATH/sketch/Multiprotocol.h" | awk -v N=3 '{print $N}')
MULTI_VERSION=$MAJOR_VERSION.$MINOR_VERSION.$REVISION_VERSION.$PATCH_VERSION
else
MULTI_VERSION=
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.hex" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.hex" "$BUILD_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.hex"
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.bin" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.bin" "$BUILD_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.bin"
fi
if [ $# -eq 5 ]; then
if [ $EXPORT_FLAG == "EXPORT" ]; then
if [ -e "$BUILD_PATH/$PROJECT_NAME.hex" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.hex" "$SKETCH_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.hex"
fi
if [ -e "$BUILD_PATH/$PROJECT_NAME.bin" ]; then
cp "$BUILD_PATH/$PROJECT_NAME.bin" "$SKETCH_PATH/multi-$MULTI_TYPE-$MULTI_VERSION.bin"
fi
if [ -e "$SKETCH_PATH/multi-$MULTI_TYPE.hex" ]; then
rm "$SKETCH_PATH/multi-$MULTI_TYPE.hex"
fi
if [ -e "$SKETCH_PATH/multi-$MULTI_TYPE.bin" ]; then
rm "$SKETCH_PATH/multi-$MULTI_TYPE.bin"
fi
fi
fi

View File

@ -1,67 +0,0 @@
@ECHO OFF
SETLOCAL EnableDelayedExpansion
REM SET DEBUG=1
SET BUILD_PATH=%1
SET PROJECT_NAME=%2
SET SKETCH_PATH=%3
SET MULTI_BOARD=%4
SET EXPORT_FLAG=%5
REM Remove double-quotes from the paths
SET BUILD_PATH=%BUILD_PATH:"=%
SET SKETCH_PATH=%SKETCH_PATH:"=%
IF DEFINED DEBUG (
ECHO Sketch Path: %SKETCH_PATH%
ECHO Multi board: %MULTI_BOARD%
)
SET MULTI_TYPE=orx
IF EXIST "%1\sketch\Multiprotocol.h" (
REM ECHO Getting Multi-MODULE firmware version from "%1\sketch\Multiprotocol.h"
FOR /F "tokens=* usebackq skip=2" %%A in (`find "#define VERSION_MAJOR" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%A") do SET MAJOR_VERSION=%%i
FOR /F "tokens=* usebackq skip=2" %%B in (`find "#define VERSION_MINOR" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%B") do SET MINOR_VERSION=%%i
FOR /F "tokens=* usebackq skip=2" %%C in (`find "#define VERSION_REVISION" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%C") do SET REVISION_VERSION=%%i
FOR /F "tokens=* usebackq skip=2" %%D in (`find "#define VERSION_PATCH_LEVEL" "%1\sketch\Multiprotocol.h"`) DO FOR /F "tokens=3" %%i in ("%%D") do SET PATCH_VERSION=%%i
SET MULTI_VER=!MAJOR_VERSION!.!MINOR_VERSION!.!REVISION_VERSION!.!PATCH_VERSION!
) ELSE (
SET MULTI_VER=
)
IF DEFINED DEBUG ECHO Multi-MODULE firmware version: %MULTI_VER%
REM Copy the compiled file to the sketch folder with the version number in the file name
IF EXIST "%BUILD_PATH%\%PROJECT_NAME%.hex" (
IF DEFINED DEBUG ECHO COPY "%BUILD_PATH%\%PROJECT_NAME%.hex" "%BUILD_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.hex" /Y
COPY "%BUILD_PATH%\%PROJECT_NAME%.hex" "%BUILD_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.hex" /Y >NUL
)
IF EXIST "%BUILD_PATH%\%PROJECT_NAME%.bin" (
IF DEFINED DEBUG ECHO COPY "%BUILD_PATH%\%PROJECT_NAME%.bin" "%BUILD_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.bin" /Y
COPY "%BUILD_PATH%\%PROJECT_NAME%.bin" "%BUILD_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.bin" /Y >NUL
)
IF "%EXPORT_FLAG%"=="EXPORT" (
REM Copy the compiled file to the sketch folder with the version number in the file name
IF EXIST "%BUILD_PATH%\%PROJECT_NAME%.hex" (
IF DEFINED DEBUG ECHO COPY "%BUILD_PATH%\%PROJECT_NAME%.hex" "%SKETCH_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.hex" /Y
COPY "%BUILD_PATH%\%PROJECT_NAME%.hex" "%SKETCH_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.hex" /Y >NUL
)
IF EXIST "%BUILD_PATH%\%PROJECT_NAME%.bin" (
IF DEFINED DEBUG ECHO COPY "%BUILD_PATH%\%PROJECT_NAME%.bin" "%SKETCH_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.bin" /Y
COPY "%BUILD_PATH%\%PROJECT_NAME%.bin" "%SKETCH_PATH%\multi-%MULTI_TYPE%-%MULTI_VER%.bin" /Y >NUL
)
IF EXIST "%SKETCH_PATH%\multi-%MULTI_TYPE%.bin" (
IF DEFINED DEBUG ECHO DEL "%SKETCH_PATH%\multi-%MULTI_TYPE%.bin"
DEL "%SKETCH_PATH%\multi-%MULTI_TYPE%.bin" >NUL
)
IF EXIST "%SKETCH_PATH%\multi-%MULTI_TYPE%.hex" (
IF DEFINED DEBUG ECHO DEL "%SKETCH_PATH%\multi-%MULTI_TYPE%.hex"
DEL "%SKETCH_PATH%\multi-%MULTI_TYPE%.hex" >NUL
)
)

View File

@ -16,7 +16,7 @@ multistm32f103c.pid.0=0x0004
multistm32f103c.build.variant=generic_stm32f103c multistm32f103c.build.variant=generic_stm32f103c
multistm32f103c.build.vect=VECT_TAB_ADDR=0x8000000 multistm32f103c.build.vect=VECT_TAB_ADDR=0x8000000
multistm32f103c.build.core=maple multistm32f103c.build.core=maple
multistm32f103c.build.board=MULTI_STM32_FLASH_FROM_TX multistm32f103c.build.board=MULTI_STM32_FLASH_FROM_TX=103
multistm32f103c.upload.use_1200bps_touch=false multistm32f103c.upload.use_1200bps_touch=false
multistm32f103c.upload.file_type=bin multistm32f103c.upload.file_type=bin
multistm32f103c.upload.auto_reset=true multistm32f103c.upload.auto_reset=true
@ -37,20 +37,20 @@ multistm32f103c.bootloader.tool=serial_upload
#---------------------------- UPLOAD METHODS --------------------------- #---------------------------- UPLOAD METHODS ---------------------------
multistm32f103c.menu.upload_method.TxFlashMethod=Flash from Tx multistm32f103c.menu.upload_method.TxFlashMethod=Flash from Tx
multistm32f103c.menu.upload_method.TxFlashMethod.build.board=MULTI_STM32_FLASH_FROM_TX=103
multistm32f103c.menu.upload_method.TxFlashMethod.upload.tool=tx_upload multistm32f103c.menu.upload_method.TxFlashMethod.upload.tool=tx_upload
multistm32f103c.menu.upload_method.TxFlashMethod.build.upload_flags=-DSERIAL_USB -DGENERIC_BOOTLOADER multistm32f103c.menu.upload_method.TxFlashMethod.build.upload_flags=-DSERIAL_USB -DGENERIC_BOOTLOADER
multistm32f103c.menu.upload_method.TxFlashMethod.build.vect=VECT_TAB_ADDR=0x8002000 multistm32f103c.menu.upload_method.TxFlashMethod.build.vect=VECT_TAB_ADDR=0x8002000
multistm32f103c.menu.upload_method.TxFlashMethod.build.ldscript=ld/bootloader_20.ld multistm32f103c.menu.upload_method.TxFlashMethod.build.ldscript=ld/bootloader_20.ld
multistm32f103c.menu.upload_method.TxFlashMethod.build.board=MULTI_STM32_FLASH_FROM_TX
multistm32f103c.menu.upload_method.TxFlashMethod.bootloader.file=Multi4in1/StmMultiBoot.bin multistm32f103c.menu.upload_method.TxFlashMethod.bootloader.file=Multi4in1/StmMultiBoot.bin
multistm32f103c.menu.upload_method.DFUUploadMethod=Upload via USB multistm32f103c.menu.upload_method.DFUUploadMethod=Upload via USB
multistm32f103c.menu.upload_method.DFUUploadMethod.build.board=MULTI_STM32_NO_BOOT=103
multistm32f103c.menu.upload_method.DFUUploadMethod.upload.protocol=maple_dfu multistm32f103c.menu.upload_method.DFUUploadMethod.upload.protocol=maple_dfu
multistm32f103c.menu.upload_method.DFUUploadMethod.upload.tool=maple_upload multistm32f103c.menu.upload_method.DFUUploadMethod.upload.tool=maple_upload
multistm32f103c.menu.upload_method.DFUUploadMethod.build.upload_flags=-DSERIAL_USB -DGENERIC_BOOTLOADER multistm32f103c.menu.upload_method.DFUUploadMethod.build.upload_flags=-DSERIAL_USB -DGENERIC_BOOTLOADER
multistm32f103c.menu.upload_method.DFUUploadMethod.build.vect=VECT_TAB_ADDR=0x8002000 multistm32f103c.menu.upload_method.DFUUploadMethod.build.vect=VECT_TAB_ADDR=0x8002000
multistm32f103c.menu.upload_method.DFUUploadMethod.build.ldscript=ld/bootloader_20.ld multistm32f103c.menu.upload_method.DFUUploadMethod.build.ldscript=ld/bootloader_20.ld
multistm32f103c.menu.upload_method.DFUUploadMethod.build.board=MULTI_STM32_NO_BOOT
multistm32f103c.menu.upload_method.DFUUploadMethod.upload.usbID=1EAF:0003 multistm32f103c.menu.upload_method.DFUUploadMethod.upload.usbID=1EAF:0003
multistm32f103c.menu.upload_method.DFUUploadMethod.upload.altID=2 multistm32f103c.menu.upload_method.DFUUploadMethod.upload.altID=2
multistm32f103c.menu.upload_method.DFUUploadMethod.bootloader.file=Multi4in1/StmMultiUSB.bin multistm32f103c.menu.upload_method.DFUUploadMethod.bootloader.file=Multi4in1/StmMultiUSB.bin
@ -59,6 +59,6 @@ multistm32f103c.menu.upload_method.serialMethod=Upload via Serial (FTDI)
multistm32f103c.menu.upload_method.serialMethod.upload.protocol=maple_serial multistm32f103c.menu.upload_method.serialMethod.upload.protocol=maple_serial
multistm32f103c.menu.upload_method.serialMethod.upload.tool=serial_upload multistm32f103c.menu.upload_method.serialMethod.upload.tool=serial_upload
multistm32f103c.menu.upload_method.serialMethod.build.upload_flags=-DCONFIG_MAPLE_MINI_NO_DISABLE_DEBUG multistm32f103c.menu.upload_method.serialMethod.build.upload_flags=-DCONFIG_MAPLE_MINI_NO_DISABLE_DEBUG
multistm32f103c.menu.upload_method.serialMethod.build.board=MULTI_STM32_NO_BOOT multistm32f103c.menu.upload_method.serialMethod.build.board=MULTI_STM32_NO_BOOT=103
############################################################## ##############################################################

View File

@ -193,7 +193,8 @@ size_t HardwareSerial::write(unsigned char ch) {
return 1; return 1;
} }
/* edogaldo: Waits for the transmission of outgoing serial data to complete (Arduino 1.0 api specs) */
void HardwareSerial::flush(void) { void HardwareSerial::flush(void) {
usart_reset_rx(this->usart_device); while(!rb_is_empty(this->usart_device->wb)); // wait for TX buffer empty
usart_reset_tx(this->usart_device); while(!((this->usart_device->regs->SR) & (1<<USART_SR_TC_BIT))); // wait for TC (Transmission Complete) flag set
} }

View File

@ -138,10 +138,24 @@ void HardwareTimer::detachInterrupt(int channel) {
timer_detach_interrupt(this->dev, (uint8)channel); timer_detach_interrupt(this->dev, (uint8)channel);
} }
void HardwareTimer::enableDMA(int channel) {
timer_dma_enable_req(this->dev, (uint8)channel);
}
void HardwareTimer::disableDMA(int channel) {
timer_dma_disable_req(this->dev, (uint8)channel);
}
void HardwareTimer::refresh(void) { void HardwareTimer::refresh(void) {
timer_generate_update(this->dev); timer_generate_update(this->dev);
} }
void HardwareTimer::setMasterModeTrGo(uint32_t mode) {
this->dev->regs.bas->CR2 &= ~TIMER_CR2_MMS;
this->dev->regs.bas->CR2 |= mode;
}
/* CARLOS Changes to add encoder mode.*/ /* CARLOS Changes to add encoder mode.*/
//direction of movement. (to be better described). //direction of movement. (to be better described).

View File

@ -177,7 +177,8 @@ public:
* This interrupt handler will be called when the timer's counter * This interrupt handler will be called when the timer's counter
* reaches the given channel compare value. * reaches the given channel compare value.
* *
* @param channel the channel to attach the ISR to, from 1 to 4. * @param channel the channel to attach the ISR to, from 0 to 4.
* Channel 0 is for overflow interrupt (update interrupt).
* @param handler The ISR to attach to the given channel. * @param handler The ISR to attach to the given channel.
* @see voidFuncPtr * @see voidFuncPtr
*/ */
@ -189,7 +190,8 @@ public:
* *
* The handler will no longer be called by this timer. * The handler will no longer be called by this timer.
* *
* @param channel the channel whose interrupt to detach, from 1 to 4. * @param channel the channel whose interrupt to detach, from 0 to 4.
* Channel 0 is for overflow interrupt (update interrupt).
* @see HardwareTimer::attachInterrupt() * @see HardwareTimer::attachInterrupt()
*/ */
void detachInterrupt(int channel); void detachInterrupt(int channel);
@ -209,6 +211,23 @@ public:
*/ */
void refresh(void); void refresh(void);
// SYFRE
/**
* @brief Set the Master mode TRGO signal
* These bits allow to select the information to be sent in master mode to slave timers for
* synchronization (TRGO).
* mode:
* TIMER_CR2_MMS_RESET
* TIMER_CR2_MMS_ENABLE
* TIMER_CR2_MMS_UPDATE
* TIMER_CR2_MMS_COMPARE_PULSE
* TIMER_CR2_MMS_COMPARE_OC1REF
* TIMER_CR2_MMS_COMPARE_OC2REF
* TIMER_CR2_MMS_COMPARE_OC3REF
* TIMER_CR2_MMS_COMPARE_OC4REF
*/
void setMasterModeTrGo(uint32_t mode);
//CARLOS. //CARLOS.
/* /*
added these functions to make sense for the encoder mode. added these functions to make sense for the encoder mode.
@ -229,6 +248,12 @@ public:
/* Escape hatch */ /* Escape hatch */
/** /**
* @brief Enable/disable DMA request for the input channel.
*/
void enableDMA(int channel);
void disableDMA(int channel);
/**
* @brief Get a pointer to the underlying libmaple timer_dev for * @brief Get a pointer to the underlying libmaple timer_dev for
* this HardwareTimer instance. * this HardwareTimer instance.
*/ */

View File

@ -44,6 +44,48 @@ IPAddress::IPAddress(const uint8_t *address)
memcpy(_address.bytes, address, sizeof(_address.bytes)); memcpy(_address.bytes, address, sizeof(_address.bytes));
} }
bool IPAddress::fromString(const char *address)
{
// TODO: add support for "a", "a.b", "a.b.c" formats
uint16_t acc = 0; // Accumulator
uint8_t dots = 0;
while (*address)
{
char c = *address++;
if (c >= '0' && c <= '9')
{
acc = acc * 10 + (c - '0');
if (acc > 255) {
// Value out of [0..255] range
return false;
}
}
else if (c == '.')
{
if (dots == 3) {
// Too much dots (there must be 3 dots)
return false;
}
_address.bytes[dots++] = acc;
acc = 0;
}
else
{
// Invalid char
return false;
}
}
if (dots != 3) {
// Too few dots (there must be 3 dots)
return false;
}
_address.bytes[3] = acc;
return true;
}
IPAddress& IPAddress::operator=(const uint8_t *address) IPAddress& IPAddress::operator=(const uint8_t *address)
{ {
memcpy(_address.bytes, address, sizeof(_address.bytes)); memcpy(_address.bytes, address, sizeof(_address.bytes));

View File

@ -46,6 +46,9 @@ public:
IPAddress(uint32_t address); IPAddress(uint32_t address);
IPAddress(const uint8_t *address); IPAddress(const uint8_t *address);
bool fromString(const char *address);
bool fromString(const String &address) { return fromString(address.c_str()); }
// Overloaded cast operator to allow IPAddress objects to be used where a pointer // Overloaded cast operator to allow IPAddress objects to be used where a pointer
// to a four-byte uint8_t array is expected // to a four-byte uint8_t array is expected
operator uint32_t() const { return _address.dword; }; operator uint32_t() const { return _address.dword; };

View File

@ -99,10 +99,6 @@ size_t Print::print(unsigned long n, int base) {
} }
size_t Print::print(long long n, int base) { size_t Print::print(long long n, int base) {
if (base == BYTE)
{
return write((uint8)n);
}
if (n < 0) { if (n < 0) {
print('-'); print('-');
n = -n; n = -n;
@ -111,19 +107,23 @@ size_t Print::print(long long n, int base) {
} }
size_t Print::print(unsigned long long n, int base) { size_t Print::print(unsigned long long n, int base) {
size_t c=0; return printNumber(n, base);
if (base == BYTE) {
c= write((uint8)n);
} else {
c= printNumber(n, base);
}
return c;
} }
size_t Print::print(double n, int digits) { size_t Print::print(double n, int digits) {
return printFloat(n, digits); return printFloat(n, digits);
} }
size_t Print::print(const __FlashStringHelper *ifsh)
{
return print(reinterpret_cast<const char *>(ifsh));
}
size_t Print::print(const Printable& x)
{
return x.printTo(*this);
}
size_t Print::println(void) size_t Print::println(void)
{ {
size_t n = print('\r'); size_t n = print('\r');
@ -198,6 +198,20 @@ size_t Print::println(double n, int digits) {
return s; return s;
} }
size_t Print::println(const __FlashStringHelper *ifsh)
{
size_t n = print(ifsh);
n += println();
return n;
}
size_t Print::println(const Printable& x)
{
size_t n = print(x);
n += println();
return n;
}
#ifdef SUPPORTS_PRINTF #ifdef SUPPORTS_PRINTF
#include <stdio.h> #include <stdio.h>
#include <stdarg.h> #include <stdarg.h>

View File

@ -25,9 +25,9 @@
#include <libmaple/libmaple_types.h> #include <libmaple/libmaple_types.h>
#include "WString.h" #include "WString.h"
#include "Printable.h"
enum { enum {
BYTE = 0,
BIN = 2, BIN = 2,
OCT = 8, OCT = 8,
DEC = 10, DEC = 10,
@ -51,6 +51,8 @@ public:
size_t print(long long, int=DEC); size_t print(long long, int=DEC);
size_t print(unsigned long long, int=DEC); size_t print(unsigned long long, int=DEC);
size_t print(double, int=2); size_t print(double, int=2);
size_t print(const __FlashStringHelper *);
size_t print(const Printable&);
size_t println(void); size_t println(void);
size_t println(const String &s); size_t println(const String &s);
size_t println(char); size_t println(char);
@ -63,6 +65,8 @@ public:
size_t println(long long, int=DEC); size_t println(long long, int=DEC);
size_t println(unsigned long long, int=DEC); size_t println(unsigned long long, int=DEC);
size_t println(double, int=2); size_t println(double, int=2);
size_t println(const __FlashStringHelper *);
size_t println(const Printable&);
#ifdef SUPPORTS_PRINTF #ifdef SUPPORTS_PRINTF
// Roger Clark. Work in progress to add printf support // Roger Clark. Work in progress to add printf support
int printf(const char * format, ...); int printf(const char * format, ...);

View File

@ -268,3 +268,68 @@ String Stream::readStringUntil(char terminator)
return ret; return ret;
} }
int Stream::findMulti( struct Stream::MultiTarget *targets, int tCount) {
// any zero length target string automatically matches and would make
// a mess of the rest of the algorithm.
for (struct MultiTarget *t = targets; t < targets+tCount; ++t) {
if (t->len <= 0)
return t - targets;
}
while (1) {
int c = timedRead();
if (c < 0)
return -1;
for (struct MultiTarget *t = targets; t < targets+tCount; ++t) {
// the simple case is if we match, deal with that first.
if (c == t->str[t->index]) {
if (++t->index == t->len)
return t - targets;
else
continue;
}
// if not we need to walk back and see if we could have matched further
// down the stream (ie '1112' doesn't match the first position in '11112'
// but it will match the second position so we can't just reset the current
// index to 0 when we find a mismatch.
if (t->index == 0)
continue;
int origIndex = t->index;
do {
--t->index;
// first check if current char works against the new current index
if (c != t->str[t->index])
continue;
// if it's the only char then we're good, nothing more to check
if (t->index == 0) {
t->index++;
break;
}
// otherwise we need to check the rest of the found string
int diff = origIndex - t->index;
size_t i;
for (i = 0; i < t->index; ++i) {
if (t->str[i] != t->str[i + diff])
break;
}
// if we successfully got through the previous loop then our current
// index is good.
if (i == t->index) {
t->index++;
break;
}
// otherwise we just try the next index
} while (t->index);
}
}
// unreachable
return -1;
}

View File

@ -55,6 +55,7 @@ class Stream : public Print
// parsing methods // parsing methods
void setTimeout(unsigned long timeout); // sets maximum milliseconds to wait for stream data, default is 1 second void setTimeout(unsigned long timeout); // sets maximum milliseconds to wait for stream data, default is 1 second
unsigned long getTimeout(void) { return _timeout; }
bool find(char *target); // reads data from the stream until the target string is found bool find(char *target); // reads data from the stream until the target string is found
bool find(uint8_t *target) { return find ((char *)target); } bool find(uint8_t *target) { return find ((char *)target); }
@ -64,6 +65,8 @@ class Stream : public Print
bool find(uint8_t *target, size_t length) { return find ((char *)target, length); } bool find(uint8_t *target, size_t length) { return find ((char *)target, length); }
// returns true if target string is found, false if timed out // returns true if target string is found, false if timed out
bool find(char target) { return find (&target, 1); }
bool findUntil(char *target, char *terminator); // as find but search ends if the terminator string is found bool findUntil(char *target, char *terminator); // as find but search ends if the terminator string is found
bool findUntil(uint8_t *target, char *terminator) { return findUntil((char *)target, terminator); } bool findUntil(uint8_t *target, char *terminator) { return findUntil((char *)target, terminator); }
@ -97,6 +100,16 @@ class Stream : public Print
// this allows format characters (typically commas) in values to be ignored // this allows format characters (typically commas) in values to be ignored
float parseFloat(char skipChar); // as above but the given skipChar is ignored float parseFloat(char skipChar); // as above but the given skipChar is ignored
struct MultiTarget {
const char *str; // string you're searching for
size_t len; // length of string you're searching for
size_t index; // index used by the search routine.
};
// This allows you to search for an arbitrary number of strings.
// Returns index of the target that is found first or -1 if timeout occurs.
int findMulti(struct MultiTarget *targets, int tCount);
}; };
#endif #endif

View File

@ -195,7 +195,7 @@ String & String::copy(const __FlashStringHelper *pstr, unsigned int length)
void String::move(String &rhs) void String::move(String &rhs)
{ {
if (buffer) { if (buffer) {
if (capacity >= rhs.len) { if (rhs && capacity >= rhs.len) {
strcpy(buffer, rhs.buffer); strcpy(buffer, rhs.buffer);
len = rhs.len; len = rhs.len;
rhs.len = 0; rhs.len = 0;

View File

@ -161,6 +161,10 @@ public:
void toCharArray(char *buf, unsigned int bufsize, unsigned int index=0) const void toCharArray(char *buf, unsigned int bufsize, unsigned int index=0) const
{getBytes((unsigned char *)buf, bufsize, index);} {getBytes((unsigned char *)buf, bufsize, index);}
const char * c_str() const { return buffer; } const char * c_str() const { return buffer; }
char* begin() { return buffer; }
char* end() { return buffer + length(); }
const char* begin() const { return c_str(); }
const char* end() const { return c_str() + length(); }
// search // search
int indexOf( char ch ) const; int indexOf( char ch ) const;

View File

@ -160,4 +160,6 @@ uint16 analogRead(uint8 pin);
*/ */
void shiftOut(uint8 dataPin, uint8 clockPin, uint8 bitOrder, uint8 value); void shiftOut(uint8 dataPin, uint8 clockPin, uint8 bitOrder, uint8 value);
uint32 shiftIn( uint32 ulDataPin, uint32 ulClockPin, uint32 ulBitOrder );
#endif #endif

View File

@ -120,8 +120,12 @@ extern char* ltoa( long value, char *string, int radix )
return string; return string;
} }
#if __GNUC__ > 4 || (__GNUC__ == 4 && (__GNUC_MINOR__ > 9 || \
extern char* utoa( unsigned long value, char *string, int radix ) (__GNUC_MINOR__ == 9 && __GNUC_PATCHLEVEL__ > 2)))
extern char* utoa( unsigned value, char *string, int radix )
#else
extern char* utoa( unsigned int value, char *string, int radix )
#endif
{ {
return ultoa( value, string, radix ) ; return ultoa( value, string, radix ) ;
} }

View File

@ -31,7 +31,12 @@ extern void itoa( int n, char s[] ) ;
extern char* itoa( int value, char *string, int radix ) ; extern char* itoa( int value, char *string, int radix ) ;
extern char* ltoa( long value, char *string, int radix ) ; extern char* ltoa( long value, char *string, int radix ) ;
extern char* utoa( unsigned long value, char *string, int radix ) ; #if __GNUC__ > 4 || (__GNUC__ == 4 && (__GNUC_MINOR__ > 9 || \
(__GNUC_MINOR__ == 9 && __GNUC_PATCHLEVEL__ > 2)))
extern char* utoa( unsigned value, char *string, int radix ) ;
#else
extern char* utoa( unsigned int value, char *string, int radix ) ;
#endif
extern char* ultoa( unsigned long value, char *string, int radix ) ; extern char* ultoa( unsigned long value, char *string, int radix ) ;
#endif /* 0 */ #endif /* 0 */

View File

@ -59,6 +59,7 @@ void adc_set_extsel(adc_dev *dev, adc_extsel_event event) {
uint32 cr2 = dev->regs->CR2; uint32 cr2 = dev->regs->CR2;
cr2 &= ~ADC_CR2_EXTSEL; cr2 &= ~ADC_CR2_EXTSEL;
cr2 |= event; cr2 |= event;
cr2 |= ADC_CR2_EXTTRIG;
dev->regs->CR2 = cr2; dev->regs->CR2 = cr2;
} }

View File

@ -203,7 +203,7 @@ void adc_foreach(void (*fn)(adc_dev*)) {
#endif #endif
} }
void adc_config_gpio(adc_dev *ignored, gpio_dev *gdev, uint8 bit) { void adc_config_gpio(adc_dev *ignored __attribute__((unused)), gpio_dev *gdev, uint8 bit) {
gpio_set_mode(gdev, bit, GPIO_INPUT_ANALOG); gpio_set_mode(gdev, bit, GPIO_INPUT_ANALOG);
} }

View File

@ -341,7 +341,6 @@ void dma_set_per_addr(dma_dev *dev, dma_channel channel, __io void *addr) {
* @see dma_attach_interrupt() * @see dma_attach_interrupt()
* @see dma_enable() * @see dma_enable()
*/ */
__deprecated
void dma_setup_transfer(dma_dev *dev, void dma_setup_transfer(dma_dev *dev,
dma_channel channel, dma_channel channel,
__io void *peripheral_address, __io void *peripheral_address,

View File

@ -142,7 +142,6 @@ gpio_pin_mode gpio_get_mode(gpio_dev *dev, uint8 pin) {
gpio_reg_map *regs = dev->regs; gpio_reg_map *regs = dev->regs;
__io uint32 *cr = &regs->CRL + (pin >> 3); __io uint32 *cr = &regs->CRL + (pin >> 3);
uint32 shift = (pin & 0x7) * 4; uint32 shift = (pin & 0x7) * 4;
uint32 tmp = *cr;
uint32 crMode = (*cr>>shift) & 0x0F; uint32 crMode = (*cr>>shift) & 0x0F;

View File

@ -84,7 +84,7 @@ void spi_slave_enable(spi_dev *dev, spi_mode mode, uint32 flags) {
} }
/** /**
* @brief Nonblocking SPI transmit. * @brief Blocking SPI transmit.
* @param dev SPI port to use for transmission * @param dev SPI port to use for transmission
* @param buf Buffer to transmit. The sizeof buf's elements are * @param buf Buffer to transmit. The sizeof buf's elements are
* inferred from dev's data frame format (i.e., are * inferred from dev's data frame format (i.e., are
@ -93,13 +93,19 @@ void spi_slave_enable(spi_dev *dev, spi_mode mode, uint32 flags) {
* @return Number of elements transmitted. * @return Number of elements transmitted.
*/ */
uint32 spi_tx(spi_dev *dev, const void *buf, uint32 len) { uint32 spi_tx(spi_dev *dev, const void *buf, uint32 len) {
uint32 txed = 0; uint32 txed = len;
uint8 byte_frame = spi_dff(dev) == SPI_DFF_8_BIT; spi_reg_map *regs = dev->regs;
while (spi_is_tx_empty(dev) && (txed < len)) { if ( spi_dff(dev) == SPI_DFF_8_BIT ) {
if (byte_frame) { const uint8 * dp8 = (const uint8*)buf;
dev->regs->DR = ((const uint8*)buf)[txed++]; while ( len-- ) {
while ( (regs->SR & SPI_SR_TXE)==0 ) ; //while ( spi_is_tx_empty(dev)==0 ); // wait Tx to be empty
regs->DR = *dp8++;
}
} else { } else {
dev->regs->DR = ((const uint16*)buf)[txed++]; const uint16 * dp16 = (const uint16*)buf;
while ( len-- ) {
while ( (regs->SR & SPI_SR_TXE)==0 ) ; //while ( spi_is_tx_empty(dev)==0 ); // wait Tx to be empty
regs->DR = *dp16++;
} }
} }
return txed; return txed;

View File

@ -54,7 +54,7 @@ spi_dev *SPI3 = &spi3;
* Routines * Routines
*/ */
void spi_config_gpios(spi_dev *ignored, void spi_config_gpios(spi_dev *ignored __attribute__((unused)),
uint8 as_master, uint8 as_master,
gpio_dev *nss_dev, gpio_dev *nss_dev,
uint8 nss_bit, uint8 nss_bit,

View File

@ -327,7 +327,7 @@ static void output_compare_mode(timer_dev *dev, uint8 channel) {
} }
//added by CARLOS. //added by CARLOS.
static void encoder_mode(timer_dev *dev, uint8 channel) { static void encoder_mode(timer_dev *dev, uint8 channel __attribute__((unused))) {
//prescaler. //prescaler.
//(dev->regs).gen->PSC = 1; //(dev->regs).gen->PSC = 1;

View File

@ -203,15 +203,15 @@ void usart_foreach(void (*fn)(usart_dev*)) {
void __irq_usart1(void) { void __irq_usart1(void) {
usart_irq(&usart1_rb, &usart1_wb, USART1_BASE); usart_irq(&usart1_rb, &usart1_wb, USART1_BASE);
} }
/*
void __irq_usart2(void) {
usart_irq(&usart2_rb, &usart2_wb, USART2_BASE);
}
//void __irq_usart2(void) { void __irq_usart3(void) {
// usart_irq(&usart2_rb, &usart2_wb, USART2_BASE); usart_irq(&usart3_rb, &usart3_wb, USART3_BASE);
//} }
*/
//void __irq_usart3(void) {
// usart_irq(&usart3_rb, &usart3_wb, USART3_BASE);
//}
#ifdef STM32_HIGH_DENSITY #ifdef STM32_HIGH_DENSITY
void __irq_uart4(void) { void __irq_uart4(void) {
usart_irq(&uart4_rb, &uart4_wb, UART4_BASE); usart_irq(&uart4_rb, &uart4_wb, UART4_BASE);

View File

@ -62,8 +62,8 @@
#if !(defined(BOARD_maple) || defined(BOARD_maple_RET6) || \ #if !(defined(BOARD_maple) || defined(BOARD_maple_RET6) || \
defined(BOARD_maple_mini) || defined(BOARD_maple_native)) defined(BOARD_maple_mini) || defined(BOARD_maple_native))
#warning USB CDC ACM relies on LeafLabs board-specific configuration.\ //#warning USB CDC ACM relies on LeafLabs board-specific configuration.\
You may have problems on non-LeafLabs boards. // You may have problems on non-LeafLabs boards.
#endif #endif
static void vcomDataTxCb(void); static void vcomDataTxCb(void);
@ -261,18 +261,28 @@ static ONE_DESCRIPTOR String_Descriptor[N_STRING_DESCRIPTORS] = {
/* I/O state */ /* I/O state */
#define CDC_SERIAL_BUFFER_SIZE 512 #define CDC_SERIAL_RX_BUFFER_SIZE 256 // must be power of 2
#define CDC_SERIAL_RX_BUFFER_SIZE_MASK (CDC_SERIAL_RX_BUFFER_SIZE-1)
/* Received data */ /* Received data */
static volatile uint8 vcomBufferRx[CDC_SERIAL_BUFFER_SIZE]; static volatile uint8 vcomBufferRx[CDC_SERIAL_RX_BUFFER_SIZE];
/* Read index into vcomBufferRx */ /* Write index to vcomBufferRx */
static volatile uint32 rx_offset = 0; static volatile uint32 rx_head;
/* Number of bytes left to transmit */ /* Read index from vcomBufferRx */
static volatile uint32 n_unsent_bytes = 0; static volatile uint32 rx_tail;
/* Are we currently sending an IN packet? */
static volatile uint8 transmitting = 0; #define CDC_SERIAL_TX_BUFFER_SIZE 256 // must be power of 2
/* Number of unread bytes */ #define CDC_SERIAL_TX_BUFFER_SIZE_MASK (CDC_SERIAL_TX_BUFFER_SIZE-1)
static volatile uint32 n_unread_bytes = 0; // Tx data
static volatile uint8 vcomBufferTx[CDC_SERIAL_TX_BUFFER_SIZE];
// Write index to vcomBufferTx
static volatile uint32 tx_head;
// Read index from vcomBufferTx
static volatile uint32 tx_tail;
// Are we currently sending an IN packet?
static volatile int8 transmitting;
/* Other state (line coding, DTR/RTS) */ /* Other state (line coding, DTR/RTS) */
@ -374,8 +384,12 @@ void usb_cdcacm_enable(gpio_dev *disc_dev, uint8 disc_bit) {
/* Present ourselves to the host. Writing 0 to "disc" pin must /* Present ourselves to the host. Writing 0 to "disc" pin must
* pull USB_DP pin up while leaving USB_DM pulled down by the * pull USB_DP pin up while leaving USB_DM pulled down by the
* transceiver. See USB 2.0 spec, section 7.1.7.3. */ * transceiver. See USB 2.0 spec, section 7.1.7.3. */
if (disc_dev!=NULL)
{
gpio_set_mode(disc_dev, disc_bit, GPIO_OUTPUT_PP); gpio_set_mode(disc_dev, disc_bit, GPIO_OUTPUT_PP);
gpio_write_bit(disc_dev, disc_bit, 0); gpio_write_bit(disc_dev, disc_bit, 0);
}
/* Initialize the USB peripheral. */ /* Initialize the USB peripheral. */
usb_init_usblib(USBLIB, ep_int_in, ep_int_out); usb_init_usblib(USBLIB, ep_int_in, ep_int_out);
@ -385,38 +399,45 @@ void usb_cdcacm_disable(gpio_dev *disc_dev, uint8 disc_bit) {
/* Turn off the interrupt and signal disconnect (see e.g. USB 2.0 /* Turn off the interrupt and signal disconnect (see e.g. USB 2.0
* spec, section 7.1.7.3). */ * spec, section 7.1.7.3). */
nvic_irq_disable(NVIC_USB_LP_CAN_RX0); nvic_irq_disable(NVIC_USB_LP_CAN_RX0);
if (disc_dev!=NULL)
{
gpio_write_bit(disc_dev, disc_bit, 1); gpio_write_bit(disc_dev, disc_bit, 1);
} }
}
void usb_cdcacm_putc(char ch) { void usb_cdcacm_putc(char ch) {
while (!usb_cdcacm_tx((uint8*)&ch, 1)) while (!usb_cdcacm_tx((uint8*)&ch, 1))
; ;
} }
/* This function is blocking. /* This function is non-blocking.
* *
* It copies data from a usercode buffer into the USB peripheral TX * It copies data from a user buffer into the USB peripheral TX
* buffer, and returns the number of bytes copied. */ * buffer, and returns the number of bytes copied. */
uint32 usb_cdcacm_tx(const uint8* buf, uint32 len) { uint32 usb_cdcacm_tx(const uint8* buf, uint32 len)
/* Last transmission hasn't finished, so abort. */ {
while ( usb_cdcacm_is_transmitting()>0 ) ; // wait for end of transmission if (len==0) return 0; // no data to send
/* We can only put USB_CDCACM_TX_EPSIZE bytes in the buffer. */ uint32 head = tx_head; // load volatile variable
if (len > USB_CDCACM_TX_EPSIZE) { uint32 tx_unsent = (head - tx_tail) & CDC_SERIAL_TX_BUFFER_SIZE_MASK;
len = USB_CDCACM_TX_EPSIZE;
}
/* Queue bytes for sending. */ // We can only put bytes in the buffer if there is place
if (len) { if (len > (CDC_SERIAL_TX_BUFFER_SIZE-tx_unsent-1) ) {
usb_copy_to_pma(buf, len, USB_CDCACM_TX_ADDR); len = (CDC_SERIAL_TX_BUFFER_SIZE-tx_unsent-1);
}
if (len==0) return 0; // buffer full
uint16 i;
// copy data from user buffer to USB Tx buffer
for (i=0; i<len; i++) {
vcomBufferTx[head] = buf[i];
head = (head+1) & CDC_SERIAL_TX_BUFFER_SIZE_MASK;
}
tx_head = head; // store volatile variable
if (transmitting<0) {
vcomDataTxCb(); // initiate data transmission
} }
// We still need to wait for the interrupt, even if we're sending
// zero bytes. (Sending zero-size packets is useful for flushing
// host-side buffers.)
usb_set_ep_tx_count(USB_CDCACM_TX_ENDP, len);
n_unsent_bytes = len;
transmitting = 1;
usb_set_ep_tx_stat(USB_CDCACM_TX_ENDP, USB_EP_STAT_TX_VALID);
return len; return len;
} }
@ -424,69 +445,73 @@ uint32 usb_cdcacm_tx(const uint8* buf, uint32 len) {
uint32 usb_cdcacm_data_available(void) { uint32 usb_cdcacm_data_available(void) {
return n_unread_bytes; return (rx_head - rx_tail) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
} }
uint8 usb_cdcacm_is_transmitting(void) { uint8 usb_cdcacm_is_transmitting(void) {
return transmitting; return ( transmitting>0 ? transmitting : 0);
} }
uint16 usb_cdcacm_get_pending(void) { uint16 usb_cdcacm_get_pending(void) {
return n_unsent_bytes; return (tx_head - tx_tail) & CDC_SERIAL_TX_BUFFER_SIZE_MASK;
} }
/* Nonblocking byte receive. /* Non-blocking byte receive.
* *
* Copies up to len bytes from our private data buffer (*NOT* the PMA) * Copies up to len bytes from our private data buffer (*NOT* the PMA)
* into buf and deq's the FIFO. */ * into buf and deq's the FIFO. */
uint32 usb_cdcacm_rx(uint8* buf, uint32 len) { uint32 usb_cdcacm_rx(uint8* buf, uint32 len)
{
/* Copy bytes to buffer. */ /* Copy bytes to buffer. */
uint32 n_copied = usb_cdcacm_peek(buf, len); uint32 n_copied = usb_cdcacm_peek(buf, len);
/* Mark bytes as read. */ /* Mark bytes as read. */
n_unread_bytes -= n_copied; uint16 tail = rx_tail; // load volatile variable
rx_offset = (rx_offset + n_copied) % CDC_SERIAL_BUFFER_SIZE; tail = (tail + n_copied) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
rx_tail = tail; // store volatile variable
/* If all bytes have been read, re-enable the RX endpoint, which uint32 rx_unread = (rx_head - tail) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
* was set to NAK when the current batch of bytes was received. */ // If buffer was emptied to a pre-set value, re-enable the RX endpoint
if (n_unread_bytes == 0) { if ( rx_unread <= 64 ) { // experimental value, gives the best performance
usb_set_ep_rx_count(USB_CDCACM_RX_ENDP, USB_CDCACM_RX_EPSIZE);
usb_set_ep_rx_stat(USB_CDCACM_RX_ENDP, USB_EP_STAT_RX_VALID); usb_set_ep_rx_stat(USB_CDCACM_RX_ENDP, USB_EP_STAT_RX_VALID);
} }
return n_copied; return n_copied;
} }
/* Nonblocking byte lookahead. /* Non-blocking byte lookahead.
* *
* Looks at unread bytes without marking them as read. */ * Looks at unread bytes without marking them as read. */
uint32 usb_cdcacm_peek(uint8* buf, uint32 len) { uint32 usb_cdcacm_peek(uint8* buf, uint32 len)
{
int i; int i;
uint32 head = rx_offset; uint32 tail = rx_tail;
uint32 rx_unread = (rx_head-tail) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
if (len > n_unread_bytes) { if (len > rx_unread) {
len = n_unread_bytes; len = rx_unread;
} }
for (i = 0; i < len; i++) { for (i = 0; i < len; i++) {
buf[i] = vcomBufferRx[head]; buf[i] = vcomBufferRx[tail];
head = (head + 1) % CDC_SERIAL_BUFFER_SIZE; tail = (tail + 1) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
} }
return len; return len;
} }
uint32 usb_cdcacm_peek_ex(uint8* buf, uint32 offset, uint32 len) { uint32 usb_cdcacm_peek_ex(uint8* buf, uint32 offset, uint32 len)
{
int i; int i;
uint32 head = (rx_offset + offset) % CDC_SERIAL_BUFFER_SIZE; uint32 tail = (rx_tail + offset) & CDC_SERIAL_RX_BUFFER_SIZE_MASK ;
uint32 rx_unread = (rx_head-tail) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
if (len + offset > n_unread_bytes) { if (len + offset > rx_unread) {
len = n_unread_bytes - offset; len = rx_unread - offset;
} }
for (i = 0; i < len; i++) { for (i = 0; i < len; i++) {
buf[i] = vcomBufferRx[head]; buf[i] = vcomBufferRx[tail];
head = (head + 1) % CDC_SERIAL_BUFFER_SIZE; tail = (tail + 1) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
} }
return len; return len;
@ -495,12 +520,12 @@ uint32 usb_cdcacm_peek_ex(uint8* buf, uint32 offset, uint32 len) {
/* Roger Clark. Added. for Arduino 1.0 API support of Serial.peek() */ /* Roger Clark. Added. for Arduino 1.0 API support of Serial.peek() */
int usb_cdcacm_peek_char() int usb_cdcacm_peek_char()
{ {
if (n_unread_bytes == 0) if (usb_cdcacm_data_available() == 0)
{ {
return -1; return -1;
} }
return vcomBufferRx[rx_offset]; return vcomBufferRx[rx_tail];
} }
uint8 usb_cdcacm_get_dtr() { uint8 usb_cdcacm_get_dtr() {
@ -534,39 +559,73 @@ int usb_cdcacm_get_n_data_bits(void) {
return line_coding.bDataBits; return line_coding.bDataBits;
} }
/* /*
* Callbacks * Callbacks
*/ */
static void vcomDataTxCb(void)
static void vcomDataTxCb(void) { {
n_unsent_bytes = 0; uint32 tail = tx_tail; // load volatile variable
transmitting = 0; uint32 tx_unsent = (tx_head - tail) & CDC_SERIAL_TX_BUFFER_SIZE_MASK;
if (tx_unsent==0) {
if ( (--transmitting)==0) goto flush; // no more data to send
return; // it was already flushed, keep Tx endpoint disabled
}
transmitting = 1;
// We can only send up to USB_CDCACM_TX_EPSIZE bytes in the endpoint.
if (tx_unsent > USB_CDCACM_TX_EPSIZE) {
tx_unsent = USB_CDCACM_TX_EPSIZE;
}
// copy the bytes from USB Tx buffer to PMA buffer
uint32 *dst = usb_pma_ptr(USB_CDCACM_TX_ADDR);
uint16 tmp = 0;
uint16 val;
int i;
for (i = 0; i < tx_unsent; i++) {
val = vcomBufferTx[tail];
tail = (tail + 1) & CDC_SERIAL_TX_BUFFER_SIZE_MASK;
if (i&1) {
*dst++ = tmp | (val<<8);
} else {
tmp = val;
}
}
if ( tx_unsent&1 ) {
*dst = tmp;
}
tx_tail = tail; // store volatile variable
flush:
// enable Tx endpoint
usb_set_ep_tx_count(USB_CDCACM_TX_ENDP, tx_unsent);
usb_set_ep_tx_stat(USB_CDCACM_TX_ENDP, USB_EP_STAT_TX_VALID);
} }
static void vcomDataRxCb(void) {
uint32 ep_rx_size; static void vcomDataRxCb(void)
uint32 tail = (rx_offset + n_unread_bytes) % CDC_SERIAL_BUFFER_SIZE; {
uint8 ep_rx_data[USB_CDCACM_RX_EPSIZE]; uint32 head = rx_head; // load volatile variable
uint32 ep_rx_size = usb_get_ep_rx_count(USB_CDCACM_RX_ENDP);
// This copy won't overwrite unread bytes as long as there is
// enough room in the USB Rx buffer for next packet
uint32 *src = usb_pma_ptr(USB_CDCACM_RX_ADDR);
uint16 tmp = 0;
uint8 val;
uint32 i; uint32 i;
usb_set_ep_rx_stat(USB_CDCACM_RX_ENDP, USB_EP_STAT_RX_NAK);
ep_rx_size = usb_get_ep_rx_count(USB_CDCACM_RX_ENDP);
/* This copy won't overwrite unread bytes, since we've set the RX
* endpoint to NAK, and will only set it to VALID when all bytes
* have been read. */
usb_copy_from_pma((uint8*)ep_rx_data, ep_rx_size,
USB_CDCACM_RX_ADDR);
for (i = 0; i < ep_rx_size; i++) { for (i = 0; i < ep_rx_size; i++) {
vcomBufferRx[tail] = ep_rx_data[i]; if (i&1) {
tail = (tail + 1) % CDC_SERIAL_BUFFER_SIZE; val = tmp>>8;
} else {
tmp = *src++;
val = tmp&0xFF;
} }
vcomBufferRx[head] = val;
head = (head + 1) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
}
rx_head = head; // store volatile variable
n_unread_bytes += ep_rx_size; uint32 rx_unread = (head - rx_tail) & CDC_SERIAL_RX_BUFFER_SIZE_MASK;
// only enable further Rx if there is enough room to receive one more packet
if ( n_unread_bytes == 0 ) { if ( rx_unread < (CDC_SERIAL_RX_BUFFER_SIZE-USB_CDCACM_RX_EPSIZE) ) {
usb_set_ep_rx_count(USB_CDCACM_RX_ENDP, USB_CDCACM_RX_EPSIZE);
usb_set_ep_rx_stat(USB_CDCACM_RX_ENDP, USB_EP_STAT_RX_VALID); usb_set_ep_rx_stat(USB_CDCACM_RX_ENDP, USB_EP_STAT_RX_VALID);
} }
@ -646,10 +705,11 @@ static void usbReset(void) {
SetDeviceAddress(0); SetDeviceAddress(0);
/* Reset the RX/TX state */ /* Reset the RX/TX state */
n_unread_bytes = 0; rx_head = 0;
n_unsent_bytes = 0; rx_tail = 0;
rx_offset = 0; tx_head = 0;
transmitting = 0; tx_tail = 0;
transmitting = -1;
} }
static RESULT usbDataSetup(uint8 request) { static RESULT usbDataSetup(uint8 request) {

View File

@ -29,7 +29,7 @@
/* TODO these could use some improvement; they're fairly /* TODO these could use some improvement; they're fairly
* straightforward ports of the analogous ST code. The PMA blit * straightforward ports of the analogous ST code. The PMA blit
* routines in particular are obvious targets for performance * routines in particular are obvious targets for performance
* measurement and tuning. */ * measurement and tuning.
void usb_copy_to_pma(const uint8 *buf, uint16 len, uint16 pma_offset) { void usb_copy_to_pma(const uint8 *buf, uint16 len, uint16 pma_offset) {
uint16 *dst = (uint16*)usb_pma_ptr(pma_offset); uint16 *dst = (uint16*)usb_pma_ptr(pma_offset);
@ -57,7 +57,7 @@ void usb_copy_from_pma(uint8 *buf, uint16 len, uint16 pma_offset) {
*dst = *src & 0xFF; *dst = *src & 0xFF;
} }
} }
*/
static void usb_set_ep_rx_count_common(uint32 *rxc, uint16 count) { static void usb_set_ep_rx_count_common(uint32 *rxc, uint16 count) {
uint16 nblocks; uint16 nblocks;
if (count > 62) { if (count > 62) {
@ -76,12 +76,12 @@ static void usb_set_ep_rx_count_common(uint32 *rxc, uint16 count) {
*rxc = nblocks << 10; *rxc = nblocks << 10;
} }
} }
/*
void usb_set_ep_rx_buf0_count(uint8 ep, uint16 count) { void usb_set_ep_rx_buf0_count(uint8 ep, uint16 count) {
uint32 *rxc = usb_ep_rx_buf0_count_ptr(ep); uint32 *rxc = usb_ep_rx_buf0_count_ptr(ep);
usb_set_ep_rx_count_common(rxc, count); usb_set_ep_rx_count_common(rxc, count);
} }
*/
void usb_set_ep_rx_count(uint8 ep, uint16 count) { void usb_set_ep_rx_count(uint8 ep, uint16 count) {
uint32 *rxc = usb_ep_rx_count_ptr(ep); uint32 *rxc = usb_ep_rx_count_ptr(ep);
usb_set_ep_rx_count_common(rxc, count); usb_set_ep_rx_count_common(rxc, count);

View File

@ -88,7 +88,7 @@ void _fail(const char* file, int line, const char* exp) {
* Provide an __assert_func handler to libc so that calls to assert() * Provide an __assert_func handler to libc so that calls to assert()
* get redirected to _fail. * get redirected to _fail.
*/ */
void __assert_func(const char* file, int line, const char* method, void __assert_func(const char* file, int line, const char* method __attribute__((unused)),
const char* expression) { const char* expression) {
_fail(file, line, expression); _fail(file, line, expression);
} }

View File

@ -0,0 +1,36 @@
/*
Copyright (c) 2014 Arduino. All right reserved.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#include <stdlib.h>
void *operator new(size_t size) {
return malloc(size);
}
void *operator new[](size_t size) {
return malloc(size);
}
void operator delete(void * ptr) {
free(ptr);
}
void operator delete[](void * ptr) {
free(ptr);
}

View File

@ -0,0 +1,198 @@
/******************************************************************************
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*****************************************************************************/
/**
* @file libmaple/sdio.c
* @author stevstrong
* @brief Secure digital input/output interface.
*/
#include <libmaple/sdio.h>
#include <libmaple/gpio.h>
#include <boards.h>
#include "wirish.h"
//#include <libmaple/libmaple.h>
//#include <libmaple/rcc.h>
//#include <series/gpio.h>
//#include "wirish.h"
//#include "boards.h"
//
#if defined(STM32_HIGH_DENSITY) || defined(STM32_XL_DENSITY)
sdio_dev * SDIO = SDIO_BASE;
#define DELAY_LONG 10
#define DELAY_SHORT 1
uint8_t dly = DELAY_LONG; // microseconds delay after accessing registers
/*
* SDIO convenience routines
*/
void sdio_gpios_init(void)
{
gpio_set_mode(PIN_MAP[BOARD_SDIO_D0].gpio_device, PIN_MAP[BOARD_SDIO_D0].gpio_bit, GPIO_AF_OUTPUT_PP);
gpio_set_mode(PIN_MAP[BOARD_SDIO_D1].gpio_device, PIN_MAP[BOARD_SDIO_D1].gpio_bit, GPIO_AF_OUTPUT_PP);
gpio_set_mode(PIN_MAP[BOARD_SDIO_D2].gpio_device, PIN_MAP[BOARD_SDIO_D2].gpio_bit, GPIO_AF_OUTPUT_PP);
gpio_set_mode(PIN_MAP[BOARD_SDIO_D3].gpio_device, PIN_MAP[BOARD_SDIO_D3].gpio_bit, GPIO_AF_OUTPUT_PP);
gpio_set_mode(PIN_MAP[BOARD_SDIO_CLK].gpio_device, PIN_MAP[BOARD_SDIO_CLK].gpio_bit, GPIO_AF_OUTPUT_PP);
gpio_set_mode(PIN_MAP[BOARD_SDIO_CMD].gpio_device, PIN_MAP[BOARD_SDIO_CMD].gpio_bit, GPIO_AF_OUTPUT_PP);
/*
* Todo just remove it, not needed for F1.
*/
/*
gpio_set_af_mode(BOARD_SDIO_D0, 12);
gpio_set_af_mode(BOARD_SDIO_D1, 12);
gpio_set_af_mode(BOARD_SDIO_D2, 12);
gpio_set_af_mode(BOARD_SDIO_D3, 12);
gpio_set_af_mode(BOARD_SDIO_CLK, 12);
gpio_set_af_mode(BOARD_SDIO_CMD, 12);
*/
}
void sdio_gpios_deinit(void)
{
gpio_set_mode(PIN_MAP[BOARD_SDIO_D0].gpio_device, PIN_MAP[BOARD_SDIO_D0].gpio_bit, GPIO_INPUT_FLOATING);
gpio_set_mode(PIN_MAP[BOARD_SDIO_D1].gpio_device, PIN_MAP[BOARD_SDIO_D1].gpio_bit, GPIO_INPUT_FLOATING);
gpio_set_mode(PIN_MAP[BOARD_SDIO_D2].gpio_device, PIN_MAP[BOARD_SDIO_D2].gpio_bit, GPIO_INPUT_FLOATING);
gpio_set_mode(PIN_MAP[BOARD_SDIO_D3].gpio_device, PIN_MAP[BOARD_SDIO_D3].gpio_bit, GPIO_INPUT_FLOATING);
gpio_set_mode(PIN_MAP[BOARD_SDIO_CLK].gpio_device, PIN_MAP[BOARD_SDIO_CLK].gpio_bit, GPIO_INPUT_FLOATING);
gpio_set_mode(PIN_MAP[BOARD_SDIO_CMD].gpio_device, PIN_MAP[BOARD_SDIO_CMD].gpio_bit, GPIO_INPUT_FLOATING);
/*
* Todo just remove it, not needed for F1.
*/
/*
gpio_set_af_mode(BOARD_SDIO_D0, 0);
gpio_set_af_mode(BOARD_SDIO_D1, 0);
gpio_set_af_mode(BOARD_SDIO_D2, 0);
gpio_set_af_mode(BOARD_SDIO_D3, 0);
gpio_set_af_mode(BOARD_SDIO_CLK, 0);
gpio_set_af_mode(BOARD_SDIO_CMD, 0);
*/
}
/**
* @brief Initialize and reset the SDIO device.
*/
void sdio_init(void)
{
rcc_clk_enable(RCC_SDIO);
rcc_reset_dev(RCC_SDIO);
}
void sdio_power_on(void)
{
SDIO->POWER = SDIO_POWER_PWRCTRL_ON;
// After a data write, data cannot be written to this register for three SDIOCLK clock periods
// plus two PCLK2 clock periods.
delay_us(DELAY_LONG);
}
void sdio_power_off(void)
{
SDIO->POWER = SDIO_POWER_PWRCTRL_OFF;
// After a data write, data cannot be written to this register for three SDIOCLK clock periods
// plus two PCLK2 clock periods.
delay_us(DELAY_LONG);
}
void sdio_set_clock(uint32_t clk)
{
if (clk>24000000UL) clk = 24000000UL; // limit the SDIO master clock to 24MHz
if (clk<1000000) dly = DELAY_LONG;
else dly = DELAY_SHORT;
sdio_disable();
SDIO->CLKCR = (SDIO->CLKCR & (~(SDIO_CLKCR_CLKDIV|SDIO_CLKCR_BYPASS))) | SDIO_CLKCR_CLKEN | (((SDIOCLK/clk)-2)&SDIO_CLKCR_CLKDIV);
delay_us(dly);
}
void sdio_set_dbus_width(uint16_t bus_w)
{
SDIO->CLKCR = (SDIO->CLKCR & (~SDIO_CLKCR_WIDBUS)) | bus_w;
delay_us(dly);
}
void sdio_set_dblock_size(uint8_t dbsize)
{
SDIO->DCTRL = (SDIO->DCTRL&(~SDIO_DCTRL_DBLOCKSIZE)) | ((dbsize&0xF)<<4);
delay_us(dly);
}
void sdio_enable(void)
{
SDIO->CLKCR |= SDIO_CLKCR_CLKEN;
delay_us(dly);
}
void sdio_disable(void)
{
SDIO->CLKCR ^= SDIO_CLKCR_CLKEN;
delay_us(dly);
}
/**
* @brief Configure and enable the SDIO device.
*/
void sdio_begin(void)
{
sdio_gpios_init();
sdio_init();
sdio_power_on();
// Set initial SCK rate.
sdio_set_clock(400000);
delay_us(200); // generate 80 pulses at 400kHz
}
/**
* @brief Disables the SDIO device.
*/
void sdio_end(void)
{
sdio_disable();
while ( sdio_cmd_xfer_ongoing() );
sdio_power_off();
rcc_clk_disable(RCC_SDIO);
sdio_gpios_deinit();
}
/**
* @brief Send command by the SDIO device.
*/
uint8_t sdio_cmd_send(uint16_t cmd_index_resp_type, uint32_t arg)
{
uint8_t retries = 10; // in case of errors
do { // retry command if errors detected
// clear interrupt flags - IMPORTANT!!!
SDIO->ICR = SDIO_ICR_CMD_FLAGS;
// write command
SDIO->ARG = arg;
SDIO->CMD = (uint32_t)(SDIO_CMD_CPSMEN | cmd_index_resp_type );
while ( (SDIO->STA&SDIO_STA_CMDACT) ) ; // wait for actual command transfer to finish
// wait for response, if the case
if ( cmd_index_resp_type&(SDIO_CMD_WAIT_SHORT_RESP|SDIO_CMD_WAIT_LONG_RESP) ) {
while ( !(SDIO->STA&(SDIO_STA_CMDREND|SDIO_STA_CMD_ERROR_FLAGS)) ) ;
} else break; // no response required
if ( SDIO->STA&(SDIO_STA_CMDREND|SDIO_STA_CTIMEOUT) )
break; // response received or timeout
// ignore CRC error for CMD5 and ACMD41
if ( ((cmd_index_resp_type&SDIO_CMD_CMDINDEX)==5) || ((cmd_index_resp_type&SDIO_CMD_CMDINDEX)==41) )
break;
} while ( (--retries) );
return (uint8_t)retries;
}
#endif // defined(STM32_HIGH_DENSITY) || defined(STM32_XL_DENSITY)

View File

@ -1,5 +1,6 @@
#include <wiring_pulse.h> #include <wiring_pulse.h>
#include "boards.h" #include "boards.h"
#include "variant.h"
/* Measures the length (in microseconds) of a pulse on the pin; state is HIGH /* Measures the length (in microseconds) of a pulse on the pin; state is HIGH
* or LOW, the type of pulse to measure. Works on pulses from 2-3 microseconds * or LOW, the type of pulse to measure. Works on pulses from 2-3 microseconds
* to 3 minutes in length, but must be called at least a few dozen microseconds * to 3 minutes in length, but must be called at least a few dozen microseconds
@ -28,13 +29,13 @@
*/ */
uint32_t pulseIn( uint32_t pin, uint32_t state, uint32_t timeout ) uint32_t pulseIn( uint32_t pin, uint32_t state, uint32_t timeout )
{ {
// cache the port and bit of the pin in order to speed up the // cache the IDR address and bit of the pin in order to speed up the
// pulse width measuring loop and achieve finer resolution. calling // pulse width measuring loop and achieve finer resolution. calling
// digitalRead() instead yields much coarser resolution. // digitalRead() instead yields much coarser resolution.
gpio_dev *dev=PIN_MAP[pin].gpio_device; __io uint32_t * const idr = portInputRegister(digitalPinToPort(pin));
uint32_t bit = (1U << PIN_MAP[pin].gpio_bit); const uint32_t bit = digitalPinToBitMask(pin);
const uint32_t stateMask = (state ? bit:0);
uint32_t width = 0; // keep initialization out of time critical area uint32_t width = 0; // keep initialization out of time critical area
@ -45,7 +46,7 @@ uint32_t pulseIn( uint32_t pin, uint32_t state, uint32_t timeout )
volatile uint32_t dummyWidth=0; volatile uint32_t dummyWidth=0;
// wait for any previous pulse to end // wait for any previous pulse to end
while ( (dev->regs->IDR & bit) == bit) { while ((*idr & bit) == stateMask) {
if (numloops++ == maxloops) { if (numloops++ == maxloops) {
return 0; return 0;
} }
@ -53,7 +54,7 @@ uint32_t pulseIn( uint32_t pin, uint32_t state, uint32_t timeout )
} }
// wait for the pulse to start // wait for the pulse to start
while ((dev->regs->IDR & bit) != bit) { while ((*idr & bit) != stateMask) {
if (numloops++ == maxloops) { if (numloops++ == maxloops) {
return 0; return 0;
} }
@ -61,7 +62,7 @@ uint32_t pulseIn( uint32_t pin, uint32_t state, uint32_t timeout )
} }
// wait for the pulse to stop // wait for the pulse to stop
while ((dev->regs->IDR & bit) == bit) { while ((*idr & bit) == stateMask) {
if (numloops++ == maxloops) { if (numloops++ == maxloops) {
return 0; return 0;
} }

View File

@ -80,10 +80,13 @@ void pinMode(uint8 pin, WiringPinMode mode) {
gpio_set_mode(PIN_MAP[pin].gpio_device, PIN_MAP[pin].gpio_bit, outputMode); gpio_set_mode(PIN_MAP[pin].gpio_device, PIN_MAP[pin].gpio_bit, outputMode);
if (PIN_MAP[pin].timer_device != NULL) { if (PIN_MAP[pin].timer_device != NULL) {
/* Enable/disable timer channels if we're switching into or if ( pwm ) { // we're switching into PWM, enable timer channels
* out of PWM. */
timer_set_mode(PIN_MAP[pin].timer_device, timer_set_mode(PIN_MAP[pin].timer_device,
PIN_MAP[pin].timer_channel, PIN_MAP[pin].timer_channel,
pwm ? TIMER_PWM : TIMER_DISABLED); TIMER_PWM );
} else { // disable channel output in non pwm-Mode
timer_cc_disable(PIN_MAP[pin].timer_device,
PIN_MAP[pin].timer_channel);
}
} }
} }

View File

@ -0,0 +1,205 @@
///////////////////////////////////////////////////////////////////////
//
// tone(pin,frequency[,duration]) generate a tone on a given pin
//
// noTone(pin) switch off the tone on the pin
//
// setToneTimerChannel(timer,channel) force use of given timer/channel
//
///////////////////////////////////////////////////////////////////////
#include "Arduino.h"
#include <HardwareTimer.h>
#define PinTimer(pin) (PIN_MAP[pin].timer_device->clk_id-RCC_TIMER1+1)
#define PinChannel(pin) (PIN_MAP[pin].timer_channel)
// if USE_PIN_TIMER is set, the PWM timer/channel is used for PWM pins
#define USE_PIN_TIMER
// if USE_BSRR is set the tone pin will be written via the fast BSRR register
// instead of using the slow digitalWrite() function in the interrupt handler
#define USE_BSRR
// construct static timer array (
#ifdef STM32_HIGH_DENSITY
// define default timer and channel
#ifndef TONE_TIMER
#define TONE_TIMER 8
#endif
#ifndef TONE_CHANNEL
#define TONE_CHANNEL 8
#endif
HardwareTimer TTimer1(1), TTimer2(2), TTimer3(3), TTimer4(4),TTimer5(5), TTimer6(6), TTimer7(7), TTimer8(8);
HardwareTimer *TTimer[8] = { &TTimer1,&TTimer2,&TTimer3,&TTimer4,&TTimer5,&TTimer6,&TTimer7,&TTimer8 };
#else
// define default timer and channel
#ifndef TONE_TIMER
#define TONE_TIMER 4
#endif
#ifndef TONE_CHANNEL
#define TONE_CHANNEL 4
#endif
HardwareTimer TTimer1(1), TTimer2(2), TTimer3(3), TTimer4(4);
HardwareTimer *TTimer[4] = { &TTimer1,&TTimer2,&TTimer3,&TTimer4 };
#endif
uint8_t tone_force_channel = 0; // forced timer channel
uint8_t tone_force_ntimer = 0; // forced timer
HardwareTimer *tone_timer;// = TTimer[TONE_TIMER-1]; // timer used to generate frequency
uint8_t tone_channel = TONE_CHANNEL; // timer channel used to generate frequency
uint8_t tone_ntimer = TONE_TIMER; // timer used to generate frequency
bool tone_state = true; // last pin state for toggling
short tone_pin = -1; // pin for outputting sound
short tone_freq = 444; // tone frequency (0=pause)
volatile uint32_t tone_nhw = 0; // tone duration in number of half waves
uint16_t tone_tcount = 0; // time between handler calls in 1/36 usec
uint16_t tone_ncount = 0; // handler call between toggling
uint16_t tone_n = 0; // remaining handler calls before toggling
uint32_t tone_next = 0; // counter value of next interrupt
#ifdef USE_BSRR
volatile uint32_t *tone_bsrr; // BSRR set register (lower 16 bits)
uint32_t tone_smask=0; // BSRR set bitmask
uint32_t tone_rmask=0; // BSRR reset bitmask
#endif
////////////////////////////////////////////////////////////////////////////////
// timer hander for tone with no duration specified,
// will keep going until noTone() is called
void tone_handler_1(void) {
tone_next += tone_tcount; // comparator value for next interrupt
tone_timer->setCompare(tone_channel, tone_next); // and install it
if(--tone_n == 0){
tone_state = !tone_state; // toggle tone output
#ifdef USE_BSRR
if(tone_state)
*tone_bsrr = tone_smask;
else
*tone_bsrr = tone_rmask;
#else
digitalWrite(tone_pin,tone_state);// and output it
#endif
tone_n = tone_ncount; // reset interrupt counter
}
}
////////////////////////////////////////////////////////////////////////////////
// timer hander for tone with a specified duration,
// will stop automatically when duration time is up.
void tone_handler_2(void) {
tone_next += tone_tcount;
tone_timer->setCompare(tone_channel, tone_next);
if(--tone_n == 0){
if(tone_freq>0){ // toggle pin
tone_state = !tone_state;
#ifdef USE_BSRR
if(tone_state)
*tone_bsrr = tone_smask;
else
*tone_bsrr = tone_rmask;
#else
digitalWrite(tone_pin,tone_state);// and output it
#endif
}
tone_n = tone_ncount;
if(!--tone_nhw){ // check if tone duration has finished
tone_timer->pause(); // disable timer
pinMode(tone_pin, INPUT); // disable tone pin
}
}
}
////////////////////////////////////////////////////////////////////////////////
// play a tone on given pin with given frequency and optional duration in msec
void tone(uint32_t pin, uint32_t freq, uint32_t duration) {
tone_pin = pin;
#ifdef USE_PIN_TIMER
// if the pin has a PWM timer/channel, use it (unless the timer/channel are forced)
if(PinChannel(tone_pin) && !tone_force_channel){
tone_channel = PinChannel(tone_pin);
tone_ntimer = PinTimer(tone_pin);
} else
#endif
{
// set timer and channel to default resp values forced with setToneTimerChannel
tone_ntimer = tone_force_channel?tone_force_ntimer:TONE_TIMER;
tone_channel = tone_force_channel?tone_force_channel:TONE_CHANNEL;
}
tone_timer = TTimer[tone_ntimer-1];
tone_freq = freq;
tone_nhw = 0;
tone_next = 0;
tone_timer->pause();
if(freq > 0){
uint32_t count = (F_CPU/4)/freq; // timer counts per half wave
tone_ncount = tone_n = (count>>16)+1; // number of 16-bit count chunk
tone_tcount = count/tone_ncount; // size of count chunk
if(duration > 0) // number of half waves to be generated
tone_nhw = ((duration*freq)/1000)<<1;
else // no duration specified, continuous sound until noTone() called
tone_nhw = 0;
pinMode(tone_pin, PWM); // configure output pin
pinMode(tone_pin, OUTPUT); // configure output pin
#ifdef USE_BSRR
// Set up BSRR register values for fast ISR
tone_bsrr = &((PIN_MAP[tone_pin].gpio_device)->regs->BSRR);
tone_smask = (BIT(PIN_MAP[tone_pin].gpio_bit));
tone_rmask = tone_smask<<16;
#endif
// Set up an interrupt on given timer and channel
tone_next = tone_tcount; // prepare channel compare register
tone_timer->setMode(tone_channel,TIMER_OUTPUT_COMPARE);
tone_timer->setCompare(tone_channel,tone_next);
// attach corresponding handler routine
tone_timer->attachInterrupt(tone_channel,tone_nhw?tone_handler_2:tone_handler_1);
// Refresh the tone timer
tone_timer->refresh();
// Start the timer counting
tone_timer->resume();
} else {
// detach handler routine
tone_timer->detachInterrupt(tone_channel);
// disactive pin by configuring it as input
pinMode(tone_pin, INPUT);
}
//while(tone_nhw) ; // blocks till duration elapsed
}
////////////////////////////////////////////////////////////////////////////////
// disable tone on specified pin, if any
void noTone(uint32_t pin){
tone(pin,0,0); // it's all handled in tone()
}
////////////////////////////////////////////////////////////////////////////////
// set timer and channel to some different value
// must be called before calling tone() or after noTone() was called
void setToneTimerChannel(uint8_t ntimer, uint8_t channel){
tone_force_ntimer = ntimer;
tone_force_channel = channel;
}

View File

@ -0,0 +1,28 @@
/*
Copyright (c) 2015 Arduino LLC. All right reserved.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Lesser General Public
License as published by the Free Software Foundation; either
version 2.1 of the License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
See the GNU Lesser General Public License for more details.
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*/
#pragma once
#ifdef __cplusplus
#include "Arduino.h"
void tone(uint32_t _pin, uint32_t frequency, uint32_t duration = 0);
void noTone(uint32_t _pin);
#endif

View File

@ -54,6 +54,9 @@ static void ifaceSetupHook(unsigned, void*);
*/ */
#define USB_TIMEOUT 50 #define USB_TIMEOUT 50
#if BOARD_HAVE_SERIALUSB
bool USBSerial::_hasBegun = false;
#endif
USBSerial::USBSerial(void) { USBSerial::USBSerial(void) {
#if !BOARD_HAVE_SERIALUSB #if !BOARD_HAVE_SERIALUSB
@ -62,8 +65,13 @@ USBSerial::USBSerial(void) {
} }
void USBSerial::begin(void) { void USBSerial::begin(void) {
#if BOARD_HAVE_SERIALUSB #if BOARD_HAVE_SERIALUSB
usb_cdcacm_enable(BOARD_USB_DISC_DEV, BOARD_USB_DISC_BIT); if (_hasBegun)
return;
_hasBegun = true;
usb_cdcacm_enable(BOARD_USB_DISC_DEV, (uint8_t)BOARD_USB_DISC_BIT);
usb_cdcacm_set_hooks(USB_CDCACM_HOOK_RX, rxHook); usb_cdcacm_set_hooks(USB_CDCACM_HOOK_RX, rxHook);
usb_cdcacm_set_hooks(USB_CDCACM_HOOK_IFACE_SETUP, ifaceSetupHook); usb_cdcacm_set_hooks(USB_CDCACM_HOOK_IFACE_SETUP, ifaceSetupHook);
#endif #endif
@ -75,6 +83,7 @@ void USBSerial::begin(unsigned long ignoreBaud)
volatile unsigned long removeCompilerWarningsIgnoreBaud=ignoreBaud; volatile unsigned long removeCompilerWarningsIgnoreBaud=ignoreBaud;
ignoreBaud=removeCompilerWarningsIgnoreBaud; ignoreBaud=removeCompilerWarningsIgnoreBaud;
begin();
} }
void USBSerial::begin(unsigned long ignoreBaud, uint8_t ignore) void USBSerial::begin(unsigned long ignoreBaud, uint8_t ignore)
{ {
@ -83,13 +92,16 @@ volatile uint8_t removeCompilerWarningsIgnore=ignore;
ignoreBaud=removeCompilerWarningsIgnoreBaud; ignoreBaud=removeCompilerWarningsIgnoreBaud;
ignore=removeCompilerWarningsIgnore; ignore=removeCompilerWarningsIgnore;
begin();
} }
void USBSerial::end(void) { void USBSerial::end(void) {
#if BOARD_HAVE_SERIALUSB #if BOARD_HAVE_SERIALUSB
usb_cdcacm_disable(BOARD_USB_DISC_DEV, BOARD_USB_DISC_BIT); usb_cdcacm_disable(BOARD_USB_DISC_DEV, (uint8_t)BOARD_USB_DISC_BIT);
usb_cdcacm_remove_hooks(USB_CDCACM_HOOK_RX | USB_CDCACM_HOOK_IFACE_SETUP); usb_cdcacm_remove_hooks(USB_CDCACM_HOOK_RX | USB_CDCACM_HOOK_IFACE_SETUP);
_hasBegun = false;
#endif #endif
} }
size_t USBSerial::write(uint8 ch) { size_t USBSerial::write(uint8 ch) {
@ -100,43 +112,22 @@ size_t n = 0;
size_t USBSerial::write(const char *str) { size_t USBSerial::write(const char *str) {
size_t n = 0; size_t n = 0;
this->write(str, strlen(str)); this->write((const uint8*)str, strlen(str));
return n; return n;
} }
size_t USBSerial::write(const void *buf, uint32 len) { size_t USBSerial::write(const uint8 *buf, uint32 len)
{
size_t n = 0; size_t n = 0;
if (!this->isConnected() || !buf) { if (!(bool) *this || !buf) {
return 0; return 0;
} }
uint32 txed = 0; uint32 txed = 0;
uint32 old_txed = 0; while (txed < len) {
uint32 start = millis(); txed += usb_cdcacm_tx((const uint8*)buf + txed, len - txed);
uint32 sent = 0;
while (txed < len && (millis() - start < USB_TIMEOUT)) {
sent = usb_cdcacm_tx((const uint8*)buf + txed, len - txed);
txed += sent;
if (old_txed != txed) {
start = millis();
}
old_txed = txed;
} }
#if 0
// this code leads to a serious performance drop and appears to be
// unnecessary - everything seems to work fine without, -jcw, 2015-11-05
// see http://stm32duino.com/posting.php?mode=quote&f=3&p=7746
if (sent == USB_CDCACM_TX_EPSIZE) {
while (usb_cdcacm_is_transmitting() != 0) {
}
/* flush out to avoid having the pc wait for more data */
usb_cdcacm_tx(NULL, 0);
}
#endif
return n; return n;
} }
@ -168,19 +159,28 @@ void USBSerial::flush(void)
return; return;
} }
uint32 USBSerial::read(void *buf, uint32 len) { uint32 USBSerial::read(uint8 * buf, uint32 len) {
if (!buf) {
return 0;
}
uint32 rxed = 0; uint32 rxed = 0;
while (rxed < len) { while (rxed < len) {
rxed += usb_cdcacm_rx((uint8*)buf + rxed, len - rxed); rxed += usb_cdcacm_rx(buf + rxed, len - rxed);
} }
return rxed; return rxed;
} }
size_t USBSerial::readBytes(char *buf, const size_t& len)
{
size_t rxed=0;
unsigned long startMillis;
startMillis = millis();
if (len <= 0) return 0;
do {
rxed += usb_cdcacm_rx((uint8 *)buf + rxed, len - rxed);
if (rxed == len) return rxed;
} while(millis() - startMillis < _timeout);
return rxed;
}
/* Blocks forever until 1 byte is received */ /* Blocks forever until 1 byte is received */
int USBSerial::read(void) { int USBSerial::read(void) {
uint8 b; uint8 b;
@ -203,10 +203,6 @@ uint8 USBSerial::pending(void) {
return usb_cdcacm_get_pending(); return usb_cdcacm_get_pending();
} }
uint8 USBSerial::isConnected(void) {
return usb_is_connected(USBLIB) && usb_is_configured(USBLIB) && usb_cdcacm_get_dtr();
}
uint8 USBSerial::getDTR(void) { uint8 USBSerial::getDTR(void) {
return usb_cdcacm_get_dtr(); return usb_cdcacm_get_dtr();
} }
@ -215,6 +211,10 @@ uint8 USBSerial::getRTS(void) {
return usb_cdcacm_get_rts(); return usb_cdcacm_get_rts();
} }
USBSerial::operator bool() {
return usb_is_connected(USBLIB) && usb_is_configured(USBLIB) && usb_cdcacm_get_dtr();
}
#if BOARD_HAVE_SERIALUSB #if BOARD_HAVE_SERIALUSB
#ifdef SERIAL_USB #ifdef SERIAL_USB
USBSerial Serial; USBSerial Serial;
@ -236,7 +236,7 @@ enum reset_state_t {
static reset_state_t reset_state = DTR_UNSET; static reset_state_t reset_state = DTR_UNSET;
static void ifaceSetupHook(unsigned hook, void *requestvp) { static void ifaceSetupHook(unsigned hook __attribute__((unused)), void *requestvp) {
uint8 request = *(uint8*)requestvp; uint8 request = *(uint8*)requestvp;
// Ignore requests we're not interested in. // Ignore requests we're not interested in.
@ -290,7 +290,7 @@ static void wait_reset(void) {
#define STACK_TOP 0x20000800 #define STACK_TOP 0x20000800
#define EXC_RETURN 0xFFFFFFF9 #define EXC_RETURN 0xFFFFFFF9
#define DEFAULT_CPSR 0x61000000 #define DEFAULT_CPSR 0x61000000
static void rxHook(unsigned hook, void *ignored) { static void rxHook(unsigned hook __attribute__((unused)), void *ignored __attribute__((unused))) {
/* FIXME this is mad buggy; we need a new reset sequence. E.g. NAK /* FIXME this is mad buggy; we need a new reset sequence. E.g. NAK
* after each RX means you can't reset if any bytes are waiting. */ * after each RX means you can't reset if any bytes are waiting. */
if (reset_state == DTR_NEGEDGE) { if (reset_state == DTR_NEGEDGE) {

View File

@ -49,11 +49,10 @@ public:
void begin(unsigned long, uint8_t); void begin(unsigned long, uint8_t);
void end(void); void end(void);
operator bool() { return true; } // Roger Clark. This is needed because in cardinfo.ino it does if (!Serial) . It seems to be a work around for the Leonardo that we needed to implement just to be compliant with the API
virtual int available(void);// Changed to virtual virtual int available(void);// Changed to virtual
uint32 read(void *buf, uint32 len); size_t readBytes(char *buf, const size_t& len);
uint32 read(uint8 * buf, uint32 len);
// uint8 read(void); // uint8 read(void);
// Roger Clark. added functions to support Arduino 1.0 API // Roger Clark. added functions to support Arduino 1.0 API
@ -65,12 +64,27 @@ public:
size_t write(uint8); size_t write(uint8);
size_t write(const char *str); size_t write(const char *str);
size_t write(const void*, uint32); size_t write(const uint8*, uint32);
uint8 getRTS(); uint8 getRTS();
uint8 getDTR(); uint8 getDTR();
uint8 isConnected();
uint8 pending(); uint8 pending();
/* SukkoPera: This is the Arduino way to check if an USB CDC serial
* connection is open.
* Used for instance in cardinfo.ino.
*/
operator bool();
/* Old libmaple way to check for serial connection.
*
* Deprecated, use the above.
*/
uint8 isConnected() __attribute__((deprecated("Use !Serial instead"))) { return (bool) *this; }
protected:
static bool _hasBegun;
}; };
#ifdef SERIAL_USB #ifdef SERIAL_USB
@ -78,4 +92,3 @@ public:
#endif #endif
#endif #endif

Some files were not shown because too many files have changed in this diff Show More