diff options
24 files changed, 1107 insertions, 181 deletions
diff --git a/apps/ChangeLog.txt b/apps/ChangeLog.txt index 1ca261df6..f79305d47 100755 --- a/apps/ChangeLog.txt +++ b/apps/ChangeLog.txt @@ -188,3 +188,5 @@ dump the system log if CONFIG_SYSLOG is selected. 6.16 2012-xx-xx Gregory Nutt <gnutt@nuttx.org> + + * apps/examples/qencoder: Add a quadrature driver test. diff --git a/apps/examples/Makefile b/apps/examples/Makefile index eea75083c..d6ac49163 100644 --- a/apps/examples/Makefile +++ b/apps/examples/Makefile @@ -39,9 +39,9 @@ SUBDIRS = adc buttons can composite dhcpd ftpc ftpd hello helloxx hidkbd \ igmp lcdrw mm mount nettest nsh null nx nxffs nxflat nxhello nximage \ - nxlines nxtext ostest pashello pipe poll pwm rgmp romfs sendmail \ + nxlines nxtext ostest pashello pipe poll pwm qencoder rgmp romfs \ serloop telnetd thttpd tiff touchscreen udp uip usbserial \ - usbstorage usbterm wget wlan + sendmail usbstorage usbterm wget wlan # Sub-directories that might need context setup. Directories may need # context setup for a variety of reasons, but the most common is because @@ -56,7 +56,7 @@ SUBDIRS = adc buttons can composite dhcpd ftpc ftpd hello helloxx hidkbd \ CNTXTDIRS = pwm ifeq ($(CONFIG_NSH_BUILTIN_APPS),y) -CNTXTDIRS += adc can composite ftpd dhcpd nettest telnetd +CNTXTDIRS += adc can composite ftpd dhcpd nettest qencoder telnetd endif ifeq ($(CONFIG_EXAMPLES_HELLOXX_BUILTIN),y) diff --git a/apps/examples/README.txt b/apps/examples/README.txt index d598180e5..eeb05562d 100644 --- a/apps/examples/README.txt +++ b/apps/examples/README.txt @@ -906,6 +906,33 @@ examples/pwm only available if CONFIG_PWM_PULSECOUNT is defined. Default: 0 (i.e., use the duration, not the count). +examples/qencoder +^^^^^^^^^^^^^^^^^ + + This example is a simple test of a Quadrature Encoder driver. It simply reads + positional data from the encoder and prints it., + + This test depends on these specific QE/NSH configurations settings (your + specific PWM settings might require additional settings). + + CONFIG_QENCODER - Enables quadrature encoder support (upper-half driver). + CONFIG_NSH_BUILTIN_APPS - Build the QE test as an NSH built-in function. + Default: Built as a standalone progrem. + + Additional configuration options will mostly likely be required for the board- + specific lower-half driver. See the README.txt file in your board configuration + directory. + + Specific configuration options for this example include: + + CONFIG_EXAMPLES_QENCODER_DEVPATH - The path to the QE device. Default: + /dev/qe0 + CONFIG_EXAMPLES_QENCODER_NSAMPLES - If CONFIG_NSH_BUILTIN_APPS + is defined, then the number of samples is provided on the command line + and this value is ignored. Otherwise, this number of samples is + collected and the program terminates. Default: Samples are collected + indefinitely. + examples/rgmp ^^^^^^^^^^^^^ diff --git a/apps/examples/qencoder/Makefile b/apps/examples/qencoder/Makefile new file mode 100644 index 000000000..3f3fc9def --- /dev/null +++ b/apps/examples/qencoder/Makefile @@ -0,0 +1,105 @@ +############################################################################ +# apps/examples/qe/Makefile +# +# Copyright (C) 2012 Gregory Nutt. All rights reserved. +# Author: Gregory Nutt <gnutt@nuttx.org> +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in +# the documentation and/or other materials provided with the +# distribution. +# 3. Neither the name NuttX nor the names of its contributors may be +# used to endorse or promote products derived from this software +# without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS +# FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE +# COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, +# INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, +# BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS +# OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED +# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN +# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +# POSSIBILITY OF SUCH DAMAGE. +# +############################################################################ + +-include $(TOPDIR)/.config +-include $(TOPDIR)/Make.defs +include $(APPDIR)/Make.defs + +# NuttX NX Graphics Example. + +ASRCS = +CSRCS = qe_main.c + +AOBJS = $(ASRCS:.S=$(OBJEXT)) +COBJS = $(CSRCS:.c=$(OBJEXT)) + +SRCS = $(ASRCS) $(CSRCS) +OBJS = $(AOBJS) $(COBJS) + +ifeq ($(WINTOOL),y) + BIN = "${shell cygpath -w $(APPDIR)/libapps$(LIBEXT)}" +else + BIN = "$(APPDIR)/libapps$(LIBEXT)" +endif + +ROOTDEPPATH = --dep-path . + +# Quadrature Encoder built-in application info + +APPNAME = qe +PRIORITY = SCHED_PRIORITY_DEFAULT +STACKSIZE = 2048 + +# Common build + +VPATH = + +all: .built +.PHONY: context clean depend distclean + +$(AOBJS): %$(OBJEXT): %.S + $(call ASSEMBLE, $<, $@) + +$(COBJS): %$(OBJEXT): %.c + $(call COMPILE, $<, $@) + +.built: $(OBJS) + @( for obj in $(OBJS) ; do \ + $(call ARCHIVE, $(BIN), $${obj}); \ + done ; ) + @touch .built + +.context: +ifeq ($(CONFIG_NSH_BUILTIN_APPS),y) + $(call REGISTER,$(APPNAME),$(PRIORITY),$(STACKSIZE),$(APPNAME)_main) + @touch $@ +endif + +context: .context + +.depend: Makefile $(SRCS) + @$(MKDEP) $(ROOTDEPPATH) $(CC) -- $(CFLAGS) -- $(SRCS) >Make.dep + @touch $@ + +depend: .depend + +clean: + @rm -f *.o *~ .*.swp .built + $(call CLEAN) + +distclean: clean + @rm -f Make.dep .depend + +-include Make.dep diff --git a/apps/examples/qencoder/qe.h b/apps/examples/qencoder/qe.h new file mode 100644 index 000000000..8b9035604 --- /dev/null +++ b/apps/examples/qencoder/qe.h @@ -0,0 +1,123 @@ +/**************************************************************************** + * examples/examples/qe/qe.h + * + * Copyright (C) 2011 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ****************************************************************************/ + +#ifndef __APPS_EXAMPLES_QENCODER_QE_H +#define __APPS_EXAMPLES_QENCODER_QE_H + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include <nuttx/config.h> + +/**************************************************************************** + * Definitions + ****************************************************************************/ +/* Configuration ************************************************************/ +/* CONFIG_NSH_BUILTIN_APPS - Build the QE test as an NSH built-in function. + * Default: Built as a standalone problem + * CONFIG_EXAMPLES_QENCODER_DEVPATH - The path to the QE device. Default: + * /dev/qe0 + * CONFIG_EXAMPLES_QENCODER_NSAMPLES - If CONFIG_NSH_BUILTIN_APPS + * is defined, then the number of samples is provided on the command line + * and this value is ignored. Otherwise, this number of samples is + * collected and the program terminates. Default: Samples are collected + * indefinitely. + */ + +#ifndef CONFIG_QENCODER +# error "QE device support is not enabled (CONFIG_QENCODER)" +#endif + +#ifndef CONFIG_EXAMPLES_QENCODER_DEVPATH +# define CONFIG_EXAMPLES_QENCODER_DEVPATH "/dev/qe0" +#endif + +/* Debug ********************************************************************/ + +#ifdef CONFIG_CPP_HAVE_VARARGS +# ifdef CONFIG_DEBUG +# define message(...) lib_rawprintf(__VA_ARGS__) +# define msgflush() +# else +# define message(...) printf(__VA_ARGS__) +# define msgflush() fflush(stdout) +# endif +#else +# ifdef CONFIG_DEBUG +# define message lib_rawprintf +# define msgflush() +# else +# define message printf +# define msgflush() fflush(stdout) +# endif +#endif + +/**************************************************************************** + * Public Types + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +struct qe_example_s +{ + bool reset; + int nloops; +}; +#endif + +/**************************************************************************** + * Public Variables + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +extern struct qe_example_s g_qeexample; +#endif + +/**************************************************************************** + * Public Function Prototypes + ****************************************************************************/ + +/**************************************************************************** + * Name: qe_devinit() + * + * Description: + * Perform architecuture-specific initialization of the QE hardware. This + * interface must be provided by all configurations using apps/examples/qe + * + ****************************************************************************/ + +int qe_devinit(void); + +#endif /* __APPS_EXAMPLES_QENCODER_QE_H */ diff --git a/apps/examples/qencoder/qe_main.c b/apps/examples/qencoder/qe_main.c new file mode 100644 index 000000000..c9a4d30e6 --- /dev/null +++ b/apps/examples/qencoder/qe_main.c @@ -0,0 +1,310 @@ +/**************************************************************************** + * examples/qe/qe_main.c + * + * Copyright (C) 2012 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ****************************************************************************/ + +/**************************************************************************** + * Included Files + ****************************************************************************/ + +#include <nuttx/config.h> + +#include <sys/types.h> +#include <sys/ioctl.h> + +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <fcntl.h> +#include <limits.h> +#include <errno.h> +#include <debug.h> + +#include <nuttx/sensors/qencoder.h> + +#include "qe.h" + +/**************************************************************************** + * Pre-processor Definitions + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +# define MAIN_NAME qe_main +# define MAIN_STRING "qe_main: " +#else +# define MAIN_NAME user_start +# define MAIN_STRING "user_start: " +#endif + +/**************************************************************************** + * Private Types + ****************************************************************************/ + +/**************************************************************************** + * Private Function Prototypes + ****************************************************************************/ + +/**************************************************************************** + * Private Data + ****************************************************************************/ + +/**************************************************************************** + * Public Data + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +struct qe_example_s g_qeexample; +#endif + +/**************************************************************************** + * Private Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: qe_help + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +static void qe_help(void) +{ + message("\nUsage: qe [OPTIONS]\n\n"); + message("OPTIONS include:\n"); + message(" [-n samples] number of samples\n"); + message(" [-r] reset the count\n"); + message(" [-h] shows this message and exits\n\n"); +} +#endif + +/**************************************************************************** + * Name: arg_string + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +int arg_string(FAR char **arg, FAR char **value) +{ + FAR char *ptr = *arg; + + if (ptr[2] == '\0') + { + *value = arg[1]; + return 2; + } + else + { + *value = &ptr[2]; + return 1; + } +} +#endif + +/**************************************************************************** + * Name: arg_decimal + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +int arg_decimal(FAR char **arg, FAR long *value) +{ + FAR char *string; + int ret; + + ret = arg_string(arg, &string); + *value = strtol(string, NULL, 10); + return ret; +} +#endif + +/**************************************************************************** + * Name: parse_args + ****************************************************************************/ + +#ifdef CONFIG_NSH_BUILTIN_APPS +void parse_args(int argc, FAR char **argv) +{ + FAR char *ptr; + long value; + int index; + int nargs; + + g_qeexample.reset = false; + g_qeexample.nloops = 1; + + for (index = 1; index < argc; ) + { + ptr = argv[index]; + if (ptr[0] != '-') + { + message("Invalid options format: %s\n", ptr); + exit(0); + } + + switch (ptr[1]) + { + case 'n': + nargs = arg_decimal(&argv[index], &value); + if (value < 0 || value > INT_MAX) + { + message("Sample count out of range: %ld\n", value); + exit(1); + } + + g_qeexample.nloops = (int)value; + index += nargs; + break; + + case 'r': + g_qeexample.reset = true; + index++; + break; + + case 'h': + qe_help(); + exit(EXIT_SUCCESS); + + default: + message("Unsupported option: %s\n", ptr); + qe_help(); + exit(EXIT_FAILURE); + } + } +} +#endif + +/**************************************************************************** + * Public Functions + ****************************************************************************/ + +/**************************************************************************** + * Name: user_start/qe_main + ****************************************************************************/ + +int MAIN_NAME(int argc, char *argv[]) +{ + int32_t position; + int fd; + int exitval = EXIT_SUCCESS; + int ret; +#if defined(CONFIG_NSH_BUILTIN_APPS) || defined(CONFIG_EXAMPLES_QENCODER_NSAMPLES) + int nloops; +#endif + + /* Parse command line arguments */ + +#ifdef CONFIG_NSH_BUILTIN_APPS + parse_args(argc, argv); +#endif + + /* Initialization of the encoder hardware is performed by logic external to + * this test. + */ + + message(MAIN_STRING "Initializing external encoder\n"); + ret = qe_devinit(); + if (ret != OK) + { + message(MAIN_STRING "qe_devinit failed: %d\n", ret); + exitval = EXIT_FAILURE; + goto errout; + } + + /* Open the encoder device for reading */ + + message(MAIN_STRING "Hardware initialized. Opening the encoder device\n"); + fd = open(CONFIG_EXAMPLES_QENCODER_DEVPATH, O_RDONLY); + if (fd < 0) + { + message(MAIN_STRING "open %s failed: %d\n", + CONFIG_EXAMPLES_QENCODER_DEVPATH, errno); + exitval = EXIT_FAILURE; + goto errout_with_dev; + } + + /* Reset the count if so requested */ + + if (g_qeexample.reset) + { + message(MAIN_STRING "Resetting the count...\n"); + ret = ioctl(fd, QEIOC_RESET, 0); + if (ret < 0) + { + message(MAIN_STRING "ioctl(QEIOC_RESET) failed: %d\n", errno); + exitval = EXIT_FAILURE; + goto errout_with_dev; + } + } + + /* Now loop the appropriate number of times, displaying the collected + * encoder samples. + */ + +#if defined(CONFIG_NSH_BUILTIN_APPS) + message(MAIN_STRING "Number of samples: %d\n", g_qeexample.nloops); + for (nloops = 0; nloops < g_qeexample.nloops; nloops++) +#elif defined(CONFIG_EXAMPLES_QENCODER_NSAMPLES) + message(MAIN_STRING "Number of samples: %d\n", CONFIG_EXAMPLES_QENCODER_NSAMPLES); + for (nloops = 0; nloops < CONFIG_EXAMPLES_QENCODER_NSAMPLES; nloops++) +#else + for (;;) +#endif + { + /* Flush any output before the loop entered or from the previous pass + * through the loop. + */ + + msgflush(); + + /* Get the positions data using the ioctl */ + + ret = ioctl(fd, QEIOC_POSITION, (unsigned long)((uintptr_t)&position)); + if (ret < 0) + { + message(MAIN_STRING "ioctl(QEIOC_POSITION) failed: %d\n", errno); + exitval = EXIT_FAILURE; + goto errout_with_dev; + } + + /* Print the sample data on successful return */ + + else + { + message(MAIN_STRING " %d\n", position); + } + } + +errout_with_dev: + close(fd); + +errout: + message("Terminating!\n"); + msgflush(); + return exitval; +} diff --git a/nuttx/arch/arm/src/stm32/chip/stm32f40xxx_pinmap.h b/nuttx/arch/arm/src/stm32/chip/stm32f40xxx_pinmap.h index f98b3e6de..b5ae8b91c 100644 --- a/nuttx/arch/arm/src/stm32/chip/stm32f40xxx_pinmap.h +++ b/nuttx/arch/arm/src/stm32/chip/stm32f40xxx_pinmap.h @@ -455,122 +455,122 @@ #define GPIO_TIM1_CH1N_1 (GPIO_ALT|GPIO_AF1|GPIO_PORTA|GPIO_PIN7) #define GPIO_TIM1_CH1N_2 (GPIO_ALT|GPIO_AF1|GPIO_PORTB|GPIO_PIN13) #define GPIO_TIM1_CH1N_3 (GPIO_ALT|GPIO_AF1|GPIO_PORTE|GPIO_PIN8) -#define GPIO_TIM1_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN8) -#define GPIO_TIM1_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN9) +#define GPIO_TIM1_CH1IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN8) +#define GPIO_TIM1_CH1IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN9) #define GPIO_TIM1_CH1OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN8) #define GPIO_TIM1_CH1OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTE|GPIO_PIN9) #define GPIO_TIM1_CH2N_1 (GPIO_ALT|GPIO_AF1|GPIO_PORTB|GPIO_PIN0) #define GPIO_TIM1_CH2N_2 (GPIO_ALT|GPIO_AF1|GPIO_PORTB|GPIO_PIN14) #define GPIO_TIM1_CH2N_3 (GPIO_ALT|GPIO_AF1|GPIO_PORTE|GPIO_PIN10) -#define GPIO_TIM1_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN9) -#define GPIO_TIM1_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN11) +#define GPIO_TIM1_CH2IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN9) +#define GPIO_TIM1_CH2IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN11) #define GPIO_TIM1_CH2OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN9) #define GPIO_TIM1_CH2OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTE|GPIO_PIN11) #define GPIO_TIM1_CH3N_1 (GPIO_ALT|GPIO_AF1|GPIO_PORTB|GPIO_PIN1) #define GPIO_TIM1_CH3N_2 (GPIO_ALT|GPIO_AF1|GPIO_PORTC|GPIO_PIN15) #define GPIO_TIM1_CH3N_3 (GPIO_ALT|GPIO_AF1|GPIO_PORTE|GPIO_PIN12) -#define GPIO_TIM1_CH3IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN10) -#define GPIO_TIM1_CH3IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN13) +#define GPIO_TIM1_CH3IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN10) +#define GPIO_TIM1_CH3IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN13) #define GPIO_TIM1_CH3OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN10) #define GPIO_TIM1_CH3OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTE|GPIO_PIN13) -#define GPIO_TIM1_CH4IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN11) -#define GPIO_TIM1_CH4IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN14) +#define GPIO_TIM1_CH4IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN11) +#define GPIO_TIM1_CH4IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN14) #define GPIO_TIM1_CH4OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN11) #define GPIO_TIM1_CH4OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTE|GPIO_PIN14) -#define GPIO_TIM1_ETR_1 (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN12) -#define GPIO_TIM1_ETR_2 (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTE|GPIO_PIN7) +#define GPIO_TIM1_ETR_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN12) +#define GPIO_TIM1_ETR_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTE|GPIO_PIN7) -#define GPIO_TIM2_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN0) -#define GPIO_TIM2_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN15) -#define GPIO_TIM2_CH1IN_3 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN5) +#define GPIO_TIM2_CH1IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN0) +#define GPIO_TIM2_CH1IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN15) +#define GPIO_TIM2_CH1IN_3 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN5) #define GPIO_TIM2_CH1OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN0) #define GPIO_TIM2_CH1OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN15) #define GPIO_TIM2_CH1OUT_3 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN5) -#define GPIO_TIM2_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN1) -#define GPIO_TIM2_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN3) +#define GPIO_TIM2_CH2IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN1) +#define GPIO_TIM2_CH2IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN3) #define GPIO_TIM2_CH2OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN1) #define GPIO_TIM2_CH2OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN3) -#define GPIO_TIM2_CH3IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN2) -#define GPIO_TIM2_CH3IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN10) +#define GPIO_TIM2_CH3IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN2) +#define GPIO_TIM2_CH3IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN10) #define GPIO_TIM2_CH3OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN2) #define GPIO_TIM2_CH3OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN10) -#define GPIO_TIM2_CH4IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN3) -#define GPIO_TIM2_CH4IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN11) +#define GPIO_TIM2_CH4IN_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN3) +#define GPIO_TIM2_CH4IN_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN11) #define GPIO_TIM2_CH4OUT_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN3) #define GPIO_TIM2_CH4OUT_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN11) -#define GPIO_TIM2_ETR_1 (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN0) -#define GPIO_TIM2_ETR_2 (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN15) -#define GPIO_TIM2_ETR_3 (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN5) +#define GPIO_TIM2_ETR_1 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN0) +#define GPIO_TIM2_ETR_2 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN15) +#define GPIO_TIM2_ETR_3 (GPIO_ALT|GPIO_AF1|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN5) -#define GPIO_TIM3_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN6) -#define GPIO_TIM3_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN4) -#define GPIO_TIM3_CH1IN_3 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN6) +#define GPIO_TIM3_CH1IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN6) +#define GPIO_TIM3_CH1IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN4) +#define GPIO_TIM3_CH1IN_3 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN6) #define GPIO_TIM3_CH1OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN6) #define GPIO_TIM3_CH1OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN4) #define GPIO_TIM3_CH1OUT_3 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN6) -#define GPIO_TIM3_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN7) -#define GPIO_TIM3_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN5) -#define GPIO_TIM3_CH2IN_3 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN7) +#define GPIO_TIM3_CH2IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN7) +#define GPIO_TIM3_CH2IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN5) +#define GPIO_TIM3_CH2IN_3 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN7) #define GPIO_TIM3_CH2OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN7) #define GPIO_TIM3_CH2OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN5) #define GPIO_TIM3_CH2OUT_3 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN7) -#define GPIO_TIM3_CH3IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN0) -#define GPIO_TIM3_CH3IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN8) +#define GPIO_TIM3_CH3IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN0) +#define GPIO_TIM3_CH3IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN8) #define GPIO_TIM3_CH3OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN0) #define GPIO_TIM3_CH3OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN8) -#define GPIO_TIM3_CH4IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN1) -#define GPIO_TIM3_CH4IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN9) +#define GPIO_TIM3_CH4IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN1) +#define GPIO_TIM3_CH4IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN9) #define GPIO_TIM3_CH4OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN1) #define GPIO_TIM3_CH4OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN9) -#define GPIO_TIM3_ETR (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTD|GPIO_PIN2) +#define GPIO_TIM3_ETR (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTD|GPIO_PIN2) -#define GPIO_TIM4_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN6) -#define GPIO_TIM4_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN12) +#define GPIO_TIM4_CH1IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN6) +#define GPIO_TIM4_CH1IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN12) #define GPIO_TIM4_CH1OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN6) #define GPIO_TIM4_CH1OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN12) -#define GPIO_TIM4_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN7) -#define GPIO_TIM4_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN13) +#define GPIO_TIM4_CH2IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN7) +#define GPIO_TIM4_CH2IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN13) #define GPIO_TIM4_CH2OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN7) #define GPIO_TIM4_CH2OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN13) -#define GPIO_TIM4_CH3IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN8) -#define GPIO_TIM4_CH3IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN14) +#define GPIO_TIM4_CH3IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN8) +#define GPIO_TIM4_CH3IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN14) #define GPIO_TIM4_CH3OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN8) #define GPIO_TIM4_CH3OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN14) -#define GPIO_TIM4_CH4IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN9) -#define GPIO_TIM4_CH4IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN15) +#define GPIO_TIM4_CH4IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN9) +#define GPIO_TIM4_CH4IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTD|GPIO_PIN15) #define GPIO_TIM4_CH4OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN9) #define GPIO_TIM4_CH4OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTD|GPIO_PIN15) -#define GPIO_TIM4_ETR (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTE|GPIO_PIN0) +#define GPIO_TIM4_ETR (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTE|GPIO_PIN0) -#define GPIO_TIM5_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN0) -#define GPIO_TIM5_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN10) +#define GPIO_TIM5_CH1IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN0) +#define GPIO_TIM5_CH1IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN10) #define GPIO_TIM5_CH1OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN0) #define GPIO_TIM5_CH1OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN10) -#define GPIO_TIM5_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN1) -#define GPIO_TIM5_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN11) +#define GPIO_TIM5_CH2IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN1) +#define GPIO_TIM5_CH2IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN11) #define GPIO_TIM5_CH2OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN1) #define GPIO_TIM5_CH2OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN11) -#define GPIO_TIM5_CH3IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN2) -#define GPIO_TIM5_CH3IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN12) +#define GPIO_TIM5_CH3IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN2) +#define GPIO_TIM5_CH3IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN12) #define GPIO_TIM5_CH3OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN2) #define GPIO_TIM5_CH3OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN12) -#define GPIO_TIM5_CH4IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN3) -#define GPIO_TIM5_CH4IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN0) +#define GPIO_TIM5_CH4IN_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN3) +#define GPIO_TIM5_CH4IN_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN0) #define GPIO_TIM5_CH4OUT_1 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN3) #define GPIO_TIM5_CH4OUT_2 (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTI|GPIO_PIN0) -#define GPIO_TIM5_ETR (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTH|GPIO_PIN10) +#define GPIO_TIM5_ETR (GPIO_ALT|GPIO_AF2|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTH|GPIO_PIN10) #define GPIO_TIM8_BKIN_1 (GPIO_ALT|GPIO_AF3|GPIO_PORTA|GPIO_PIN6) #define GPIO_TIM8_BKIN_2 (GPIO_ALT|GPIO_AF3|GPIO_PORTI|GPIO_PIN4) #define GPIO_TIM8_CH1N_1 (GPIO_ALT|GPIO_AF3|GPIO_PORTA|GPIO_PIN5) #define GPIO_TIM8_CH1N_2 (GPIO_ALT|GPIO_AF3|GPIO_PORTA|GPIO_PIN7) #define GPIO_TIM8_CH1N_3 (GPIO_ALT|GPIO_AF3|GPIO_PORTH|GPIO_PIN13) -#define GPIO_TIM8_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN6) -#define GPIO_TIM8_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN5) +#define GPIO_TIM8_CH1IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN6) +#define GPIO_TIM8_CH1IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN5) #define GPIO_TIM8_CH1OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN6) #define GPIO_TIM8_CH1OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTI|GPIO_PIN5) -#define GPIO_TIM8_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN7) -#define GPIO_TIM8_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN6) +#define GPIO_TIM8_CH2IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN7) +#define GPIO_TIM8_CH2IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN6) #define GPIO_TIM8_CH2OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN7) #define GPIO_TIM8_CH2OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTI|GPIO_PIN6) #define GPIO_TIM8_CH2N_1 (GPIO_ALT|GPIO_AF3|GPIO_PORTB|GPIO_PIN0) @@ -579,52 +579,52 @@ #define GPIO_TIM8_CH3N_1 (GPIO_ALT|GPIO_AF3|GPIO_PORTB|GPIO_PIN1) #define GPIO_TIM8_CH3N_2 (GPIO_ALT|GPIO_AF3|GPIO_PORTC|GPIO_PIN15) #define GPIO_TIM8_CH3N_3 (GPIO_ALT|GPIO_AF3|GPIO_PORTH|GPIO_PIN15) -#define GPIO_TIM8_CH3IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN8) -#define GPIO_TIM8_CH3IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN7) +#define GPIO_TIM8_CH3IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN8) +#define GPIO_TIM8_CH3IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN7) #define GPIO_TIM8_CH3OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN8) #define GPIO_TIM8_CH3OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTI|GPIO_PIN7) -#define GPIO_TIM8_CH4IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN9) -#define GPIO_TIM8_CH4IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN2) +#define GPIO_TIM8_CH4IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN9) +#define GPIO_TIM8_CH4IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTI|GPIO_PIN2) #define GPIO_TIM8_CH4OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN9) #define GPIO_TIM8_CH4OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTI|GPIO_PIN2) -#define GPIO_TIM8_ETR_1 (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN0) -#define GPIO_TIM8_ETR_2 (GPIO_INPUT|GPIO_FLOAT|GPIO_PORTI|GPIO_PIN3) +#define GPIO_TIM8_ETR_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTA|GPIO_PIN0) +#define GPIO_TIM8_ETR_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_FLOAT|GPIO_PORTI|GPIO_PIN3) -#define GPIO_TIM9_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN2) -#define GPIO_TIM9_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN5) +#define GPIO_TIM9_CH1IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN2) +#define GPIO_TIM9_CH1IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN5) #define GPIO_TIM9_CH1OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN2) #define GPIO_TIM9_CH1OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTE|GPIO_PIN5) -#define GPIO_TIM9_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN3) -#define GPIO_TIM9_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN6) +#define GPIO_TIM9_CH2IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN3) +#define GPIO_TIM9_CH2IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN6) #define GPIO_TIM9_CH2OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN3) #define GPIO_TIM9_CH2OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTE|GPIO_PIN6) -#define GPIO_TIM10_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN8) -#define GPIO_TIM10_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN6) +#define GPIO_TIM10_CH1IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN8) +#define GPIO_TIM10_CH1IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN6) #define GPIO_TIM10_CH1OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN8) #define GPIO_TIM10_CH1OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN6) -#define GPIO_TIM11_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN9) -#define GPIO_TIM11_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN7) +#define GPIO_TIM11_CH1IN_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN9) +#define GPIO_TIM11_CH1IN_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN7) #define GPIO_TIM11_CH1OUT_1 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN9) #define GPIO_TIM11_CH1OUT_2 (GPIO_ALT|GPIO_AF3|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN7) -#define GPIO_TIM12_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN6) -#define GPIO_TIM12_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN14) +#define GPIO_TIM12_CH1IN_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN6) +#define GPIO_TIM12_CH1IN_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTB|GPIO_PIN14) #define GPIO_TIM12_CH1OUT_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN6) #define GPIO_TIM12_CH1OUT_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTB|GPIO_PIN14) -#define GPIO_TIM12_CH2IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN15) -#define GPIO_TIM12_CH2IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN9) +#define GPIO_TIM12_CH2IN_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTC|GPIO_PIN15) +#define GPIO_TIM12_CH2IN_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTH|GPIO_PIN9) #define GPIO_TIM12_CH2OUT_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTC|GPIO_PIN15) #define GPIO_TIM12_CH2OUT_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTH|GPIO_PIN9) -#define GPIO_TIM13_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN6) -#define GPIO_TIM13_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN8) +#define GPIO_TIM13_CH1IN_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN6) +#define GPIO_TIM13_CH1IN_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN8) #define GPIO_TIM13_CH1OUT_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN6) #define GPIO_TIM13_CH1OUT_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN8) -#define GPIO_TIM14_CH1IN_1 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN7) -#define GPIO_TIM14_CH1IN_2 (GPIO_INPUT|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN9) +#define GPIO_TIM14_CH1IN_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTA|GPIO_PIN7) +#define GPIO_TIM14_CH1IN_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PULLUP|GPIO_PORTF|GPIO_PIN9) #define GPIO_TIM14_CH1OUT_1 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTA|GPIO_PIN7) #define GPIO_TIM14_CH1OUT_2 (GPIO_ALT|GPIO_AF9|GPIO_SPEED_50MHz|GPIO_PUSHPULL|GPIO_PORTF|GPIO_PIN9) diff --git a/nuttx/arch/arm/src/stm32/stm32_qencoder.c b/nuttx/arch/arm/src/stm32/stm32_qencoder.c index 271bf1dee..97d7c4235 100644 --- a/nuttx/arch/arm/src/stm32/stm32_qencoder.c +++ b/nuttx/arch/arm/src/stm32/stm32_qencoder.c @@ -65,7 +65,7 @@ * Pre-processor Definitions ************************************************************************************/ /* Debug ****************************************************************************/ -/* Non-standard debug that may be enabled just for testing QENCODER */ +/* Non-standard debug that may be enabled just for testing the quadrature encoder */ #ifndef CONFIG_DEBUG # undef CONFIG_DEBUG_QENCODER @@ -647,17 +647,13 @@ static int stm32_setup(FAR struct qe_lowerhalf_s *lower) stm32_configgpio(priv->config->ti1cfg); stm32_configgpio(priv->config->ti2cfg); - /* Set the encoder Mode 3*/ + /* Set the encoder Mode 3 */ #warning REVISIT smcr = stm32_getreg16(priv, STM32_GTIM_SMCR_OFFSET); smcr &= ~GTIM_SMCR_SMS_MASK; smcr |= GTIM_SMCR_ENCMD3; stm32_putreg16(priv, STM32_GTIM_SMCR_OFFSET, smcr); - /* Write to TIM CCER */ - - stm32_putreg16(priv, STM32_GTIM_CCER_OFFSET, ccer); - /* TI1 Channel Configuration */ /* Disable the Channel 1: Reset the CC1E Bit */ @@ -988,11 +984,11 @@ static int stm32_ioctl(FAR struct qe_lowerhalf_s *lower, int cmd, unsigned long * * Description: * Initialize a quadrature encoder interface. This function must be called from - * board-specific logic after input pins have been configured. + * board-specific logic. * * Input Parameters: * devpath - The full path to the driver to register. E.g., "/dev/qe0" - * tim - The timer number to used. time must be an element of {1,2,3,4,5,8} + * tim - The timer number to used. 'tim' must be an element of {1,2,3,4,5,8} * * Returned Values: * Zero on success; A negated errno value is returned on failure. @@ -1007,8 +1003,9 @@ int stm32_qeinitialize(FAR const char *devpath, int tim) /* Find the pre-allocated timer state structure corresponding to this timer */ priv = stm32_tim2lower(tim); - if (priv) + if (!priv) { + qedbg("TIM%d support not configured\n", tim); return -ENXIO; } @@ -1016,6 +1013,7 @@ int stm32_qeinitialize(FAR const char *devpath, int tim) if (priv->inuse) { + qedbg("TIM%d is in-used\n", tim); return -EBUSY; } @@ -1024,6 +1022,7 @@ int stm32_qeinitialize(FAR const char *devpath, int tim) ret = qe_register(devpath, (FAR struct qe_lowerhalf_s *)priv); if (ret < 0) { + qedbg("qe_register failed: %d\n", ret); return ret; } diff --git a/nuttx/arch/arm/src/stm32/stm32_qencoder.h b/nuttx/arch/arm/src/stm32/stm32_qencoder.h index f0b93f857..e9e71a956 100644 --- a/nuttx/arch/arm/src/stm32/stm32_qencoder.h +++ b/nuttx/arch/arm/src/stm32/stm32_qencoder.h @@ -96,11 +96,11 @@ * * Description: * Initialize a quadrature encoder interface. This function must be called from - * board-specific logic after input pins have been configured. + * board-specific logic.. * * Input Parameters: * devpath - The full path to the driver to register. E.g., "/dev/qe0" - * tim - The timer number to used. time must be an element of {1,2,3,4,5,8} + * tim - The timer number to used. 'tim' must be an element of {1,2,3,4,5,8} * * Returned Values: * Zero on success; A negated errno value is returned on failure. diff --git a/nuttx/configs/stm32f4discovery/README.txt b/nuttx/configs/stm32f4discovery/README.txt index 2e05b2c40..7187130b4 100755 --- a/nuttx/configs/stm32f4discovery/README.txt +++ b/nuttx/configs/stm32f4discovery/README.txt @@ -11,9 +11,11 @@ Contents - GNU Toolchain Options - IDEs - NuttX buildroot Toolchain - - stm32f4discovery-specific Configuration Options - LEDs - PWM + - UARTs + - Timer Inputs/Outputs + - STM32F4Discovery-specific Configuration Options - Configurations Development Environment @@ -139,7 +141,7 @@ NuttX buildroot Toolchain 1. You must have already configured Nuttx in <some-dir>/nuttx. cd tools - ./configure.sh stm32f4discovery/<sub-dir> + ./configure.sh STM32F4Discovery/<sub-dir> 2. Download the latest buildroot package into <some-dir> @@ -165,10 +167,10 @@ NuttX buildroot Toolchain LEDs ==== -The stm32f4discovery board has four LEDs; green, organge, red and blue on the +The STM32F4Discovery board has four LEDs; green, organge, red and blue on the board.. These LEDs are not used by the board port unless CONFIG_ARCH_LEDS is defined. In that case, the usage by the board port is defined in -include/board.h and src/up_leds.c. The LEDs are used to encode OS-related\ +include/board.h and src/up_leds.c. The LEDs are used to encode OS-related events as follows: SYMBOL Meaning LED1* LED2 LED3 LED4 @@ -194,12 +196,120 @@ events as follows: PWM === -The stm32f4discovery has no real on-board PWM devices, but the board can be +The STM32F4Discovery has no real on-board PWM devices, but the board can be configured to output a pulse train using TIM4 CH2 on PD3. This pin is available next to the audio jack. -stm32f4discovery-specific Configuration Options -============================================ +UART +==== + +UART/USART PINS +--------------- + +USART1 + CK PA8 + CTS PA11* + RTS PA12* + RX PA10*, PB7 + TX PA9*, PB6* +USART2 + CK PA4*, PD7 + CTS PA0*, PD3 + RTS PA1, PD4* + RX PA3, PD6 + TX PA2, PD5* +USART3 + CK PB12, PC12*, PD10 + CTS PB13, PD11 + RTS PB14, PD12* + RX PB11, PC11, PD9 + TX PB10*, PC10*, PD8 +UART4 + RX PA1, PC11 + TX PA0*, PC10* +UART5 + RX PD2 + TX PC12* +USART6 + CK PC8, PG7** + CTS PG13**, PG15** + RTS PG12**, PG8** + RX PC7*, PG9** + TX PC6, PG14** + + * Indicates pins that have other on-board functins and should be used only + with care (See table 5 in the STM32F4Discovery User Guide). The rest are + free I/O pins. +** Port G pins are not supported by the MCU + +Default USART/UART Configuration +-------------------------------- + +USART2 is enabled in all configurations (see */defconfig). RX and TX are +configured on pins PA3 and PA2, respectively (see include/board.h). + +Timer Inputs/Outputs +==================== + +TIM1 + CH1 PA8, PE9 + CH2 PA9*, PE11 + CH3 PA10*, PE13 + CH4 PA11*, PE14 +TIM2 + CH1 PA0*, PA15, PA5* + CH2 PA1, PB3* + CH3 PA2, PB10* + CH4 PA3, PB11 +TIM3 + CH1 PA6*, PB4, PC6 + CH2 PA7*, PB5, PC7* + CH3 PB0, PC8 + CH4 PB1, PC9 +TIM4 + CH1 PB6*, PD12* + CH2 PB7, PD13* + CH3 PB8, PD14* + CH4 PB9*, PD15* +TIM5 + CH1 PA0*, PH10** + CH2 PA1, PH11** + CH3 PA2, PH12** + CH4 PA3, PI0 +TIM8 + CH1 PC6, PI5 + CH2 PC7*, PI6 + CH3 PC8, PI7 + CH4 PC9, PI2 +TIM9 + CH1 PA2, PE5 + CH2 PA3, PE6 +TIM10 + CH1 PB8, PF6 +TIM11 + CH1 PB9*, PF7 +TIM12 + CH1 PH6**, PB14 + CH2 PC15, PH9** +TIM13 + CH1 PA6*, PF8 +TIM14 + CH1 PA7*, PF9 + + * Indicates pins that have other on-board functins and should be used only + with care (See table 5 in the STM32F4Discovery User Guide). The rest are + free I/O pins. +** Port H pins are not supported by the MCU + +Quadrature Encode Timer Inputs +------------------------------ + +If enabled (by setting CONFIG_QENCODER=y), then quadrature encoder will +user TIM2 (see nsh/defconfig) and input pins PA15, and PA1 for CH1 and +CH2, respectively (see include board.h). + +STM32F4Discovery-specific Configuration Options +=============================================== CONFIG_ARCH - Identifies the arch/ subdirectory. This should be set to: @@ -231,7 +341,7 @@ stm32f4discovery-specific Configuration Options CONFIG_ARCH_BOARD - Identifies the configs subdirectory and hence, the board that supports the particular chip or SoC. - CONFIG_ARCH_BOARD=stm32f4discovery (for the stm32f4discovery development board) + CONFIG_ARCH_BOARD=STM32F4Discovery (for the STM32F4Discovery development board) CONFIG_ARCH_BOARD_name - For use in C code @@ -438,11 +548,11 @@ stm32f4discovery-specific Configuration Options Configurations ============== -Each stm32f4discovery configuration is maintained in a sudirectory and +Each STM32F4Discovery configuration is maintained in a sudirectory and can be selected as follow: cd tools - ./configure.sh stm32f4discovery/<subdir> + ./configure.sh STM32F4Discovery/<subdir> cd - . ./setenv.sh @@ -461,13 +571,14 @@ Where <subdir> is one of the following: Configures the NuttShell (nsh) located at apps/examples/nsh. The Configuration enables both the serial and telnet NSH interfaces. - CONFIG_STM32_CODESOURCERYL=y : CodeSourcery under Linux / Mac OS X + CONFIG_STM32_CODESOURCERYL=y : CodeSourcery under Linux / Mac OS X NOTES: 1. This example supports the PWM test (apps/examples/pwm) but this must be manually enabled by selecting: CONFIG_PWM=y : Enable the generic PWM infrastructure + CONFIG_STM32_TIM4=y : Enable TIM4 CONFIG_STM32_TIM4_PWM=y : Use TIM4 to generate PWM output See also apps/examples/README.txt @@ -476,3 +587,15 @@ Where <subdir> is one of the following: CONFIG_DEBUG_PWM + 1. This example supports the Quadrature Encode test (apps/examples/qencoder) + but this must be manually enabled by selecting: + + CONFIG_QENCODER=y : Enable the generic Quadrature Encoder infrastructure + CONFIG_STM32_TIM2=y : Enable TIM2 + CONFIG_STM32_TIM2_QE=y : Use TIM2 as the quadrature encoder + + See also apps/examples/README.txt + + Special PWM-only debug options: + + CONFIG_DEBUG_QENCODER diff --git a/nuttx/configs/stm32f4discovery/include/board.h b/nuttx/configs/stm32f4discovery/include/board.h index 1ac0b0701..a34f22109 100755 --- a/nuttx/configs/stm32f4discovery/include/board.h +++ b/nuttx/configs/stm32f4discovery/include/board.h @@ -208,6 +208,7 @@ * * The STM32F4 Discovery has no on-board serial devices, but the console is * brought out to PA2 (TX) and PA3 (RX) for connection to an external serial device. + * (See the README.txt file for other options) */ #define GPIO_USART2_RX GPIO_USART2_RX_1 @@ -227,6 +228,11 @@ #define GPIO_SPI1_MOSI GPIO_SPI1_MOSI_1 #define GPIO_SPI1_SCK GPIO_SPI1_SCK_1 +/* Timer Inputs/Outputs (see the README.txt file for options) */ + +#define GPIO_TIM2_CH1IN GPIO_TIM2_CH1IN_2 +#define GPIO_TIM2_CH2IN GPIO_TIM2_CH2IN_1 + /************************************************************************************ * Public Data ************************************************************************************/ diff --git a/nuttx/configs/stm32f4discovery/nsh/appconfig b/nuttx/configs/stm32f4discovery/nsh/appconfig index 770762110..73da507f5 100644 --- a/nuttx/configs/stm32f4discovery/nsh/appconfig +++ b/nuttx/configs/stm32f4discovery/nsh/appconfig @@ -51,3 +51,7 @@ endif ifeq ($(CONFIG_PWM),y) CONFIGURED_APPS += examples/pwm endif + +ifeq ($(CONFIG_QENCODER),y) +CONFIGURED_APPS += examples/qencoder +endif diff --git a/nuttx/configs/stm32f4discovery/nsh/defconfig b/nuttx/configs/stm32f4discovery/nsh/defconfig index 7bd0cec32..b95d2a52c 100755 --- a/nuttx/configs/stm32f4discovery/nsh/defconfig +++ b/nuttx/configs/stm32f4discovery/nsh/defconfig @@ -1,7 +1,7 @@ ############################################################################ # configs/stm32f4discovery/nsh/defconfig # -# Copyright (C) 2011 Gregory Nutt. All rights reserved. +# Copyright (C) 2011-2012 Gregory Nutt. All rights reserved. # Author: Gregory Nutt <gnutt@nuttx.org> # # Redistribution and use in source and binary forms, with or without @@ -313,19 +313,26 @@ CONFIG_STM32_PHYSR_FULLDUPLEX=0x0004 CONFIG_STM32_ETH_PTP=n CONFIG_STM32_ETHMAC_REGDEBUG=n - # # PWM configuration # # The stm32f4discovery has no real on-board PWM devices, but the board can be configured to output -# a pulse train using TIM4 CH2. +# a pulse train using TIM4 CH2. (Don't forget to set CONFIG_STM32_TIM4=y above) # CONFIG_PWM=n -CONFIG_STM32_TIM4=y CONFIG_STM32_TIM4_PWM=y CONFIG_STM32_TIM4_CHANNEL=2 # +# Quadrature Encoder configuration. +# +# Uses TIM2 (CONFIG_STM32_TIM2=y above) +# +# +CONFIG_QENCODER=n +CONFIG_STM32_TIM2_QE=y + +# # General build options # # CONFIG_RRLOAD_BINARY - make the rrload binary format used with @@ -452,6 +459,7 @@ CONFIG_DEBUG_RTC=n CONFIG_DEBUG_ANALOG=n CONFIG_DEBUG_PWM=n CONFIG_DEBUG_CAN=n +CONFIG_DEBUG_QENCODER=n CONFIG_HAVE_CXX=y CONFIG_MM_REGIONS=2 CONFIG_ARCH_LOWPUTC=y diff --git a/nuttx/configs/stm32f4discovery/src/Makefile b/nuttx/configs/stm32f4discovery/src/Makefile index 133cc1467..88fd4e0ec 100644 --- a/nuttx/configs/stm32f4discovery/src/Makefile +++ b/nuttx/configs/stm32f4discovery/src/Makefile @@ -56,6 +56,10 @@ ifeq ($(CONFIG_PWM),y) CSRCS += up_pwm.c endif +ifeq ($(CONFIG_QENCODER),y) +CSRCS += up_qencoder.c +endif + COBJS = $(CSRCS:.c=$(OBJEXT)) SRCS = $(ASRCS) $(CSRCS) diff --git a/nuttx/configs/stm32f4discovery/src/stm32f4discovery-internal.h b/nuttx/configs/stm32f4discovery/src/stm32f4discovery-internal.h index 8b9ca8d3c..4c3ea10db 100644 --- a/nuttx/configs/stm32f4discovery/src/stm32f4discovery-internal.h +++ b/nuttx/configs/stm32f4discovery/src/stm32f4discovery-internal.h @@ -2,7 +2,7 @@ * configs/stm3240g_eval/src/stm3240g_internal.h * arch/arm/src/board/stm3240g_internal.n * - * Copyright (C) 2011 Gregory Nutt. All rights reserved. + * Copyright (C) 2011-2012 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without diff --git a/nuttx/configs/stm32f4discovery/src/up_autoleds.c b/nuttx/configs/stm32f4discovery/src/up_autoleds.c index 5d97f8758..34faa33fc 100644 --- a/nuttx/configs/stm32f4discovery/src/up_autoleds.c +++ b/nuttx/configs/stm32f4discovery/src/up_autoleds.c @@ -2,7 +2,7 @@ * configs/stm3240g_eval/src/up_autoleds.c * arch/arm/src/board/up_autoleds.c * - * Copyright (C) 2011 Gregory Nutt. All rights reserved. + * Copyright (C) 2011-2012 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without diff --git a/nuttx/configs/stm32f4discovery/src/up_buttons.c b/nuttx/configs/stm32f4discovery/src/up_buttons.c index 60ac6c369..ae1366930 100644 --- a/nuttx/configs/stm32f4discovery/src/up_buttons.c +++ b/nuttx/configs/stm32f4discovery/src/up_buttons.c @@ -1,7 +1,7 @@ /**************************************************************************** * configs/stm32f4discovery/src/up_buttons.c * - * Copyright (C) 2011 Gregory Nutt. All rights reserved. + * Copyright (C) 2011-2012 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without diff --git a/nuttx/configs/stm32f4discovery/src/up_qencoder.c b/nuttx/configs/stm32f4discovery/src/up_qencoder.c new file mode 100644 index 000000000..5d91f4c36 --- /dev/null +++ b/nuttx/configs/stm32f4discovery/src/up_qencoder.c @@ -0,0 +1,144 @@ +/************************************************************************************ + * configs/stm32f4discovery/src/up_qencoder.c + * arch/arm/src/board/up_qencoder.c + * + * Copyright (C) 2012 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ************************************************************************************/ + +/************************************************************************************ + * Included Files + ************************************************************************************/ + +#include <nuttx/config.h> + +#include <errno.h> +#include <debug.h> + +#include <nuttx/sensors/qencoder.h> +#include <arch/board/board.h> + +#include "chip.h" +#include "up_arch.h" +#include "stm32_qencoder.h" +#include "stm32f4discovery-internal.h" + +/************************************************************************************ + * Definitions + ************************************************************************************/ +/* Configuration *******************************************************************/ +/* The following checks assum that the quadrature encoder is on TIM2. Make the + * appropriate changes if your configuration differes. + */ + +#define HAVE_QENCODER 1 + +#ifndef CONFIG_QENCODER +# undef HAVE_QENCODER +#endif + +#ifndef CONFIG_STM32_TIM2 +# undef HAVE_QENCODER +#endif + +#ifndef CONFIG_STM32_TIM2_QE +# undef HAVE_QENCODER +#endif + +#ifdef HAVE_QENCODER + +/* Debug ***************************************************************************/ +/* Non-standard debug that may be enabled just for testing the quadrature encoder */ + +#ifndef CONFIG_DEBUG +# undef CONFIG_DEBUG_QENCODER +#endif + +#ifdef CONFIG_DEBUG_QENCODER +# define qedbg dbg +# define qelldbg lldbg +# ifdef CONFIG_DEBUG_VERBOSE +# define qevdbg vdbg +# define qellvdbg llvdbg +# else +# define qelldbg(x...) +# define qellvdbg(x...) +# endif +#else +# define qedbg(x...) +# define qelldbg(x...) +# define qevdbg(x...) +# define qellvdbg(x...) +#endif + +/************************************************************************************ + * Private Functions + ************************************************************************************/ + +/************************************************************************************ + * Public Functions + ************************************************************************************/ + +/************************************************************************************ + * Name: qe_devinit + * + * Description: + * All STM32 architectures must provide the following interface to work with + * examples/qencoder. + * + ************************************************************************************/ + +int qe_devinit(void) +{ + static initialized = false; + int ret; + + /* Check if we are already initialized */ + + if (!initialized) + { + /* Initialize a quadrature encoder interface. */ + + qevdbg("Initializing the quadrature encoder\n"); + ret = stm32_qeinitialize("/dev/qe0", 2); + if (ret < 0) + { + qedbg("stm32_qeinitialize failed: %d\n", ret); + return ret; + } + + initialized = true; + } + + return OK; +} + +#endif /* HAVE_QENCODER */ diff --git a/nuttx/drivers/sensors/qencoder.c b/nuttx/drivers/sensors/qencoder.c index edbe8255c..84bc15813 100644 --- a/nuttx/drivers/sensors/qencoder.c +++ b/nuttx/drivers/sensors/qencoder.c @@ -365,7 +365,13 @@ static int qe_ioctl(FAR struct file *filep, int cmd, unsigned long arg) * lower - An instance of the lower half interface * * Returned Value: - * Zero (OK) on success; a negated errno value on failure. + * Zero (OK) on success; a negated errno value on failure. The following + * possible error values may be returned (most are returned by + * register_driver()): + * + * EINVAL - 'path' is invalid for this operation + * EEXIST - An inode already exists at 'path' + * ENOMEM - Failed to allocate in-memory resources for the operation * ****************************************************************************/ diff --git a/nuttx/fs/fs_inodereserve.c b/nuttx/fs/fs_inodereserve.c index da73b0ac9..f1a899244 100644 --- a/nuttx/fs/fs_inodereserve.c +++ b/nuttx/fs/fs_inodereserve.c @@ -1,8 +1,8 @@ /**************************************************************************** * fs/fs_registerreserve.c * - * Copyright (C) 2007-2009, 2011 Gregory Nutt. All rights reserved. - * Author: Gregory Nutt <spudmonkey@racsa.co.cr> + * Copyright (C) 2007-2009, 2011-2012 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -39,6 +39,7 @@ #include <nuttx/config.h> +#include <assert.h> #include <errno.h> #include <nuttx/kmalloc.h> @@ -66,7 +67,7 @@ * Name: inode_namelen ****************************************************************************/ -static int inode_namelen(const char *name) +static int inode_namelen(FAR const char *name) { const char *tmp = name; while(*tmp && *tmp != '/') tmp++; @@ -87,7 +88,7 @@ static void inode_namecpy(char *dest, const char *src) * Name: inode_alloc ****************************************************************************/ -static FAR struct inode *inode_alloc(const char *name) +static FAR struct inode *inode_alloc(FAR const char *name) { int namelen = inode_namelen(name); FAR struct inode *node = (FAR struct inode*)kzalloc(FSNODE_SIZE(namelen)); @@ -142,27 +143,50 @@ static void inode_insert(FAR struct inode *node, /**************************************************************************** * Name: inode_reserve * - * NOTE: Caller must hold the inode semaphore + * Description: + * Reserve an (initialized) inode the pseudo file system. + * + * NOTE: Caller must hold the inode semaphore + * + * Input parameters: + * path - The path to the inode to create + * inode - The location to return the inode pointer + * + * Returned Value: + * Zero on success (with the inode point in 'inode'); A negated errno + * value is returned on failure: + * + * EINVAL - 'path' is invalid for this operation + * EEXIST - An inode already exists at 'path' + * ENOMEM - Failed to allocate in-memory resources for the operation + * ****************************************************************************/ -FAR struct inode *inode_reserve(const char *path) +int inode_reserve(FAR const char *path, FAR struct inode **inode) { const char *name = path; FAR struct inode *left; FAR struct inode *parent; + /* Assume failure */ + + DEBUGASSERT(path && inode); + *inode = NULL; + + /* Handle paths that are interpreted as the root directory */ + if (!*path || path[0] != '/') { - return NULL; + return -EINVAL; } /* Find the location to insert the new subtree */ - if (inode_search(&name, &left, &parent, (const char **)NULL) != NULL) + if (inode_search(&name, &left, &parent, (FAR const char **)NULL) != NULL) { - /* Is is an error if the node already exists in the tree */ + /* It is an error if the node already exists in the tree */ - return NULL; + return -EEXIST; } /* Now we now where to insert the subtree */ @@ -176,7 +200,7 @@ FAR struct inode *inode_reserve(const char *path) * by looking at the next name. */ - const char *next_name = inode_nextname(name); + FAR const char *next_name = inode_nextname(name); if (*next_name) { /* Insert an operationless node */ @@ -200,11 +224,13 @@ FAR struct inode *inode_reserve(const char *path) if (node) { inode_insert(node, left, parent); - return node; + *inode = node; + return OK; } } /* We get here on failures to allocate node memory */ - return NULL; + + return -ENOMEM; } } diff --git a/nuttx/fs/fs_internal.h b/nuttx/fs/fs_internal.h index f79715b17..af5cd615a 100644 --- a/nuttx/fs/fs_internal.h +++ b/nuttx/fs/fs_internal.h @@ -1,8 +1,8 @@ /**************************************************************************** * fs/fs_internal.h * - * Copyright (C) 2007, 2009 Gregory Nutt. All rights reserved. - * Author: Gregory Nutt <spudmonkey@racsa.co.cr> + * Copyright (C) 2007, 2009, 2012 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -111,19 +111,19 @@ EXTERN FAR struct inode *inode_search(FAR const char **path, FAR struct inode **parent, FAR const char **relpath); EXTERN void inode_free(FAR struct inode *node); -EXTERN const char *inode_nextname(const char *name); +EXTERN const char *inode_nextname(FAR const char *name); /* fs_inodereserver.c ********************************************************/ -EXTERN FAR struct inode *inode_reserve(const char *path); +EXTERN int inode_reserve(FAR const char *path, FAR struct inode **inode); /* fs_inoderemove.c **********************************************************/ -EXTERN int inode_remove(const char *path); +EXTERN int inode_remove(FAR const char *path); /* fs_inodefind.c ************************************************************/ -EXTERN FAR struct inode *inode_find(const char *path, const char **relpath); +EXTERN FAR struct inode *inode_find(FAR const char *path, const char **relpath); /* fs_inodeaddref.c **********************************************************/ diff --git a/nuttx/fs/fs_mount.c b/nuttx/fs/fs_mount.c index 803f4e797..d2e0dc961 100644 --- a/nuttx/fs/fs_mount.c +++ b/nuttx/fs/fs_mount.c @@ -1,8 +1,8 @@ /**************************************************************************** * fs/fs_mount.c * - * Copyright (C) 2007-2009, 2011 Gregory Nutt. All rights reserved. - * Author: Gregory Nutt <spudmonkey@racsa.co.cr> + * Copyright (C) 2007-2009, 2011-2012 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -193,9 +193,9 @@ mount_findfs(FAR const struct fsmap_t *fstab, FAR const char *filesystemtype) * ****************************************************************************/ -int mount(const char *source, const char *target, - const char *filesystemtype, unsigned long mountflags, - const void *data) +int mount(FAR const char *source, FAR const char *target, + FAR const char *filesystemtype, unsigned long mountflags, + FAR const void *data) { #if defined(BDFS_SUPPORT) || defined(NONBDFS_SUPPORT) #ifdef BDFS_SUPPORT @@ -205,7 +205,7 @@ int mount(const char *source, const char *target, FAR const struct mountpt_operations *mops; void *fshandle; int errcode; - int status; + int ret; /* Verify required pointer arguments */ @@ -222,11 +222,11 @@ int mount(const char *source, const char *target, /* Find the block driver */ - status = find_blockdriver(source, mountflags, &blkdrvr_inode); - if (status < 0) + ret = find_blockdriver(source, mountflags, &blkdrvr_inode); + if (ret < 0) { fdbg("Failed to find block driver %s\n", source); - errcode = -status; + errcode = -ret; goto errout; } } @@ -244,20 +244,24 @@ int mount(const char *source, const char *target, goto errout; } - /* Insert a dummy node -- we need to hold the inode semaphore + /* Insert a dummy node -- we need to hold the inode semaphore * to do this because we will have a momentarily bad structure. */ inode_semtake(); - mountpt_inode = inode_reserve(target); - if (!mountpt_inode) + ret = inode_reserve(target, &mountpt_inode); + if (ret < 0) { /* inode_reserve can fail for a couple of reasons, but the most likely - * one is that the inode already exists. + * one is that the inode already exists. inode_reserve may return: + * + * -EINVAL - 'path' is invalid for this operation + * -EEXIST - An inode already exists at 'path' + * -ENOMEM - Failed to allocate in-memory resources for the operation */ fdbg("Failed to reserve inode\n"); - errcode = EBUSY; + errcode = -ret; goto errout_with_semaphore; } @@ -289,18 +293,18 @@ int mount(const char *source, const char *target, /* On failure, the bind method returns -errorcode */ #ifdef BDFS_SUPPORT - status = mops->bind(blkdrvr_inode, data, &fshandle); + ret = mops->bind(blkdrvr_inode, data, &fshandle); #else - status = mops->bind(NULL, data, &fshandle); + ret = mops->bind(NULL, data, &fshandle); #endif - if (status != 0) + if (ret != 0) { /* The inode is unhappy with the blkdrvr for some reason. Back out * the count for the reference we failed to pass and exit with an * error. */ - fdbg("Bind method failed: %d\n", status); + fdbg("Bind method failed: %d\n", ret); #ifdef BDFS_SUPPORT #ifdef NONBDFS_SUPPORT if (blkdrvr_inode) @@ -309,7 +313,7 @@ int mount(const char *source, const char *target, blkdrvr_inode->i_crefs--; } #endif - errcode = -status; + errcode = -ret; goto errout_with_mountpt; } diff --git a/nuttx/fs/fs_registerblockdriver.c b/nuttx/fs/fs_registerblockdriver.c index 248e3e2a7..bd5c08be4 100644 --- a/nuttx/fs/fs_registerblockdriver.c +++ b/nuttx/fs/fs_registerblockdriver.c @@ -1,8 +1,8 @@ /**************************************************************************** * fs/fs_registerblockdriver.c * - * Copyright (C) 2007-2009 Gregory Nutt. All rights reserved. - * Author: Gregory Nutt <spudmonkey@racsa.co.cr> + * Copyright (C) 2007-2009, 2012 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -65,27 +65,45 @@ /**************************************************************************** * Name: register_driver + * + * Description: + * Register a block driver inode the pseudo file system. + * + * Input parameters: + * path - The path to the inode to create + * bops - The block driver operations structure + * mode - inmode priviledges (not used) + * priv - Private, user data that will be associated with the inode. + * + * Returned Value: + * Zero on success (with the inode point in 'inode'); A negated errno + * value is returned on a failure (all error values returned by + * inode_reserve): + * + * EINVAL - 'path' is invalid for this operation + * EEXIST - An inode already exists at 'path' + * ENOMEM - Failed to allocate in-memory resources for the operation + * ****************************************************************************/ -int register_blockdriver(const char *path, - const struct block_operations *bops, - mode_t mode, void *priv) +int register_blockdriver(FAR const char *path, + FAR const struct block_operations *bops, + mode_t mode, FAR void *priv) { - struct inode *node; - int ret = -ENOMEM; + FAR struct inode *node; + int ret; - /* Insert an inode for the device driver -- we need to hold the inode semaphore - * to prevent access to the tree while we this. This is because we will have a - * momentarily bad true until we populate the inode with valid data. + /* Insert an inode for the device driver -- we need to hold the inode + * semaphore to prevent access to the tree while we this. This is because + * we will have a momentarily bad true until we populate the inode with + * valid data. */ inode_semtake(); - node = inode_reserve(path); - if (node != NULL) + ret = inode_reserve(path, &node); + if (ret >= 0) { - /* We have it, now populate it with block driver specific - * information. - */ + /* We have it, now populate it with block driver specific information. */ INODE_SET_BLOCK(node); diff --git a/nuttx/fs/fs_registerdriver.c b/nuttx/fs/fs_registerdriver.c index 7b3520435..053c80061 100644 --- a/nuttx/fs/fs_registerdriver.c +++ b/nuttx/fs/fs_registerdriver.c @@ -1,8 +1,8 @@ /**************************************************************************** * fs/fs_registerdriver.c * - * Copyright (C) 2007-2009 Gregory Nutt. All rights reserved. - * Author: Gregory Nutt <spudmonkey@racsa.co.cr> + * Copyright (C) 2007-2009, 2012 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -65,34 +65,51 @@ /**************************************************************************** * Name: register_driver + * + * Description: + * Register a character driver inode the pseudo file system. + * + * Input parameters: + * path - The path to the inode to create + * fops - The file operations structure + * mode - inmode priviledges (not used) + * priv - Private, user data that will be associated with the inode. + * + * Returned Value: + * Zero on success (with the inode point in 'inode'); A negated errno + * value is returned on a failure (all error values returned by + * inode_reserve): + * + * EINVAL - 'path' is invalid for this operation + * EEXIST - An inode already exists at 'path' + * ENOMEM - Failed to allocate in-memory resources for the operation + * ****************************************************************************/ -int register_driver(const char *path, const struct file_operations *fops, - mode_t mode, void *priv) +int register_driver(FAR const char *path, FAR const struct file_operations *fops, + mode_t mode, FAR void *priv) { - struct inode *node; - int ret = ERROR; + FAR struct inode *node; + int ret; - /* Insert a dummy node -- we need to hold the inode semaphore - * to do this because we will have a momentarily bad structure. + /* Insert a dummy node -- we need to hold the inode semaphore because we + * will have a momentarily bad structure. */ inode_semtake(); - node = inode_reserve(path); - if (node != NULL) + ret = inode_reserve(path, &node); + if (ret >= 0) { - /* We have it, now populate it with driver specific - * information. - */ + /* We have it, now populate it with driver specific information. */ - INODE_SET_DRIVER(node); + INODE_SET_DRIVER(node); - node->u.i_ops = fops; + node->u.i_ops = fops; #ifdef CONFIG_FILE_MODE - node->i_mode = mode; + node->i_mode = mode; #endif - node->i_private = priv; - ret = OK; + node->i_private = priv; + ret = OK; } inode_semgive(); |