Fix up makefile .NOTPARALLEL heuristics so that linear building is only enforced...
authorDean Camera <dean@fourwalledcubicle.com>
Tue, 10 Jul 2012 19:33:39 +0000 (19:33 +0000)
committerDean Camera <dean@fourwalledcubicle.com>
Tue, 10 Jul 2012 19:33:39 +0000 (19:33 +0000)
16 files changed:
Bootloaders/makefile
BuildTests/makefile
Demos/Device/ClassDriver/makefile
Demos/Device/LowLevel/makefile
Demos/DualRole/ClassDriver/makefile
Demos/Host/ClassDriver/makefile
Demos/Host/LowLevel/makefile
LUFA/Build/lufa.sources.in
LUFA/DoxygenPages/MigrationInformation.txt
LUFA/Drivers/USB/Core/ConfigDescriptor.c [deleted file]
LUFA/Drivers/USB/Core/ConfigDescriptor.h [deleted file]
LUFA/Drivers/USB/Core/ConfigDescriptors.c [new file with mode: 0644]
LUFA/Drivers/USB/Core/ConfigDescriptors.h [new file with mode: 0644]
LUFA/Drivers/USB/USB.h
Projects/makefile
makefile

index ba4f512..1a4d345 100644 (file)
@@ -22,16 +22,18 @@ ifeq ($(MAKELEVEL), 10)
    $(error EMERGENCY ABORT: INFINITE RECURSION DETECTED)
 endif
 
-# If building without a per-project object directory, we can't build in parallel
+# Need to special-case building without a per-project object directory
 ifeq ($(OBJDIR),)
-   .NOTPARALLEL:
-
-   # Ensure projects are pre-cleaned if the target is the default or "all"
+   # If no target specified, force "clean all" and disallow parallel build   
    ifeq ($(MAKECMDGOALS),)
       MAKECMDGOALS := clean all
+      .NOTPARALLEL:
    endif
+
+   # If one of the targets is to build, force "clean" beforehand and disallow parallel build   
    ifneq ($(findstring all, $(MAKECMDGOALS)),)
       MAKECMDGOALS := clean $(MAKECMDGOALS)
+      .NOTPARALLEL:
    endif
 endif
 
index caa22fb..901dbad 100644 (file)
@@ -11,6 +11,7 @@
 # not intended to be modified or compiled by non-developers.
 
 all:
+
 %:
        @echo Executing \"make $@\" on all LUFA build tests.
        @echo
index 3a5615e..797a483 100644 (file)
@@ -22,16 +22,18 @@ ifeq ($(MAKELEVEL), 10)
    $(error EMERGENCY ABORT: INFINITE RECURSION DETECTED)
 endif
 
-# If building without a per-project object directory, we can't build in parallel
+# Need to special-case building without a per-project object directory
 ifeq ($(OBJDIR),)
-   .NOTPARALLEL:
-
-   # Ensure projects are pre-cleaned if the target is the default or "all"
+   # If no target specified, force "clean all" and disallow parallel build   
    ifeq ($(MAKECMDGOALS),)
       MAKECMDGOALS := clean all
+      .NOTPARALLEL:
    endif
+
+   # If one of the targets is to build, force "clean" beforehand and disallow parallel build   
    ifneq ($(findstring all, $(MAKECMDGOALS)),)
       MAKECMDGOALS := clean $(MAKECMDGOALS)
+      .NOTPARALLEL:
    endif
 endif
 
index 3a5615e..797a483 100644 (file)
@@ -22,16 +22,18 @@ ifeq ($(MAKELEVEL), 10)
    $(error EMERGENCY ABORT: INFINITE RECURSION DETECTED)
 endif
 
-# If building without a per-project object directory, we can't build in parallel
+# Need to special-case building without a per-project object directory
 ifeq ($(OBJDIR),)
-   .NOTPARALLEL:
-
-   # Ensure projects are pre-cleaned if the target is the default or "all"
+   # If no target specified, force "clean all" and disallow parallel build   
    ifeq ($(MAKECMDGOALS),)
       MAKECMDGOALS := clean all
+      .NOTPARALLEL:
    endif
+
+   # If one of the targets is to build, force "clean" beforehand and disallow parallel build   
    ifneq ($(findstring all, $(MAKECMDGOALS)),)
       MAKECMDGOALS := clean $(MAKECMDGOALS)
+      .NOTPARALLEL:
    endif
 endif
 
index 71fb805..b9538fe 100644 (file)
@@ -22,16 +22,18 @@ ifeq ($(MAKELEVEL), 10)
    $(error EMERGENCY ABORT: INFINITE RECURSION DETECTED)
 endif
 
-# If building without a per-project object directory, we can't build in parallel
+# Need to special-case building without a per-project object directory
 ifeq ($(OBJDIR),)
-   .NOTPARALLEL:
-
-   # Ensure projects are pre-cleaned if the target is the default or "all"
+   # If no target specified, force "clean all" and disallow parallel build   
    ifeq ($(MAKECMDGOALS),)
       MAKECMDGOALS := clean all
+      .NOTPARALLEL:
    endif
+
+   # If one of the targets is to build, force "clean" beforehand and disallow parallel build   
    ifneq ($(findstring all, $(MAKECMDGOALS)),)
       MAKECMDGOALS := clean $(MAKECMDGOALS)
+      .NOTPARALLEL:
    endif
 endif
 
index a2b14c8..d057a1c 100644 (file)
@@ -22,16 +22,18 @@ ifeq ($(MAKELEVEL), 10)
    $(error EMERGENCY ABORT: INFINITE RECURSION DETECTED)
 endif
 
-# If building without a per-project object directory, we can't build in parallel
+# Need to special-case building without a per-project object directory
 ifeq ($(OBJDIR),)
-   .NOTPARALLEL:
-
-   # Ensure projects are pre-cleaned if the target is the default or "all"
+   # If no target specified, force "clean all" and disallow parallel build   
    ifeq ($(MAKECMDGOALS),)
       MAKECMDGOALS := clean all
+      .NOTPARALLEL:
    endif
+
+   # If one of the targets is to build, force "clean" beforehand and disallow parallel build   
    ifneq ($(findstring all, $(MAKECMDGOALS)),)
       MAKECMDGOALS := clean $(MAKECMDGOALS)
+      .NOTPARALLEL:
    endif
 endif
 
index a2b14c8..d057a1c 100644 (file)
@@ -22,16 +22,18 @@ ifeq ($(MAKELEVEL), 10)
    $(error EMERGENCY ABORT: INFINITE RECURSION DETECTED)
 endif
 
-# If building without a per-project object directory, we can't build in parallel
+# Need to special-case building without a per-project object directory
 ifeq ($(OBJDIR),)
-   .NOTPARALLEL:
-
-   # Ensure projects are pre-cleaned if the target is the default or "all"
+   # If no target specified, force "clean all" and disallow parallel build   
    ifeq ($(MAKECMDGOALS),)
       MAKECMDGOALS := clean all
+      .NOTPARALLEL:
    endif
+
+   # If one of the targets is to build, force "clean" beforehand and disallow parallel build   
    ifneq ($(findstring all, $(MAKECMDGOALS)),)
       MAKECMDGOALS := clean $(MAKECMDGOALS)
+      .NOTPARALLEL:
    endif
 endif
 
index 10e5c1d..0e026c5 100644 (file)
@@ -75,7 +75,7 @@ LUFA_SRC_USB         := $(LUFA_ROOT_PATH)/Drivers/USB/Core/$(ARCH)/Device_$(ARCH
                         $(LUFA_ROOT_PATH)/Drivers/USB/Core/$(ARCH)/USBInterrupt_$(ARCH).c    \
                         $(LUFA_ROOT_PATH)/Drivers/USB/Core/$(ARCH)/EndpointStream_$(ARCH).c  \
                         $(LUFA_ROOT_PATH)/Drivers/USB/Core/$(ARCH)/PipeStream_$(ARCH).c      \
-                        $(LUFA_ROOT_PATH)/Drivers/USB/Core/ConfigDescriptor.c                \
+                        $(LUFA_ROOT_PATH)/Drivers/USB/Core/ConfigDescriptors.c               \
                         $(LUFA_ROOT_PATH)/Drivers/USB/Core/DeviceStandardReq.c               \
                         $(LUFA_ROOT_PATH)/Drivers/USB/Core/Events.c                          \
                         $(LUFA_ROOT_PATH)/Drivers/USB/Core/HostStandardReq.c                 \
index f0fd9b2..544c94e 100644 (file)
@@ -44,6 +44,9 @@
  *    - The MIDI class driver \ref MIDI_EventPacket_t event packet no longer contains seperate \c CableIndex and \c Command entries; these have been combined
  *      into a single \c Event element which can be contructed using the new macro \ref MIDI_EVENT(). Existing applications should use the new macro and structure
  *      element name.
+ *    - The library "LUFA/Drivers/USB/Core/ConfigDescriptor.c" source file has been renamed "LUFA/Drivers/USB/Core/ConfigDescriptors.c" as this was clashing with
+ *      files in some low level host mode demo applications, preventing parallel project builds. If you are referencing the project source files directly instead
+ *      of using the makefile module names, you will need to adjust your project makefile.
  *
  *  \section Sec_Migration120219 Migrating from 111009 to 120219
  *  <b>USB Core</b>
diff --git a/LUFA/Drivers/USB/Core/ConfigDescriptor.c b/LUFA/Drivers/USB/Core/ConfigDescriptor.c
deleted file mode 100644 (file)
index 5bdcdc6..0000000
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
-             LUFA Library
-     Copyright (C) Dean Camera, 2012.
-
-  dean [at] fourwalledcubicle [dot] com
-           www.lufa-lib.org
-*/
-
-/*
-  Copyright 2012  Dean Camera (dean [at] fourwalledcubicle [dot] com)
-
-  Permission to use, copy, modify, distribute, and sell this
-  software and its documentation for any purpose is hereby granted
-  without fee, provided that the above copyright notice appear in
-  all copies and that both that the copyright notice and this
-  permission notice and warranty disclaimer appear in supporting
-  documentation, and that the name of the author not be used in
-  advertising or publicity pertaining to distribution of the
-  software without specific, written prior permission.
-
-  The author disclaim all warranties with regard to this
-  software, including all implied warranties of merchantability
-  and fitness.  In no event shall the author be liable for any
-  special, indirect or consequential damages or any damages
-  whatsoever resulting from loss of use, data or profits, whether
-  in an action of contract, negligence or other tortious action,
-  arising out of or in connection with the use or performance of
-  this software.
-*/
-
-#define  __INCLUDE_FROM_USB_DRIVER
-#include "ConfigDescriptor.h"
-
-#if defined(USB_CAN_BE_HOST)
-uint8_t USB_Host_GetDeviceConfigDescriptor(const uint8_t ConfigNumber,
-                                           uint16_t* const ConfigSizePtr,
-                                           void* const BufferPtr,
-                                           const uint16_t BufferSize)
-{
-       uint8_t ErrorCode;
-       uint8_t ConfigHeader[sizeof(USB_Descriptor_Configuration_Header_t)];
-
-       USB_ControlRequest = (USB_Request_Header_t)
-               {
-                       .bmRequestType = (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE),
-                       .bRequest      = REQ_GetDescriptor,
-                       .wValue        = ((DTYPE_Configuration << 8) | (ConfigNumber - 1)),
-                       .wIndex        = 0,
-                       .wLength       = sizeof(USB_Descriptor_Configuration_Header_t),
-               };
-
-       Pipe_SelectPipe(PIPE_CONTROLPIPE);
-
-       if ((ErrorCode = USB_Host_SendControlRequest(ConfigHeader)) != HOST_SENDCONTROL_Successful)
-         return ErrorCode;
-
-       *ConfigSizePtr = le16_to_cpu(DESCRIPTOR_PCAST(ConfigHeader, USB_Descriptor_Configuration_Header_t)->TotalConfigurationSize);
-
-       if (*ConfigSizePtr > BufferSize)
-         return HOST_GETCONFIG_BuffOverflow;
-
-       USB_ControlRequest.wLength = *ConfigSizePtr;
-
-       if ((ErrorCode = USB_Host_SendControlRequest(BufferPtr)) != HOST_SENDCONTROL_Successful)
-         return ErrorCode;
-
-       if (DESCRIPTOR_TYPE(BufferPtr) != DTYPE_Configuration)
-         return HOST_GETCONFIG_InvalidData;
-
-       return HOST_GETCONFIG_Successful;
-}
-#endif
-
-void USB_GetNextDescriptorOfType(uint16_t* const BytesRem,
-                                 void** const CurrConfigLoc,
-                                 const uint8_t Type)
-{
-       while (*BytesRem)
-       {
-               USB_GetNextDescriptor(BytesRem, CurrConfigLoc);
-
-               if (DESCRIPTOR_TYPE(*CurrConfigLoc) == Type)
-                 return;
-       }
-}
-
-void USB_GetNextDescriptorOfTypeBefore(uint16_t* const BytesRem,
-                                       void** const CurrConfigLoc,
-                                       const uint8_t Type,
-                                       const uint8_t BeforeType)
-{
-       while (*BytesRem)
-       {
-               USB_GetNextDescriptor(BytesRem, CurrConfigLoc);
-
-               if (DESCRIPTOR_TYPE(*CurrConfigLoc) == Type)
-               {
-                       return;
-               }
-               else if (DESCRIPTOR_TYPE(*CurrConfigLoc) == BeforeType)
-               {
-                       *BytesRem = 0;
-                       return;
-               }
-       }
-}
-
-void USB_GetNextDescriptorOfTypeAfter(uint16_t* const BytesRem,
-                                      void** const CurrConfigLoc,
-                                      const uint8_t Type,
-                                      const uint8_t AfterType)
-{
-       USB_GetNextDescriptorOfType(BytesRem, CurrConfigLoc, AfterType);
-
-       if (*BytesRem)
-         USB_GetNextDescriptorOfType(BytesRem, CurrConfigLoc, Type);
-}
-
-uint8_t USB_GetNextDescriptorComp(uint16_t* const BytesRem,
-                                  void** const CurrConfigLoc,
-                                  ConfigComparatorPtr_t const ComparatorRoutine)
-{
-       uint8_t ErrorCode;
-
-       while (*BytesRem)
-       {
-               uint8_t* PrevDescLoc  = *CurrConfigLoc;
-               uint16_t PrevBytesRem = *BytesRem;
-
-               USB_GetNextDescriptor(BytesRem, CurrConfigLoc);
-
-               if ((ErrorCode = ComparatorRoutine(*CurrConfigLoc)) != DESCRIPTOR_SEARCH_NotFound)
-               {
-                       if (ErrorCode == DESCRIPTOR_SEARCH_Fail)
-                       {
-                               *CurrConfigLoc = PrevDescLoc;
-                               *BytesRem      = PrevBytesRem;
-                       }
-
-                       return ErrorCode;
-               }
-       }
-
-       return DESCRIPTOR_SEARCH_COMP_EndOfDescriptor;
-}
-
diff --git a/LUFA/Drivers/USB/Core/ConfigDescriptor.h b/LUFA/Drivers/USB/Core/ConfigDescriptor.h
deleted file mode 100644 (file)
index 97fb39b..0000000
+++ /dev/null
@@ -1,286 +0,0 @@
-/*
-             LUFA Library
-     Copyright (C) Dean Camera, 2012.
-
-  dean [at] fourwalledcubicle [dot] com
-           www.lufa-lib.org
-*/
-
-/*
-  Copyright 2012  Dean Camera (dean [at] fourwalledcubicle [dot] com)
-
-  Permission to use, copy, modify, distribute, and sell this
-  software and its documentation for any purpose is hereby granted
-  without fee, provided that the above copyright notice appear in
-  all copies and that both that the copyright notice and this
-  permission notice and warranty disclaimer appear in supporting
-  documentation, and that the name of the author not be used in
-  advertising or publicity pertaining to distribution of the
-  software without specific, written prior permission.
-
-  The author disclaim all warranties with regard to this
-  software, including all implied warranties of merchantability
-  and fitness.  In no event shall the author be liable for any
-  special, indirect or consequential damages or any damages
-  whatsoever resulting from loss of use, data or profits, whether
-  in an action of contract, negligence or other tortious action,
-  arising out of or in connection with the use or performance of
-  this software.
-*/
-
-/** \file
- *  \brief USB Configuration Descriptor definitions.
- *  \copydetails Group_ConfigDescriptorParser
- *
- *  \note This file should not be included directly. It is automatically included as needed by the USB driver
- *        dispatch header located in LUFA/Drivers/USB/USB.h.
- */
-
-/** \ingroup Group_StdDescriptors
- *  \defgroup Group_ConfigDescriptorParser Configuration Descriptor Parser
- *  \brief USB Configuration Descriptor definitions.
- *
- *  This section of the library gives a friendly API which can be used in host applications to easily
- *  parse an attached device's configuration descriptor so that endpoint, interface and other descriptor
- *  data can be extracted and used as needed.
- *
- *  @{
- */
-
-#ifndef __CONFIGDESCRIPTOR_H__
-#define __CONFIGDESCRIPTOR_H__
-
-       /* Includes: */
-               #include "../../../Common/Common.h"
-               #include "USBMode.h"
-               #include "HostStandardReq.h"
-               #include "StdDescriptors.h"
-
-       /* Enable C linkage for C++ Compilers: */
-               #if defined(__cplusplus)
-                       extern "C" {
-               #endif
-
-       /* Preprocessor Checks: */
-               #if !defined(__INCLUDE_FROM_USB_DRIVER)
-                       #error Do not include this file directly. Include LUFA/Drivers/USB/USB.h instead.
-               #endif
-
-       /* Public Interface - May be used in end-application: */
-               /* Macros: */
-                       /** Casts a pointer to a descriptor inside the configuration descriptor into a pointer to the given
-                        *  descriptor type.
-                        *
-                        *  Usage Example:
-                        *  \code
-                        *  uint8_t* CurrDescriptor = &ConfigDescriptor[0]; // Pointing to the configuration header
-                        *  USB_Descriptor_Configuration_Header_t* ConfigHeaderPtr = DESCRIPTOR_PCAST(CurrDescriptor,
-                        *                                                           USB_Descriptor_Configuration_Header_t);
-                        *  
-                        *  // Can now access elements of the configuration header struct using the -> indirection operator
-                        *  \endcode
-                        */
-                       #define DESCRIPTOR_PCAST(DescriptorPtr, Type) ((Type*)(DescriptorPtr))
-
-                       /** Casts a pointer to a descriptor inside the configuration descriptor into the given descriptor
-                        *  type (as an actual struct instance rather than a pointer to a struct).
-                        *
-                        *  Usage Example:
-                        *  \code
-                        *  uint8_t* CurrDescriptor = &ConfigDescriptor[0]; // Pointing to the configuration header
-                        *  USB_Descriptor_Configuration_Header_t ConfigHeader = DESCRIPTOR_CAST(CurrDescriptor,
-                        *                                                       USB_Descriptor_Configuration_Header_t);
-                        *  
-                        *  // Can now access elements of the configuration header struct using the . operator
-                        *  \endcode
-                        */
-                       #define DESCRIPTOR_CAST(DescriptorPtr, Type)  (*DESCRIPTOR_PCAST(DescriptorPtr, Type))
-
-                       /** Returns the descriptor's type, expressed as the 8-bit type value in the header of the descriptor.
-                        *  This value's meaning depends on the descriptor's placement in the descriptor, but standard type
-                        *  values can be accessed in the \ref USB_DescriptorTypes_t enum.
-                        */
-                       #define DESCRIPTOR_TYPE(DescriptorPtr)    DESCRIPTOR_PCAST(DescriptorPtr, USB_Descriptor_Header_t)->Type
-
-                       /** Returns the descriptor's size, expressed as the 8-bit value indicating the number of bytes. */
-                       #define DESCRIPTOR_SIZE(DescriptorPtr)    DESCRIPTOR_PCAST(DescriptorPtr, USB_Descriptor_Header_t)->Size
-
-               /* Type Defines: */
-                       /** Type define for a Configuration Descriptor comparator function (function taking a pointer to an array
-                        *  of type void, returning a uint8_t value).
-                        *
-                        *  \see \ref USB_GetNextDescriptorComp function for more details.
-                        */
-                       typedef uint8_t (* ConfigComparatorPtr_t)(void*);
-
-               /* Enums: */
-                       /** Enum for the possible return codes of the \ref USB_Host_GetDeviceConfigDescriptor() function. */
-                       enum USB_Host_GetConfigDescriptor_ErrorCodes_t
-                       {
-                               HOST_GETCONFIG_Successful       = 0, /**< No error occurred while retrieving the configuration descriptor. */
-                               HOST_GETCONFIG_DeviceDisconnect = 1, /**< The attached device was disconnected while retrieving the configuration
-                                                                       * descriptor.
-                                                                       */
-                               HOST_GETCONFIG_PipeError        = 2, /**< An error occurred in the pipe while sending the request. */
-                               HOST_GETCONFIG_SetupStalled     = 3, /**< The attached device stalled the request to retrieve the configuration
-                                                                       * descriptor.
-                                                                       */
-                               HOST_GETCONFIG_SoftwareTimeOut  = 4, /**< The request or data transfer timed out. */
-                               HOST_GETCONFIG_BuffOverflow     = 5, /**< The device's configuration descriptor is too large to fit into the allocated
-                                                                       * buffer.
-                                                                       */
-                               HOST_GETCONFIG_InvalidData      = 6, /**< The device returned invalid configuration descriptor data. */
-                       };
-
-                       /** Enum for return values of a descriptor comparator function. */
-                       enum DSearch_Return_ErrorCodes_t
-                       {
-                               DESCRIPTOR_SEARCH_Found                = 0, /**< Current descriptor matches comparator criteria. */
-                               DESCRIPTOR_SEARCH_Fail                 = 1, /**< No further descriptor could possibly match criteria, fail the search. */
-                               DESCRIPTOR_SEARCH_NotFound             = 2, /**< Current descriptor does not match comparator criteria. */
-                       };
-
-                       /** Enum for return values of \ref USB_GetNextDescriptorComp(). */
-                       enum DSearch_Comp_Return_ErrorCodes_t
-                       {
-                               DESCRIPTOR_SEARCH_COMP_Found           = 0, /**< Configuration descriptor now points to descriptor which matches
-                                                                            *   search criteria of the given comparator function. */
-                               DESCRIPTOR_SEARCH_COMP_Fail            = 1, /**< Comparator function returned \ref DESCRIPTOR_SEARCH_Fail. */
-                               DESCRIPTOR_SEARCH_COMP_EndOfDescriptor = 2, /**< End of configuration descriptor reached before match found. */
-                       };
-
-               /* Function Prototypes: */
-                       /** Retrieves the configuration descriptor data from an attached device via a standard request into a buffer,
-                        *  including validity and size checking to prevent a buffer overflow.
-                        *
-                        *  \param[in]     ConfigNumber   Device configuration descriptor number to fetch from the device (usually set to 1 for
-                        *                                single configuration devices).
-                        *  \param[in,out] ConfigSizePtr  Pointer to a location for storing the retrieved configuration descriptor size.
-                        *  \param[out]    BufferPtr      Pointer to the buffer for storing the configuration descriptor data.
-                        *  \param[out]    BufferSize     Size of the allocated buffer where the configuration descriptor is to be stored.
-                        *
-                        *  \return A value from the \ref USB_Host_GetConfigDescriptor_ErrorCodes_t enum.
-                        */
-                       uint8_t USB_Host_GetDeviceConfigDescriptor(const uint8_t ConfigNumber,
-                                                                  uint16_t* const ConfigSizePtr,
-                                                                  void* const BufferPtr,
-                                                                  const uint16_t BufferSize) ATTR_NON_NULL_PTR_ARG(2) ATTR_NON_NULL_PTR_ARG(3);
-
-                       /** Skips to the next sub-descriptor inside the configuration descriptor of the specified type value.
-                        *  The bytes remaining value is automatically decremented.
-                        *
-                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
-                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
-                        * \param[in]     Type           Descriptor type value to search for.
-                        */
-                       void USB_GetNextDescriptorOfType(uint16_t* const BytesRem,
-                                                        void** const CurrConfigLoc,
-                                                        const uint8_t Type)
-                                                        ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
-
-                       /** Skips to the next sub-descriptor inside the configuration descriptor of the specified type value,
-                        *  which must come before a descriptor of the second given type value. If the BeforeType type
-                        *  descriptor is reached first, the number of bytes remaining to process is set to zero and the
-                        *  function exits. The bytes remaining value is automatically decremented.
-                        *
-                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
-                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
-                        * \param[in]     Type           Descriptor type value to search for.
-                        * \param[in]     BeforeType     Descriptor type value which must not be reached before the given Type descriptor.
-                        */
-                       void USB_GetNextDescriptorOfTypeBefore(uint16_t* const BytesRem,
-                                                              void** const CurrConfigLoc,
-                                                              const uint8_t Type,
-                                                              const uint8_t BeforeType)
-                                                              ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
-
-                       /** Skips to the next sub-descriptor inside the configuration descriptor of the specified type value,
-                        *  which must come after a descriptor of the second given type value. The bytes remaining value is
-                        *  automatically decremented.
-                        *
-                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
-                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
-                        * \param[in]     Type           Descriptor type value to search for.
-                        * \param[in]     AfterType      Descriptor type value which must be reached before the given Type descriptor.
-                        */
-                       void USB_GetNextDescriptorOfTypeAfter(uint16_t* const BytesRem,
-                                                             void** const CurrConfigLoc,
-                                                             const uint8_t Type,
-                                                             const uint8_t AfterType)
-                                                             ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
-
-                       /** Searches for the next descriptor in the given configuration descriptor using a pre-made comparator
-                        *  function. The routine updates the position and remaining configuration descriptor bytes values
-                        *  automatically. If a comparator routine fails a search, the descriptor pointer is retreated back
-                        *  so that the next descriptor search invocation will start from the descriptor which first caused the
-                        *  original search to fail. This behavior allows for one comparator to be used immediately after another
-                        *  has failed, starting the second search from the descriptor which failed the first.
-                        *
-                        *  Comparator functions should be standard functions which accept a pointer to the header of the current
-                        *  descriptor inside the configuration descriptor which is being compared, and should return a value from
-                        *  the \ref DSearch_Return_ErrorCodes_t enum as a uint8_t value.
-                        *
-                        *  \note This function is available in USB Host mode only.
-                        *
-                        *  \param[in,out] BytesRem           Pointer to an int storing the remaining bytes in the configuration descriptor.
-                        *  \param[in,out] CurrConfigLoc      Pointer to the current position in the configuration descriptor.
-                        *  \param[in]     ComparatorRoutine  Name of the comparator search function to use on the configuration descriptor.
-                        *
-                        *  \return Value of one of the members of the \ref DSearch_Comp_Return_ErrorCodes_t enum.
-                        *
-                        *  Usage Example:
-                        *  \code
-                        *  uint8_t EndpointSearcher(void* CurrentDescriptor); // Comparator Prototype
-                        *  
-                        *  uint8_t EndpointSearcher(void* CurrentDescriptor)
-                        *  {
-                        *     if (DESCRIPTOR_TYPE(CurrentDescriptor) == DTYPE_Endpoint)
-                        *         return DESCRIPTOR_SEARCH_Found;
-                        *     else
-                        *         return DESCRIPTOR_SEARCH_NotFound;
-                        *  }
-                        *  
-                        *  //...
-                        *  
-                        *  // After retrieving configuration descriptor:
-                        *  if (USB_Host_GetNextDescriptorComp(&BytesRemaining, &CurrentConfigLoc, EndpointSearcher) ==
-                        *      Descriptor_Search_Comp_Found)
-                        *  {
-                        *      // Do something with the endpoint descriptor
-                        *  }
-                        *  \endcode
-                        */
-                       uint8_t USB_GetNextDescriptorComp(uint16_t* const BytesRem,
-                                                         void** const CurrConfigLoc,
-                                                         ConfigComparatorPtr_t const ComparatorRoutine);
-
-               /* Inline Functions: */
-                       /** Skips over the current sub-descriptor inside the configuration descriptor, so that the pointer then
-                           points to the next sub-descriptor. The bytes remaining value is automatically decremented.
-                        *
-                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
-                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
-                        */
-                       static inline void USB_GetNextDescriptor(uint16_t* const BytesRem,
-                                                                void** CurrConfigLoc) ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
-                       static inline void USB_GetNextDescriptor(uint16_t* const BytesRem,
-                                                                void** CurrConfigLoc)
-                       {
-                               uint16_t CurrDescriptorSize = DESCRIPTOR_CAST(*CurrConfigLoc, USB_Descriptor_Header_t).Size;
-
-                               if (*BytesRem < CurrDescriptorSize)
-                                 CurrDescriptorSize = *BytesRem;
-
-                               *CurrConfigLoc  = (void*)((uintptr_t)*CurrConfigLoc + CurrDescriptorSize);
-                               *BytesRem      -= CurrDescriptorSize;
-                       }
-
-       /* Disable C linkage for C++ Compilers: */
-               #if defined(__cplusplus)
-                       }
-               #endif
-
-#endif
-
-/** @} */
-
diff --git a/LUFA/Drivers/USB/Core/ConfigDescriptors.c b/LUFA/Drivers/USB/Core/ConfigDescriptors.c
new file mode 100644 (file)
index 0000000..47332d8
--- /dev/null
@@ -0,0 +1,146 @@
+/*
+             LUFA Library
+     Copyright (C) Dean Camera, 2012.
+
+  dean [at] fourwalledcubicle [dot] com
+           www.lufa-lib.org
+*/
+
+/*
+  Copyright 2012  Dean Camera (dean [at] fourwalledcubicle [dot] com)
+
+  Permission to use, copy, modify, distribute, and sell this
+  software and its documentation for any purpose is hereby granted
+  without fee, provided that the above copyright notice appear in
+  all copies and that both that the copyright notice and this
+  permission notice and warranty disclaimer appear in supporting
+  documentation, and that the name of the author not be used in
+  advertising or publicity pertaining to distribution of the
+  software without specific, written prior permission.
+
+  The author disclaim all warranties with regard to this
+  software, including all implied warranties of merchantability
+  and fitness.  In no event shall the author be liable for any
+  special, indirect or consequential damages or any damages
+  whatsoever resulting from loss of use, data or profits, whether
+  in an action of contract, negligence or other tortious action,
+  arising out of or in connection with the use or performance of
+  this software.
+*/
+
+#define  __INCLUDE_FROM_USB_DRIVER
+#include "ConfigDescriptors.h"
+
+#if defined(USB_CAN_BE_HOST)
+uint8_t USB_Host_GetDeviceConfigDescriptor(const uint8_t ConfigNumber,
+                                           uint16_t* const ConfigSizePtr,
+                                           void* const BufferPtr,
+                                           const uint16_t BufferSize)
+{
+       uint8_t ErrorCode;
+       uint8_t ConfigHeader[sizeof(USB_Descriptor_Configuration_Header_t)];
+
+       USB_ControlRequest = (USB_Request_Header_t)
+               {
+                       .bmRequestType = (REQDIR_DEVICETOHOST | REQTYPE_STANDARD | REQREC_DEVICE),
+                       .bRequest      = REQ_GetDescriptor,
+                       .wValue        = ((DTYPE_Configuration << 8) | (ConfigNumber - 1)),
+                       .wIndex        = 0,
+                       .wLength       = sizeof(USB_Descriptor_Configuration_Header_t),
+               };
+
+       Pipe_SelectPipe(PIPE_CONTROLPIPE);
+
+       if ((ErrorCode = USB_Host_SendControlRequest(ConfigHeader)) != HOST_SENDCONTROL_Successful)
+         return ErrorCode;
+
+       *ConfigSizePtr = le16_to_cpu(DESCRIPTOR_PCAST(ConfigHeader, USB_Descriptor_Configuration_Header_t)->TotalConfigurationSize);
+
+       if (*ConfigSizePtr > BufferSize)
+         return HOST_GETCONFIG_BuffOverflow;
+
+       USB_ControlRequest.wLength = *ConfigSizePtr;
+
+       if ((ErrorCode = USB_Host_SendControlRequest(BufferPtr)) != HOST_SENDCONTROL_Successful)
+         return ErrorCode;
+
+       if (DESCRIPTOR_TYPE(BufferPtr) != DTYPE_Configuration)
+         return HOST_GETCONFIG_InvalidData;
+
+       return HOST_GETCONFIG_Successful;
+}
+#endif
+
+void USB_GetNextDescriptorOfType(uint16_t* const BytesRem,
+                                 void** const CurrConfigLoc,
+                                 const uint8_t Type)
+{
+       while (*BytesRem)
+       {
+               USB_GetNextDescriptor(BytesRem, CurrConfigLoc);
+
+               if (DESCRIPTOR_TYPE(*CurrConfigLoc) == Type)
+                 return;
+       }
+}
+
+void USB_GetNextDescriptorOfTypeBefore(uint16_t* const BytesRem,
+                                       void** const CurrConfigLoc,
+                                       const uint8_t Type,
+                                       const uint8_t BeforeType)
+{
+       while (*BytesRem)
+       {
+               USB_GetNextDescriptor(BytesRem, CurrConfigLoc);
+
+               if (DESCRIPTOR_TYPE(*CurrConfigLoc) == Type)
+               {
+                       return;
+               }
+               else if (DESCRIPTOR_TYPE(*CurrConfigLoc) == BeforeType)
+               {
+                       *BytesRem = 0;
+                       return;
+               }
+       }
+}
+
+void USB_GetNextDescriptorOfTypeAfter(uint16_t* const BytesRem,
+                                      void** const CurrConfigLoc,
+                                      const uint8_t Type,
+                                      const uint8_t AfterType)
+{
+       USB_GetNextDescriptorOfType(BytesRem, CurrConfigLoc, AfterType);
+
+       if (*BytesRem)
+         USB_GetNextDescriptorOfType(BytesRem, CurrConfigLoc, Type);
+}
+
+uint8_t USB_GetNextDescriptorComp(uint16_t* const BytesRem,
+                                  void** const CurrConfigLoc,
+                                  ConfigComparatorPtr_t const ComparatorRoutine)
+{
+       uint8_t ErrorCode;
+
+       while (*BytesRem)
+       {
+               uint8_t* PrevDescLoc  = *CurrConfigLoc;
+               uint16_t PrevBytesRem = *BytesRem;
+
+               USB_GetNextDescriptor(BytesRem, CurrConfigLoc);
+
+               if ((ErrorCode = ComparatorRoutine(*CurrConfigLoc)) != DESCRIPTOR_SEARCH_NotFound)
+               {
+                       if (ErrorCode == DESCRIPTOR_SEARCH_Fail)
+                       {
+                               *CurrConfigLoc = PrevDescLoc;
+                               *BytesRem      = PrevBytesRem;
+                       }
+
+                       return ErrorCode;
+               }
+       }
+
+       return DESCRIPTOR_SEARCH_COMP_EndOfDescriptor;
+}
+
diff --git a/LUFA/Drivers/USB/Core/ConfigDescriptors.h b/LUFA/Drivers/USB/Core/ConfigDescriptors.h
new file mode 100644 (file)
index 0000000..97fb39b
--- /dev/null
@@ -0,0 +1,286 @@
+/*
+             LUFA Library
+     Copyright (C) Dean Camera, 2012.
+
+  dean [at] fourwalledcubicle [dot] com
+           www.lufa-lib.org
+*/
+
+/*
+  Copyright 2012  Dean Camera (dean [at] fourwalledcubicle [dot] com)
+
+  Permission to use, copy, modify, distribute, and sell this
+  software and its documentation for any purpose is hereby granted
+  without fee, provided that the above copyright notice appear in
+  all copies and that both that the copyright notice and this
+  permission notice and warranty disclaimer appear in supporting
+  documentation, and that the name of the author not be used in
+  advertising or publicity pertaining to distribution of the
+  software without specific, written prior permission.
+
+  The author disclaim all warranties with regard to this
+  software, including all implied warranties of merchantability
+  and fitness.  In no event shall the author be liable for any
+  special, indirect or consequential damages or any damages
+  whatsoever resulting from loss of use, data or profits, whether
+  in an action of contract, negligence or other tortious action,
+  arising out of or in connection with the use or performance of
+  this software.
+*/
+
+/** \file
+ *  \brief USB Configuration Descriptor definitions.
+ *  \copydetails Group_ConfigDescriptorParser
+ *
+ *  \note This file should not be included directly. It is automatically included as needed by the USB driver
+ *        dispatch header located in LUFA/Drivers/USB/USB.h.
+ */
+
+/** \ingroup Group_StdDescriptors
+ *  \defgroup Group_ConfigDescriptorParser Configuration Descriptor Parser
+ *  \brief USB Configuration Descriptor definitions.
+ *
+ *  This section of the library gives a friendly API which can be used in host applications to easily
+ *  parse an attached device's configuration descriptor so that endpoint, interface and other descriptor
+ *  data can be extracted and used as needed.
+ *
+ *  @{
+ */
+
+#ifndef __CONFIGDESCRIPTOR_H__
+#define __CONFIGDESCRIPTOR_H__
+
+       /* Includes: */
+               #include "../../../Common/Common.h"
+               #include "USBMode.h"
+               #include "HostStandardReq.h"
+               #include "StdDescriptors.h"
+
+       /* Enable C linkage for C++ Compilers: */
+               #if defined(__cplusplus)
+                       extern "C" {
+               #endif
+
+       /* Preprocessor Checks: */
+               #if !defined(__INCLUDE_FROM_USB_DRIVER)
+                       #error Do not include this file directly. Include LUFA/Drivers/USB/USB.h instead.
+               #endif
+
+       /* Public Interface - May be used in end-application: */
+               /* Macros: */
+                       /** Casts a pointer to a descriptor inside the configuration descriptor into a pointer to the given
+                        *  descriptor type.
+                        *
+                        *  Usage Example:
+                        *  \code
+                        *  uint8_t* CurrDescriptor = &ConfigDescriptor[0]; // Pointing to the configuration header
+                        *  USB_Descriptor_Configuration_Header_t* ConfigHeaderPtr = DESCRIPTOR_PCAST(CurrDescriptor,
+                        *                                                           USB_Descriptor_Configuration_Header_t);
+                        *  
+                        *  // Can now access elements of the configuration header struct using the -> indirection operator
+                        *  \endcode
+                        */
+                       #define DESCRIPTOR_PCAST(DescriptorPtr, Type) ((Type*)(DescriptorPtr))
+
+                       /** Casts a pointer to a descriptor inside the configuration descriptor into the given descriptor
+                        *  type (as an actual struct instance rather than a pointer to a struct).
+                        *
+                        *  Usage Example:
+                        *  \code
+                        *  uint8_t* CurrDescriptor = &ConfigDescriptor[0]; // Pointing to the configuration header
+                        *  USB_Descriptor_Configuration_Header_t ConfigHeader = DESCRIPTOR_CAST(CurrDescriptor,
+                        *                                                       USB_Descriptor_Configuration_Header_t);
+                        *  
+                        *  // Can now access elements of the configuration header struct using the . operator
+                        *  \endcode
+                        */
+                       #define DESCRIPTOR_CAST(DescriptorPtr, Type)  (*DESCRIPTOR_PCAST(DescriptorPtr, Type))
+
+                       /** Returns the descriptor's type, expressed as the 8-bit type value in the header of the descriptor.
+                        *  This value's meaning depends on the descriptor's placement in the descriptor, but standard type
+                        *  values can be accessed in the \ref USB_DescriptorTypes_t enum.
+                        */
+                       #define DESCRIPTOR_TYPE(DescriptorPtr)    DESCRIPTOR_PCAST(DescriptorPtr, USB_Descriptor_Header_t)->Type
+
+                       /** Returns the descriptor's size, expressed as the 8-bit value indicating the number of bytes. */
+                       #define DESCRIPTOR_SIZE(DescriptorPtr)    DESCRIPTOR_PCAST(DescriptorPtr, USB_Descriptor_Header_t)->Size
+
+               /* Type Defines: */
+                       /** Type define for a Configuration Descriptor comparator function (function taking a pointer to an array
+                        *  of type void, returning a uint8_t value).
+                        *
+                        *  \see \ref USB_GetNextDescriptorComp function for more details.
+                        */
+                       typedef uint8_t (* ConfigComparatorPtr_t)(void*);
+
+               /* Enums: */
+                       /** Enum for the possible return codes of the \ref USB_Host_GetDeviceConfigDescriptor() function. */
+                       enum USB_Host_GetConfigDescriptor_ErrorCodes_t
+                       {
+                               HOST_GETCONFIG_Successful       = 0, /**< No error occurred while retrieving the configuration descriptor. */
+                               HOST_GETCONFIG_DeviceDisconnect = 1, /**< The attached device was disconnected while retrieving the configuration
+                                                                       * descriptor.
+                                                                       */
+                               HOST_GETCONFIG_PipeError        = 2, /**< An error occurred in the pipe while sending the request. */
+                               HOST_GETCONFIG_SetupStalled     = 3, /**< The attached device stalled the request to retrieve the configuration
+                                                                       * descriptor.
+                                                                       */
+                               HOST_GETCONFIG_SoftwareTimeOut  = 4, /**< The request or data transfer timed out. */
+                               HOST_GETCONFIG_BuffOverflow     = 5, /**< The device's configuration descriptor is too large to fit into the allocated
+                                                                       * buffer.
+                                                                       */
+                               HOST_GETCONFIG_InvalidData      = 6, /**< The device returned invalid configuration descriptor data. */
+                       };
+
+                       /** Enum for return values of a descriptor comparator function. */
+                       enum DSearch_Return_ErrorCodes_t
+                       {
+                               DESCRIPTOR_SEARCH_Found                = 0, /**< Current descriptor matches comparator criteria. */
+                               DESCRIPTOR_SEARCH_Fail                 = 1, /**< No further descriptor could possibly match criteria, fail the search. */
+                               DESCRIPTOR_SEARCH_NotFound             = 2, /**< Current descriptor does not match comparator criteria. */
+                       };
+
+                       /** Enum for return values of \ref USB_GetNextDescriptorComp(). */
+                       enum DSearch_Comp_Return_ErrorCodes_t
+                       {
+                               DESCRIPTOR_SEARCH_COMP_Found           = 0, /**< Configuration descriptor now points to descriptor which matches
+                                                                            *   search criteria of the given comparator function. */
+                               DESCRIPTOR_SEARCH_COMP_Fail            = 1, /**< Comparator function returned \ref DESCRIPTOR_SEARCH_Fail. */
+                               DESCRIPTOR_SEARCH_COMP_EndOfDescriptor = 2, /**< End of configuration descriptor reached before match found. */
+                       };
+
+               /* Function Prototypes: */
+                       /** Retrieves the configuration descriptor data from an attached device via a standard request into a buffer,
+                        *  including validity and size checking to prevent a buffer overflow.
+                        *
+                        *  \param[in]     ConfigNumber   Device configuration descriptor number to fetch from the device (usually set to 1 for
+                        *                                single configuration devices).
+                        *  \param[in,out] ConfigSizePtr  Pointer to a location for storing the retrieved configuration descriptor size.
+                        *  \param[out]    BufferPtr      Pointer to the buffer for storing the configuration descriptor data.
+                        *  \param[out]    BufferSize     Size of the allocated buffer where the configuration descriptor is to be stored.
+                        *
+                        *  \return A value from the \ref USB_Host_GetConfigDescriptor_ErrorCodes_t enum.
+                        */
+                       uint8_t USB_Host_GetDeviceConfigDescriptor(const uint8_t ConfigNumber,
+                                                                  uint16_t* const ConfigSizePtr,
+                                                                  void* const BufferPtr,
+                                                                  const uint16_t BufferSize) ATTR_NON_NULL_PTR_ARG(2) ATTR_NON_NULL_PTR_ARG(3);
+
+                       /** Skips to the next sub-descriptor inside the configuration descriptor of the specified type value.
+                        *  The bytes remaining value is automatically decremented.
+                        *
+                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
+                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
+                        * \param[in]     Type           Descriptor type value to search for.
+                        */
+                       void USB_GetNextDescriptorOfType(uint16_t* const BytesRem,
+                                                        void** const CurrConfigLoc,
+                                                        const uint8_t Type)
+                                                        ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
+
+                       /** Skips to the next sub-descriptor inside the configuration descriptor of the specified type value,
+                        *  which must come before a descriptor of the second given type value. If the BeforeType type
+                        *  descriptor is reached first, the number of bytes remaining to process is set to zero and the
+                        *  function exits. The bytes remaining value is automatically decremented.
+                        *
+                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
+                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
+                        * \param[in]     Type           Descriptor type value to search for.
+                        * \param[in]     BeforeType     Descriptor type value which must not be reached before the given Type descriptor.
+                        */
+                       void USB_GetNextDescriptorOfTypeBefore(uint16_t* const BytesRem,
+                                                              void** const CurrConfigLoc,
+                                                              const uint8_t Type,
+                                                              const uint8_t BeforeType)
+                                                              ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
+
+                       /** Skips to the next sub-descriptor inside the configuration descriptor of the specified type value,
+                        *  which must come after a descriptor of the second given type value. The bytes remaining value is
+                        *  automatically decremented.
+                        *
+                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
+                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
+                        * \param[in]     Type           Descriptor type value to search for.
+                        * \param[in]     AfterType      Descriptor type value which must be reached before the given Type descriptor.
+                        */
+                       void USB_GetNextDescriptorOfTypeAfter(uint16_t* const BytesRem,
+                                                             void** const CurrConfigLoc,
+                                                             const uint8_t Type,
+                                                             const uint8_t AfterType)
+                                                             ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
+
+                       /** Searches for the next descriptor in the given configuration descriptor using a pre-made comparator
+                        *  function. The routine updates the position and remaining configuration descriptor bytes values
+                        *  automatically. If a comparator routine fails a search, the descriptor pointer is retreated back
+                        *  so that the next descriptor search invocation will start from the descriptor which first caused the
+                        *  original search to fail. This behavior allows for one comparator to be used immediately after another
+                        *  has failed, starting the second search from the descriptor which failed the first.
+                        *
+                        *  Comparator functions should be standard functions which accept a pointer to the header of the current
+                        *  descriptor inside the configuration descriptor which is being compared, and should return a value from
+                        *  the \ref DSearch_Return_ErrorCodes_t enum as a uint8_t value.
+                        *
+                        *  \note This function is available in USB Host mode only.
+                        *
+                        *  \param[in,out] BytesRem           Pointer to an int storing the remaining bytes in the configuration descriptor.
+                        *  \param[in,out] CurrConfigLoc      Pointer to the current position in the configuration descriptor.
+                        *  \param[in]     ComparatorRoutine  Name of the comparator search function to use on the configuration descriptor.
+                        *
+                        *  \return Value of one of the members of the \ref DSearch_Comp_Return_ErrorCodes_t enum.
+                        *
+                        *  Usage Example:
+                        *  \code
+                        *  uint8_t EndpointSearcher(void* CurrentDescriptor); // Comparator Prototype
+                        *  
+                        *  uint8_t EndpointSearcher(void* CurrentDescriptor)
+                        *  {
+                        *     if (DESCRIPTOR_TYPE(CurrentDescriptor) == DTYPE_Endpoint)
+                        *         return DESCRIPTOR_SEARCH_Found;
+                        *     else
+                        *         return DESCRIPTOR_SEARCH_NotFound;
+                        *  }
+                        *  
+                        *  //...
+                        *  
+                        *  // After retrieving configuration descriptor:
+                        *  if (USB_Host_GetNextDescriptorComp(&BytesRemaining, &CurrentConfigLoc, EndpointSearcher) ==
+                        *      Descriptor_Search_Comp_Found)
+                        *  {
+                        *      // Do something with the endpoint descriptor
+                        *  }
+                        *  \endcode
+                        */
+                       uint8_t USB_GetNextDescriptorComp(uint16_t* const BytesRem,
+                                                         void** const CurrConfigLoc,
+                                                         ConfigComparatorPtr_t const ComparatorRoutine);
+
+               /* Inline Functions: */
+                       /** Skips over the current sub-descriptor inside the configuration descriptor, so that the pointer then
+                           points to the next sub-descriptor. The bytes remaining value is automatically decremented.
+                        *
+                        * \param[in,out] BytesRem       Pointer to the number of bytes remaining of the configuration descriptor.
+                        * \param[in,out] CurrConfigLoc  Pointer to the current descriptor inside the configuration descriptor.
+                        */
+                       static inline void USB_GetNextDescriptor(uint16_t* const BytesRem,
+                                                                void** CurrConfigLoc) ATTR_NON_NULL_PTR_ARG(1) ATTR_NON_NULL_PTR_ARG(2);
+                       static inline void USB_GetNextDescriptor(uint16_t* const BytesRem,
+                                                                void** CurrConfigLoc)
+                       {
+                               uint16_t CurrDescriptorSize = DESCRIPTOR_CAST(*CurrConfigLoc, USB_Descriptor_Header_t).Size;
+
+                               if (*BytesRem < CurrDescriptorSize)
+                                 CurrDescriptorSize = *BytesRem;
+
+                               *CurrConfigLoc  = (void*)((uintptr_t)*CurrConfigLoc + CurrDescriptorSize);
+                               *BytesRem      -= CurrDescriptorSize;
+                       }
+
+       /* Disable C linkage for C++ Compilers: */
+               #if defined(__cplusplus)
+                       }
+               #endif
+
+#endif
+
+/** @} */
+
index 626635c..512f702 100644 (file)
@@ -41,7 +41,7 @@
  *
  *  \section Sec_Dependencies Module Source Dependencies
  *  The following files must be built with any user project that uses this module:
- *    - LUFA/Drivers/USB/Core/ConfigDescriptor.c <i>(Makefile source module name: LUFA_SRC_USB)</i>
+ *    - LUFA/Drivers/USB/Core/ConfigDescriptors.c <i>(Makefile source module name: LUFA_SRC_USB)</i>
  *    - LUFA/Drivers/USB/Core/DeviceStandardReq.c <i>(Makefile source module name: LUFA_SRC_USB)</i>
  *    - LUFA/Drivers/USB/Core/Events.c <i>(Makefile source module name: LUFA_SRC_USB)</i>
  *    - LUFA/Drivers/USB/Core/HostStandardReq.c <i>(Makefile source module name: LUFA_SRC_USB)</i>
                #include "Core/USBTask.h"
                #include "Core/Events.h"
                #include "Core/StdDescriptors.h"
-               #include "Core/ConfigDescriptor.h"
+               #include "Core/ConfigDescriptors.h"
                #include "Core/USBController.h"
                #include "Core/USBInterrupt.h"
 
index ec8e65b..f4b4111 100644 (file)
@@ -22,16 +22,18 @@ ifeq ($(MAKELEVEL), 10)
    $(error EMERGENCY ABORT: INFINITE RECURSION DETECTED)
 endif
 
-# If building without a per-project object directory, we can't build in parallel
+# Need to special-case building without a per-project object directory
 ifeq ($(OBJDIR),)
-   .NOTPARALLEL:
-
-   # Ensure projects are pre-cleaned if the target is the default or "all"
+   # If no target specified, force "clean all" and disallow parallel build   
    ifeq ($(MAKECMDGOALS),)
       MAKECMDGOALS := clean all
+      .NOTPARALLEL:
    endif
+
+   # If one of the targets is to build, force "clean" beforehand and disallow parallel build   
    ifneq ($(findstring all, $(MAKECMDGOALS)),)
       MAKECMDGOALS := clean $(MAKECMDGOALS)
+      .NOTPARALLEL:
    endif
 endif
 
index 8005f44..a134dc0 100644 (file)
--- a/makefile
+++ b/makefile
@@ -14,6 +14,7 @@
 # "make help" for additional target build information within a specific project.
 
 all:
+
 %:
        @echo Executing \"make $@\" on all LUFA library elements.
        @echo