Ver código fonte

Initial release

Dmitry 9 anos atrás
pai
commit
9f83b1a864

+ 2 - 0
.gitignore

@@ -0,0 +1,2 @@
+src/usb_32l0.c
+html/*

+ 2428 - 0
Doxyfile

@@ -0,0 +1,2428 @@
+# Doxyfile 1.8.11
+
+# This file describes the settings to be used by the documentation system
+# doxygen (www.doxygen.org) for a project.
+#
+# All text after a double hash (##) is considered a comment and is placed in
+# front of the TAG it is preceding.
+#
+# All text after a single hash (#) is considered a comment and will be ignored.
+# The format is:
+# TAG = value [value, ...]
+# For lists, items can also be appended using:
+# TAG += value [value, ...]
+# Values that contain spaces should be placed between quotes (\" \").
+
+#---------------------------------------------------------------------------
+# Project related configuration options
+#---------------------------------------------------------------------------
+
+# This tag specifies the encoding used for all characters in the config file
+# that follow. The default is UTF-8 which is also the encoding used for all text
+# before the first occurrence of this tag. Doxygen uses libiconv (or the iconv
+# built into libc) for the transcoding. See http://www.gnu.org/software/libiconv
+# for the list of possible encodings.
+# The default value is: UTF-8.
+
+DOXYFILE_ENCODING      = UTF-8
+
+# The PROJECT_NAME tag is a single word (or a sequence of words surrounded by
+# double-quotes, unless you are using Doxywizard) that should identify the
+# project for which the documentation is generated. This name is used in the
+# title of most generated pages and in a few other places.
+# The default value is: My Project.
+
+PROJECT_NAME           = "Lightweight USB stack"
+
+# The PROJECT_NUMBER tag can be used to enter a project or revision number. This
+# could be handy for archiving the generated documentation or if some version
+# control system is used.
+
+PROJECT_NUMBER         = 1.0
+
+# Using the PROJECT_BRIEF tag one can provide an optional one line description
+# for a project that appears at the top of each page and should give viewer a
+# quick idea about the purpose of the project. Keep the description short.
+
+PROJECT_BRIEF          =
+
+# With the PROJECT_LOGO tag one can specify a logo or an icon that is included
+# in the documentation. The maximum height of the logo should not exceed 55
+# pixels and the maximum width should not exceed 200 pixels. Doxygen will copy
+# the logo to the output directory.
+
+PROJECT_LOGO           =
+
+# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) path
+# into which the generated documentation will be written. If a relative path is
+# entered, it will be relative to the location where doxygen was started. If
+# left blank the current directory will be used.
+
+OUTPUT_DIRECTORY       =
+
+# If the CREATE_SUBDIRS tag is set to YES then doxygen will create 4096 sub-
+# directories (in 2 levels) under the output directory of each output format and
+# will distribute the generated files over these directories. Enabling this
+# option can be useful when feeding doxygen a huge amount of source files, where
+# putting all generated files in the same directory would otherwise causes
+# performance problems for the file system.
+# The default value is: NO.
+
+CREATE_SUBDIRS         = YES
+
+# If the ALLOW_UNICODE_NAMES tag is set to YES, doxygen will allow non-ASCII
+# characters to appear in the names of generated files. If set to NO, non-ASCII
+# characters will be escaped, for example _xE3_x81_x84 will be used for Unicode
+# U+3044.
+# The default value is: NO.
+
+ALLOW_UNICODE_NAMES    = NO
+
+# The OUTPUT_LANGUAGE tag is used to specify the language in which all
+# documentation generated by doxygen is written. Doxygen will use this
+# information to generate all constant output in the proper language.
+# Possible values are: Afrikaans, Arabic, Armenian, Brazilian, Catalan, Chinese,
+# Chinese-Traditional, Croatian, Czech, Danish, Dutch, English (United States),
+# Esperanto, Farsi (Persian), Finnish, French, German, Greek, Hungarian,
+# Indonesian, Italian, Japanese, Japanese-en (Japanese with English messages),
+# Korean, Korean-en (Korean with English messages), Latvian, Lithuanian,
+# Macedonian, Norwegian, Persian (Farsi), Polish, Portuguese, Romanian, Russian,
+# Serbian, Serbian-Cyrillic, Slovak, Slovene, Spanish, Swedish, Turkish,
+# Ukrainian and Vietnamese.
+# The default value is: English.
+
+OUTPUT_LANGUAGE        = English
+
+# If the BRIEF_MEMBER_DESC tag is set to YES, doxygen will include brief member
+# descriptions after the members that are listed in the file and class
+# documentation (similar to Javadoc). Set to NO to disable this.
+# The default value is: YES.
+
+BRIEF_MEMBER_DESC      = YES
+
+# If the REPEAT_BRIEF tag is set to YES, doxygen will prepend the brief
+# description of a member or function before the detailed description
+#
+# Note: If both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the
+# brief descriptions will be completely suppressed.
+# The default value is: YES.
+
+REPEAT_BRIEF           = YES
+
+# This tag implements a quasi-intelligent brief description abbreviator that is
+# used to form the text in various listings. Each string in this list, if found
+# as the leading text of the brief description, will be stripped from the text
+# and the result, after processing the whole list, is used as the annotated
+# text. Otherwise, the brief description is used as-is. If left blank, the
+# following values are used ($name is automatically replaced with the name of
+# the entity):The $name class, The $name widget, The $name file, is, provides,
+# specifies, contains, represents, a, an and the.
+
+ABBREVIATE_BRIEF       =
+
+# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then
+# doxygen will generate a detailed section even if there is only a brief
+# description.
+# The default value is: NO.
+
+ALWAYS_DETAILED_SEC    = NO
+
+# If the INLINE_INHERITED_MEMB tag is set to YES, doxygen will show all
+# inherited members of a class in the documentation of that class as if those
+# members were ordinary class members. Constructors, destructors and assignment
+# operators of the base classes will not be shown.
+# The default value is: NO.
+
+INLINE_INHERITED_MEMB  = NO
+
+# If the FULL_PATH_NAMES tag is set to YES, doxygen will prepend the full path
+# before files name in the file list and in the header files. If set to NO the
+# shortest path that makes the file name unique will be used
+# The default value is: YES.
+
+FULL_PATH_NAMES        = NO
+
+# The STRIP_FROM_PATH tag can be used to strip a user-defined part of the path.
+# Stripping is only done if one of the specified strings matches the left-hand
+# part of the path. The tag can be used to show relative paths in the file list.
+# If left blank the directory from which doxygen is run is used as the path to
+# strip.
+#
+# Note that you can specify absolute paths here, but also relative paths, which
+# will be relative from the directory where doxygen is started.
+# This tag requires that the tag FULL_PATH_NAMES is set to YES.
+
+STRIP_FROM_PATH        =
+
+# The STRIP_FROM_INC_PATH tag can be used to strip a user-defined part of the
+# path mentioned in the documentation of a class, which tells the reader which
+# header file to include in order to use a class. If left blank only the name of
+# the header file containing the class definition is used. Otherwise one should
+# specify the list of include paths that are normally passed to the compiler
+# using the -I flag.
+
+STRIP_FROM_INC_PATH    =
+
+# If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter (but
+# less readable) file names. This can be useful is your file systems doesn't
+# support long names like on DOS, Mac, or CD-ROM.
+# The default value is: NO.
+
+SHORT_NAMES            = YES
+
+# If the JAVADOC_AUTOBRIEF tag is set to YES then doxygen will interpret the
+# first line (until the first dot) of a Javadoc-style comment as the brief
+# description. If set to NO, the Javadoc-style will behave just like regular Qt-
+# style comments (thus requiring an explicit @brief command for a brief
+# description.)
+# The default value is: NO.
+
+JAVADOC_AUTOBRIEF      = NO
+
+# If the QT_AUTOBRIEF tag is set to YES then doxygen will interpret the first
+# line (until the first dot) of a Qt-style comment as the brief description. If
+# set to NO, the Qt-style will behave just like regular Qt-style comments (thus
+# requiring an explicit \brief command for a brief description.)
+# The default value is: NO.
+
+QT_AUTOBRIEF           = NO
+
+# The MULTILINE_CPP_IS_BRIEF tag can be set to YES to make doxygen treat a
+# multi-line C++ special comment block (i.e. a block of //! or /// comments) as
+# a brief description. This used to be the default behavior. The new default is
+# to treat a multi-line C++ comment block as a detailed description. Set this
+# tag to YES if you prefer the old behavior instead.
+#
+# Note that setting this tag to YES also means that rational rose comments are
+# not recognized any more.
+# The default value is: NO.
+
+MULTILINE_CPP_IS_BRIEF = NO
+
+# If the INHERIT_DOCS tag is set to YES then an undocumented member inherits the
+# documentation from any documented member that it re-implements.
+# The default value is: YES.
+
+INHERIT_DOCS           = YES
+
+# If the SEPARATE_MEMBER_PAGES tag is set to YES then doxygen will produce a new
+# page for each member. If set to NO, the documentation of a member will be part
+# of the file/class/namespace that contains it.
+# The default value is: NO.
+
+SEPARATE_MEMBER_PAGES  = NO
+
+# The TAB_SIZE tag can be used to set the number of spaces in a tab. Doxygen
+# uses this value to replace tabs by spaces in code fragments.
+# Minimum value: 1, maximum value: 16, default value: 4.
+
+TAB_SIZE               = 4
+
+# This tag can be used to specify a number of aliases that act as commands in
+# the documentation. An alias has the form:
+# name=value
+# For example adding
+# "sideeffect=@par Side Effects:\n"
+# will allow you to put the command \sideeffect (or @sideeffect) in the
+# documentation, which will result in a user-defined paragraph with heading
+# "Side Effects:". You can put \n's in the value part of an alias to insert
+# newlines.
+
+ALIASES                =
+
+# This tag can be used to specify a number of word-keyword mappings (TCL only).
+# A mapping has the form "name=value". For example adding "class=itcl::class"
+# will allow you to use the command class in the itcl::class meaning.
+
+TCL_SUBST              =
+
+# Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C sources
+# only. Doxygen will then generate output that is more tailored for C. For
+# instance, some of the names that are used will be different. The list of all
+# members will be omitted, etc.
+# The default value is: NO.
+
+OPTIMIZE_OUTPUT_FOR_C  = YES
+
+# Set the OPTIMIZE_OUTPUT_JAVA tag to YES if your project consists of Java or
+# Python sources only. Doxygen will then generate output that is more tailored
+# for that language. For instance, namespaces will be presented as packages,
+# qualified scopes will look different, etc.
+# The default value is: NO.
+
+OPTIMIZE_OUTPUT_JAVA   = NO
+
+# Set the OPTIMIZE_FOR_FORTRAN tag to YES if your project consists of Fortran
+# sources. Doxygen will then generate output that is tailored for Fortran.
+# The default value is: NO.
+
+OPTIMIZE_FOR_FORTRAN   = NO
+
+# Set the OPTIMIZE_OUTPUT_VHDL tag to YES if your project consists of VHDL
+# sources. Doxygen will then generate output that is tailored for VHDL.
+# The default value is: NO.
+
+OPTIMIZE_OUTPUT_VHDL   = NO
+
+# Doxygen selects the parser to use depending on the extension of the files it
+# parses. With this tag you can assign which parser to use for a given
+# extension. Doxygen has a built-in mapping, but you can override or extend it
+# using this tag. The format is ext=language, where ext is a file extension, and
+# language is one of the parsers supported by doxygen: IDL, Java, Javascript,
+# C#, C, C++, D, PHP, Objective-C, Python, Fortran (fixed format Fortran:
+# FortranFixed, free formatted Fortran: FortranFree, unknown formatted Fortran:
+# Fortran. In the later case the parser tries to guess whether the code is fixed
+# or free formatted code, this is the default for Fortran type files), VHDL. For
+# instance to make doxygen treat .inc files as Fortran files (default is PHP),
+# and .f files as C (default is Fortran), use: inc=Fortran f=C.
+#
+# Note: For files without extension you can use no_extension as a placeholder.
+#
+# Note that for custom extensions you also need to set FILE_PATTERNS otherwise
+# the files are not read by doxygen.
+
+EXTENSION_MAPPING      =
+
+# If the MARKDOWN_SUPPORT tag is enabled then doxygen pre-processes all comments
+# according to the Markdown format, which allows for more readable
+# documentation. See http://daringfireball.net/projects/markdown/ for details.
+# The output of markdown processing is further processed by doxygen, so you can
+# mix doxygen, HTML, and XML commands with Markdown formatting. Disable only in
+# case of backward compatibilities issues.
+# The default value is: YES.
+
+MARKDOWN_SUPPORT       = YES
+
+# When enabled doxygen tries to link words that correspond to documented
+# classes, or namespaces to their corresponding documentation. Such a link can
+# be prevented in individual cases by putting a % sign in front of the word or
+# globally by setting AUTOLINK_SUPPORT to NO.
+# The default value is: YES.
+
+AUTOLINK_SUPPORT       = YES
+
+# If you use STL classes (i.e. std::string, std::vector, etc.) but do not want
+# to include (a tag file for) the STL sources as input, then you should set this
+# tag to YES in order to let doxygen match functions declarations and
+# definitions whose arguments contain STL classes (e.g. func(std::string);
+# versus func(std::string) {}). This also make the inheritance and collaboration
+# diagrams that involve STL classes more complete and accurate.
+# The default value is: NO.
+
+BUILTIN_STL_SUPPORT    = NO
+
+# If you use Microsoft's C++/CLI language, you should set this option to YES to
+# enable parsing support.
+# The default value is: NO.
+
+CPP_CLI_SUPPORT        = NO
+
+# Set the SIP_SUPPORT tag to YES if your project consists of sip (see:
+# http://www.riverbankcomputing.co.uk/software/sip/intro) sources only. Doxygen
+# will parse them like normal C++ but will assume all classes use public instead
+# of private inheritance when no explicit protection keyword is present.
+# The default value is: NO.
+
+SIP_SUPPORT            = NO
+
+# For Microsoft's IDL there are propget and propput attributes to indicate
+# getter and setter methods for a property. Setting this option to YES will make
+# doxygen to replace the get and set methods by a property in the documentation.
+# This will only work if the methods are indeed getting or setting a simple
+# type. If this is not the case, or you want to show the methods anyway, you
+# should set this option to NO.
+# The default value is: YES.
+
+IDL_PROPERTY_SUPPORT   = YES
+
+# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC
+# tag is set to YES then doxygen will reuse the documentation of the first
+# member in the group (if any) for the other members of the group. By default
+# all members of a group must be documented explicitly.
+# The default value is: NO.
+
+DISTRIBUTE_GROUP_DOC   = NO
+
+# If one adds a struct or class to a group and this option is enabled, then also
+# any nested class or struct is added to the same group. By default this option
+# is disabled and one has to add nested compounds explicitly via \ingroup.
+# The default value is: NO.
+
+GROUP_NESTED_COMPOUNDS = NO
+
+# Set the SUBGROUPING tag to YES to allow class member groups of the same type
+# (for instance a group of public functions) to be put as a subgroup of that
+# type (e.g. under the Public Functions section). Set it to NO to prevent
+# subgrouping. Alternatively, this can be done per class using the
+# \nosubgrouping command.
+# The default value is: YES.
+
+SUBGROUPING            = YES
+
+# When the INLINE_GROUPED_CLASSES tag is set to YES, classes, structs and unions
+# are shown inside the group in which they are included (e.g. using \ingroup)
+# instead of on a separate page (for HTML and Man pages) or section (for LaTeX
+# and RTF).
+#
+# Note that this feature does not work in combination with
+# SEPARATE_MEMBER_PAGES.
+# The default value is: NO.
+
+INLINE_GROUPED_CLASSES = NO
+
+# When the INLINE_SIMPLE_STRUCTS tag is set to YES, structs, classes, and unions
+# with only public data fields or simple typedef fields will be shown inline in
+# the documentation of the scope in which they are defined (i.e. file,
+# namespace, or group documentation), provided this scope is documented. If set
+# to NO, structs, classes, and unions are shown on a separate page (for HTML and
+# Man pages) or section (for LaTeX and RTF).
+# The default value is: NO.
+
+INLINE_SIMPLE_STRUCTS  = NO
+
+# When TYPEDEF_HIDES_STRUCT tag is enabled, a typedef of a struct, union, or
+# enum is documented as struct, union, or enum with the name of the typedef. So
+# typedef struct TypeS {} TypeT, will appear in the documentation as a struct
+# with name TypeT. When disabled the typedef will appear as a member of a file,
+# namespace, or class. And the struct will be named TypeS. This can typically be
+# useful for C code in case the coding convention dictates that all compound
+# types are typedef'ed and only the typedef is referenced, never the tag name.
+# The default value is: NO.
+
+TYPEDEF_HIDES_STRUCT   = YES
+
+# The size of the symbol lookup cache can be set using LOOKUP_CACHE_SIZE. This
+# cache is used to resolve symbols given their name and scope. Since this can be
+# an expensive process and often the same symbol appears multiple times in the
+# code, doxygen keeps a cache of pre-resolved symbols. If the cache is too small
+# doxygen will become slower. If the cache is too large, memory is wasted. The
+# cache size is given by this formula: 2^(16+LOOKUP_CACHE_SIZE). The valid range
+# is 0..9, the default is 0, corresponding to a cache size of 2^16=65536
+# symbols. At the end of a run doxygen will report the cache usage and suggest
+# the optimal cache size from a speed point of view.
+# Minimum value: 0, maximum value: 9, default value: 0.
+
+LOOKUP_CACHE_SIZE      = 0
+
+#---------------------------------------------------------------------------
+# Build related configuration options
+#---------------------------------------------------------------------------
+
+# If the EXTRACT_ALL tag is set to YES, doxygen will assume all entities in
+# documentation are documented, even if no documentation was available. Private
+# class members and static file members will be hidden unless the
+# EXTRACT_PRIVATE respectively EXTRACT_STATIC tags are set to YES.
+# Note: This will also disable the warnings about undocumented members that are
+# normally produced when WARNINGS is set to YES.
+# The default value is: NO.
+
+EXTRACT_ALL            = NO
+
+# If the EXTRACT_PRIVATE tag is set to YES, all private members of a class will
+# be included in the documentation.
+# The default value is: NO.
+
+EXTRACT_PRIVATE        = NO
+
+# If the EXTRACT_PACKAGE tag is set to YES, all members with package or internal
+# scope will be included in the documentation.
+# The default value is: NO.
+
+EXTRACT_PACKAGE        = NO
+
+# If the EXTRACT_STATIC tag is set to YES, all static members of a file will be
+# included in the documentation.
+# The default value is: NO.
+
+EXTRACT_STATIC         = NO
+
+# If the EXTRACT_LOCAL_CLASSES tag is set to YES, classes (and structs) defined
+# locally in source files will be included in the documentation. If set to NO,
+# only classes defined in header files are included. Does not have any effect
+# for Java sources.
+# The default value is: YES.
+
+EXTRACT_LOCAL_CLASSES  = YES
+
+# This flag is only useful for Objective-C code. If set to YES, local methods,
+# which are defined in the implementation section but not in the interface are
+# included in the documentation. If set to NO, only methods in the interface are
+# included.
+# The default value is: NO.
+
+EXTRACT_LOCAL_METHODS  = NO
+
+# If this flag is set to YES, the members of anonymous namespaces will be
+# extracted and appear in the documentation as a namespace called
+# 'anonymous_namespace{file}', where file will be replaced with the base name of
+# the file that contains the anonymous namespace. By default anonymous namespace
+# are hidden.
+# The default value is: NO.
+
+EXTRACT_ANON_NSPACES   = NO
+
+# If the HIDE_UNDOC_MEMBERS tag is set to YES, doxygen will hide all
+# undocumented members inside documented classes or files. If set to NO these
+# members will be included in the various overviews, but no documentation
+# section is generated. This option has no effect if EXTRACT_ALL is enabled.
+# The default value is: NO.
+
+HIDE_UNDOC_MEMBERS     = NO
+
+# If the HIDE_UNDOC_CLASSES tag is set to YES, doxygen will hide all
+# undocumented classes that are normally visible in the class hierarchy. If set
+# to NO, these classes will be included in the various overviews. This option
+# has no effect if EXTRACT_ALL is enabled.
+# The default value is: NO.
+
+HIDE_UNDOC_CLASSES     = YES
+
+# If the HIDE_FRIEND_COMPOUNDS tag is set to YES, doxygen will hide all friend
+# (class|struct|union) declarations. If set to NO, these declarations will be
+# included in the documentation.
+# The default value is: NO.
+
+HIDE_FRIEND_COMPOUNDS  = NO
+
+# If the HIDE_IN_BODY_DOCS tag is set to YES, doxygen will hide any
+# documentation blocks found inside the body of a function. If set to NO, these
+# blocks will be appended to the function's detailed documentation block.
+# The default value is: NO.
+
+HIDE_IN_BODY_DOCS      = NO
+
+# The INTERNAL_DOCS tag determines if documentation that is typed after a
+# \internal command is included. If the tag is set to NO then the documentation
+# will be excluded. Set it to YES to include the internal documentation.
+# The default value is: NO.
+
+INTERNAL_DOCS          = NO
+
+# If the CASE_SENSE_NAMES tag is set to NO then doxygen will only generate file
+# names in lower-case letters. If set to YES, upper-case letters are also
+# allowed. This is useful if you have classes or files whose names only differ
+# in case and if your file system supports case sensitive file names. Windows
+# and Mac users are advised to set this option to NO.
+# The default value is: system dependent.
+
+CASE_SENSE_NAMES       = YES
+
+# If the HIDE_SCOPE_NAMES tag is set to NO then doxygen will show members with
+# their full class and namespace scopes in the documentation. If set to YES, the
+# scope will be hidden.
+# The default value is: NO.
+
+HIDE_SCOPE_NAMES       = NO
+
+# If the HIDE_COMPOUND_REFERENCE tag is set to NO (default) then doxygen will
+# append additional text to a page's title, such as Class Reference. If set to
+# YES the compound reference will be hidden.
+# The default value is: NO.
+
+HIDE_COMPOUND_REFERENCE= NO
+
+# If the SHOW_INCLUDE_FILES tag is set to YES then doxygen will put a list of
+# the files that are included by a file in the documentation of that file.
+# The default value is: YES.
+
+SHOW_INCLUDE_FILES     = YES
+
+# If the SHOW_GROUPED_MEMB_INC tag is set to YES then Doxygen will add for each
+# grouped member an include statement to the documentation, telling the reader
+# which file to include in order to use the member.
+# The default value is: NO.
+
+SHOW_GROUPED_MEMB_INC  = NO
+
+# If the FORCE_LOCAL_INCLUDES tag is set to YES then doxygen will list include
+# files with double quotes in the documentation rather than with sharp brackets.
+# The default value is: NO.
+
+FORCE_LOCAL_INCLUDES   = NO
+
+# If the INLINE_INFO tag is set to YES then a tag [inline] is inserted in the
+# documentation for inline members.
+# The default value is: YES.
+
+INLINE_INFO            = YES
+
+# If the SORT_MEMBER_DOCS tag is set to YES then doxygen will sort the
+# (detailed) documentation of file and class members alphabetically by member
+# name. If set to NO, the members will appear in declaration order.
+# The default value is: YES.
+
+SORT_MEMBER_DOCS       = NO
+
+# If the SORT_BRIEF_DOCS tag is set to YES then doxygen will sort the brief
+# descriptions of file, namespace and class members alphabetically by member
+# name. If set to NO, the members will appear in declaration order. Note that
+# this will also influence the order of the classes in the class list.
+# The default value is: NO.
+
+SORT_BRIEF_DOCS        = NO
+
+# If the SORT_MEMBERS_CTORS_1ST tag is set to YES then doxygen will sort the
+# (brief and detailed) documentation of class members so that constructors and
+# destructors are listed first. If set to NO the constructors will appear in the
+# respective orders defined by SORT_BRIEF_DOCS and SORT_MEMBER_DOCS.
+# Note: If SORT_BRIEF_DOCS is set to NO this option is ignored for sorting brief
+# member documentation.
+# Note: If SORT_MEMBER_DOCS is set to NO this option is ignored for sorting
+# detailed member documentation.
+# The default value is: NO.
+
+SORT_MEMBERS_CTORS_1ST = NO
+
+# If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the hierarchy
+# of group names into alphabetical order. If set to NO the group names will
+# appear in their defined order.
+# The default value is: NO.
+
+SORT_GROUP_NAMES       = NO
+
+# If the SORT_BY_SCOPE_NAME tag is set to YES, the class list will be sorted by
+# fully-qualified names, including namespaces. If set to NO, the class list will
+# be sorted only by class name, not including the namespace part.
+# Note: This option is not very useful if HIDE_SCOPE_NAMES is set to YES.
+# Note: This option applies only to the class list, not to the alphabetical
+# list.
+# The default value is: NO.
+
+SORT_BY_SCOPE_NAME     = NO
+
+# If the STRICT_PROTO_MATCHING option is enabled and doxygen fails to do proper
+# type resolution of all parameters of a function it will reject a match between
+# the prototype and the implementation of a member function even if there is
+# only one candidate or it is obvious which candidate to choose by doing a
+# simple string match. By disabling STRICT_PROTO_MATCHING doxygen will still
+# accept a match between prototype and implementation in such cases.
+# The default value is: NO.
+
+STRICT_PROTO_MATCHING  = NO
+
+# The GENERATE_TODOLIST tag can be used to enable (YES) or disable (NO) the todo
+# list. This list is created by putting \todo commands in the documentation.
+# The default value is: YES.
+
+GENERATE_TODOLIST      = YES
+
+# The GENERATE_TESTLIST tag can be used to enable (YES) or disable (NO) the test
+# list. This list is created by putting \test commands in the documentation.
+# The default value is: YES.
+
+GENERATE_TESTLIST      = YES
+
+# The GENERATE_BUGLIST tag can be used to enable (YES) or disable (NO) the bug
+# list. This list is created by putting \bug commands in the documentation.
+# The default value is: YES.
+
+GENERATE_BUGLIST       = YES
+
+# The GENERATE_DEPRECATEDLIST tag can be used to enable (YES) or disable (NO)
+# the deprecated list. This list is created by putting \deprecated commands in
+# the documentation.
+# The default value is: YES.
+
+GENERATE_DEPRECATEDLIST= YES
+
+# The ENABLED_SECTIONS tag can be used to enable conditional documentation
+# sections, marked by \if <section_label> ... \endif and \cond <section_label>
+# ... \endcond blocks.
+
+ENABLED_SECTIONS       =
+
+# The MAX_INITIALIZER_LINES tag determines the maximum number of lines that the
+# initial value of a variable or macro / define can have for it to appear in the
+# documentation. If the initializer consists of more lines than specified here
+# it will be hidden. Use a value of 0 to hide initializers completely. The
+# appearance of the value of individual variables and macros / defines can be
+# controlled using \showinitializer or \hideinitializer command in the
+# documentation regardless of this setting.
+# Minimum value: 0, maximum value: 10000, default value: 30.
+
+MAX_INITIALIZER_LINES  =
+
+# Set the SHOW_USED_FILES tag to NO to disable the list of files generated at
+# the bottom of the documentation of classes and structs. If set to YES, the
+# list will mention the files that were used to generate the documentation.
+# The default value is: YES.
+
+SHOW_USED_FILES        = YES
+
+# Set the SHOW_FILES tag to NO to disable the generation of the Files page. This
+# will remove the Files entry from the Quick Index and from the Folder Tree View
+# (if specified).
+# The default value is: YES.
+
+SHOW_FILES             = YES
+
+# Set the SHOW_NAMESPACES tag to NO to disable the generation of the Namespaces
+# page. This will remove the Namespaces entry from the Quick Index and from the
+# Folder Tree View (if specified).
+# The default value is: YES.
+
+SHOW_NAMESPACES        = YES
+
+# The FILE_VERSION_FILTER tag can be used to specify a program or script that
+# doxygen should invoke to get the current version for each file (typically from
+# the version control system). Doxygen will invoke the program by executing (via
+# popen()) the command command input-file, where command is the value of the
+# FILE_VERSION_FILTER tag, and input-file is the name of an input file provided
+# by doxygen. Whatever the program writes to standard output is used as the file
+# version. For an example see the documentation.
+
+FILE_VERSION_FILTER    =
+
+# The LAYOUT_FILE tag can be used to specify a layout file which will be parsed
+# by doxygen. The layout file controls the global structure of the generated
+# output files in an output format independent way. To create the layout file
+# that represents doxygen's defaults, run doxygen with the -l option. You can
+# optionally specify a file name after the option, if omitted DoxygenLayout.xml
+# will be used as the name of the layout file.
+#
+# Note that if you run doxygen from a directory containing a file called
+# DoxygenLayout.xml, doxygen will parse it automatically even if the LAYOUT_FILE
+# tag is left empty.
+
+LAYOUT_FILE            =
+
+# The CITE_BIB_FILES tag can be used to specify one or more bib files containing
+# the reference definitions. This must be a list of .bib files. The .bib
+# extension is automatically appended if omitted. This requires the bibtex tool
+# to be installed. See also http://en.wikipedia.org/wiki/BibTeX for more info.
+# For LaTeX the style of the bibliography can be controlled using
+# LATEX_BIB_STYLE. To use this feature you need bibtex and perl available in the
+# search path. See also \cite for info how to create references.
+
+CITE_BIB_FILES         =
+
+#---------------------------------------------------------------------------
+# Configuration options related to warning and progress messages
+#---------------------------------------------------------------------------
+
+# The QUIET tag can be used to turn on/off the messages that are generated to
+# standard output by doxygen. If QUIET is set to YES this implies that the
+# messages are off.
+# The default value is: NO.
+
+QUIET                  = NO
+
+# The WARNINGS tag can be used to turn on/off the warning messages that are
+# generated to standard error (stderr) by doxygen. If WARNINGS is set to YES
+# this implies that the warnings are on.
+#
+# Tip: Turn warnings on while writing the documentation.
+# The default value is: YES.
+
+WARNINGS               = YES
+
+# If the WARN_IF_UNDOCUMENTED tag is set to YES then doxygen will generate
+# warnings for undocumented members. If EXTRACT_ALL is set to YES then this flag
+# will automatically be disabled.
+# The default value is: YES.
+
+WARN_IF_UNDOCUMENTED   = YES
+
+# If the WARN_IF_DOC_ERROR tag is set to YES, doxygen will generate warnings for
+# potential errors in the documentation, such as not documenting some parameters
+# in a documented function, or documenting parameters that don't exist or using
+# markup commands wrongly.
+# The default value is: YES.
+
+WARN_IF_DOC_ERROR      = YES
+
+# This WARN_NO_PARAMDOC option can be enabled to get warnings for functions that
+# are documented, but have no documentation for their parameters or return
+# value. If set to NO, doxygen will only warn about wrong or incomplete
+# parameter documentation, but not about the absence of documentation.
+# The default value is: NO.
+
+WARN_NO_PARAMDOC       = NO
+
+# If the WARN_AS_ERROR tag is set to YES then doxygen will immediately stop when
+# a warning is encountered.
+# The default value is: NO.
+
+WARN_AS_ERROR          = NO
+
+# The WARN_FORMAT tag determines the format of the warning messages that doxygen
+# can produce. The string should contain the $file, $line, and $text tags, which
+# will be replaced by the file and line number from which the warning originated
+# and the warning text. Optionally the format may contain $version, which will
+# be replaced by the version of the file (if it could be obtained via
+# FILE_VERSION_FILTER)
+# The default value is: $file:$line: $text.
+
+WARN_FORMAT            = "$file:$line: $text"
+
+# The WARN_LOGFILE tag can be used to specify a file to which warning and error
+# messages should be written. If left blank the output is written to standard
+# error (stderr).
+
+WARN_LOGFILE           =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the input files
+#---------------------------------------------------------------------------
+
+# The INPUT tag is used to specify the files and/or directories that contain
+# documented source files. You may enter file names like myfile.cpp or
+# directories like /usr/src/myproject. Separate the files or directories with
+# spaces. See also FILE_PATTERNS and EXTENSION_MAPPING
+# Note: If this tag is empty the current directory is searched.
+
+INPUT                  = readme.md inc/
+
+# This tag can be used to specify the character encoding of the source files
+# that doxygen parses. Internally doxygen uses the UTF-8 encoding. Doxygen uses
+# libiconv (or the iconv built into libc) for the transcoding. See the libiconv
+# documentation (see: http://www.gnu.org/software/libiconv) for the list of
+# possible encodings.
+# The default value is: UTF-8.
+
+INPUT_ENCODING         = UTF-8
+
+# If the value of the INPUT tag contains directories, you can use the
+# FILE_PATTERNS tag to specify one or more wildcard patterns (like *.cpp and
+# *.h) to filter out the source-files in the directories.
+#
+# Note that for custom extensions or not directly supported extensions you also
+# need to set EXTENSION_MAPPING for the extension otherwise the files are not
+# read by doxygen.
+#
+# If left blank the following patterns are tested:*.c, *.cc, *.cxx, *.cpp,
+# *.c++, *.java, *.ii, *.ixx, *.ipp, *.i++, *.inl, *.idl, *.ddl, *.odl, *.h,
+# *.hh, *.hxx, *.hpp, *.h++, *.cs, *.d, *.php, *.php4, *.php5, *.phtml, *.inc,
+# *.m, *.markdown, *.md, *.mm, *.dox, *.py, *.pyw, *.f90, *.f, *.for, *.tcl,
+# *.vhd, *.vhdl, *.ucf, *.qsf, *.as and *.js.
+
+FILE_PATTERNS          = *.h
+
+# The RECURSIVE tag can be used to specify whether or not subdirectories should
+# be searched for input files as well.
+# The default value is: NO.
+
+RECURSIVE              = NO
+
+# The EXCLUDE tag can be used to specify files and/or directories that should be
+# excluded from the INPUT source files. This way you can easily exclude a
+# subdirectory from a directory tree whose root is specified with the INPUT tag.
+#
+# Note that relative paths are relative to the directory from which doxygen is
+# run.
+
+EXCLUDE                =
+
+# The EXCLUDE_SYMLINKS tag can be used to select whether or not files or
+# directories that are symbolic links (a Unix file system feature) are excluded
+# from the input.
+# The default value is: NO.
+
+EXCLUDE_SYMLINKS       = NO
+
+# If the value of the INPUT tag contains directories, you can use the
+# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude
+# certain files from those directories.
+#
+# Note that the wildcards are matched against the file with absolute path, so to
+# exclude all test directories for example use the pattern */test/*
+
+EXCLUDE_PATTERNS       =
+
+# The EXCLUDE_SYMBOLS tag can be used to specify one or more symbol names
+# (namespaces, classes, functions, etc.) that should be excluded from the
+# output. The symbol name can be a fully qualified name, a word, or if the
+# wildcard * is used, a substring. Examples: ANamespace, AClass,
+# AClass::ANamespace, ANamespace::*Test
+#
+# Note that the wildcards are matched against the file with absolute path, so to
+# exclude all test directories use the pattern */test/*
+
+EXCLUDE_SYMBOLS        =
+
+# The EXAMPLE_PATH tag can be used to specify one or more files or directories
+# that contain example code fragments that are included (see the \include
+# command).
+
+EXAMPLE_PATH           =
+
+# If the value of the EXAMPLE_PATH tag contains directories, you can use the
+# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp and
+# *.h) to filter out the source-files in the directories. If left blank all
+# files are included.
+
+EXAMPLE_PATTERNS       =
+
+# If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be
+# searched for input files to be used with the \include or \dontinclude commands
+# irrespective of the value of the RECURSIVE tag.
+# The default value is: NO.
+
+EXAMPLE_RECURSIVE      = NO
+
+# The IMAGE_PATH tag can be used to specify one or more files or directories
+# that contain images that are to be included in the documentation (see the
+# \image command).
+
+IMAGE_PATH             =
+
+# The INPUT_FILTER tag can be used to specify a program that doxygen should
+# invoke to filter for each input file. Doxygen will invoke the filter program
+# by executing (via popen()) the command:
+#
+# <filter> <input-file>
+#
+# where <filter> is the value of the INPUT_FILTER tag, and <input-file> is the
+# name of an input file. Doxygen will then use the output that the filter
+# program writes to standard output. If FILTER_PATTERNS is specified, this tag
+# will be ignored.
+#
+# Note that the filter must not add or remove lines; it is applied before the
+# code is scanned, but not when the output code is generated. If lines are added
+# or removed, the anchors will not be placed correctly.
+#
+# Note that for custom extensions or not directly supported extensions you also
+# need to set EXTENSION_MAPPING for the extension otherwise the files are not
+# properly processed by doxygen.
+
+INPUT_FILTER           =
+
+# The FILTER_PATTERNS tag can be used to specify filters on a per file pattern
+# basis. Doxygen will compare the file name with each pattern and apply the
+# filter if there is a match. The filters are a list of the form: pattern=filter
+# (like *.cpp=my_cpp_filter). See INPUT_FILTER for further information on how
+# filters are used. If the FILTER_PATTERNS tag is empty or if none of the
+# patterns match the file name, INPUT_FILTER is applied.
+#
+# Note that for custom extensions or not directly supported extensions you also
+# need to set EXTENSION_MAPPING for the extension otherwise the files are not
+# properly processed by doxygen.
+
+FILTER_PATTERNS        =
+
+# If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using
+# INPUT_FILTER) will also be used to filter the input files that are used for
+# producing the source files to browse (i.e. when SOURCE_BROWSER is set to YES).
+# The default value is: NO.
+
+FILTER_SOURCE_FILES    = NO
+
+# The FILTER_SOURCE_PATTERNS tag can be used to specify source filters per file
+# pattern. A pattern will override the setting for FILTER_PATTERN (if any) and
+# it is also possible to disable source filtering for a specific pattern using
+# *.ext= (so without naming a filter).
+# This tag requires that the tag FILTER_SOURCE_FILES is set to YES.
+
+FILTER_SOURCE_PATTERNS =
+
+# If the USE_MDFILE_AS_MAINPAGE tag refers to the name of a markdown file that
+# is part of the input, its contents will be placed on the main page
+# (index.html). This can be useful if you have a project on for instance GitHub
+# and want to reuse the introduction page also for the doxygen output.
+
+USE_MDFILE_AS_MAINPAGE = readme.md
+
+#---------------------------------------------------------------------------
+# Configuration options related to source browsing
+#---------------------------------------------------------------------------
+
+# If the SOURCE_BROWSER tag is set to YES then a list of source files will be
+# generated. Documented entities will be cross-referenced with these sources.
+#
+# Note: To get rid of all source code in the generated output, make sure that
+# also VERBATIM_HEADERS is set to NO.
+# The default value is: NO.
+
+SOURCE_BROWSER         = YES
+
+# Setting the INLINE_SOURCES tag to YES will include the body of functions,
+# classes and enums directly into the documentation.
+# The default value is: NO.
+
+INLINE_SOURCES         = NO
+
+# Setting the STRIP_CODE_COMMENTS tag to YES will instruct doxygen to hide any
+# special comment blocks from generated source code fragments. Normal C, C++ and
+# Fortran comments will always remain visible.
+# The default value is: YES.
+
+STRIP_CODE_COMMENTS    = YES
+
+# If the REFERENCED_BY_RELATION tag is set to YES then for each documented
+# function all documented functions referencing it will be listed.
+# The default value is: NO.
+
+REFERENCED_BY_RELATION = NO
+
+# If the REFERENCES_RELATION tag is set to YES then for each documented function
+# all documented entities called/used by that function will be listed.
+# The default value is: NO.
+
+REFERENCES_RELATION    = NO
+
+# If the REFERENCES_LINK_SOURCE tag is set to YES and SOURCE_BROWSER tag is set
+# to YES then the hyperlinks from functions in REFERENCES_RELATION and
+# REFERENCED_BY_RELATION lists will link to the source code. Otherwise they will
+# link to the documentation.
+# The default value is: YES.
+
+REFERENCES_LINK_SOURCE = YES
+
+# If SOURCE_TOOLTIPS is enabled (the default) then hovering a hyperlink in the
+# source code will show a tooltip with additional information such as prototype,
+# brief description and links to the definition and documentation. Since this
+# will make the HTML file larger and loading of large files a bit slower, you
+# can opt to disable this feature.
+# The default value is: YES.
+# This tag requires that the tag SOURCE_BROWSER is set to YES.
+
+SOURCE_TOOLTIPS        = YES
+
+# If the USE_HTAGS tag is set to YES then the references to source code will
+# point to the HTML generated by the htags(1) tool instead of doxygen built-in
+# source browser. The htags tool is part of GNU's global source tagging system
+# (see http://www.gnu.org/software/global/global.html). You will need version
+# 4.8.6 or higher.
+#
+# To use it do the following:
+# - Install the latest version of global
+# - Enable SOURCE_BROWSER and USE_HTAGS in the config file
+# - Make sure the INPUT points to the root of the source tree
+# - Run doxygen as normal
+#
+# Doxygen will invoke htags (and that will in turn invoke gtags), so these
+# tools must be available from the command line (i.e. in the search path).
+#
+# The result: instead of the source browser generated by doxygen, the links to
+# source code will now point to the output of htags.
+# The default value is: NO.
+# This tag requires that the tag SOURCE_BROWSER is set to YES.
+
+USE_HTAGS              = NO
+
+# If the VERBATIM_HEADERS tag is set the YES then doxygen will generate a
+# verbatim copy of the header file for each class for which an include is
+# specified. Set to NO to disable this.
+# See also: Section \class.
+# The default value is: YES.
+
+VERBATIM_HEADERS       = YES
+
+# If the CLANG_ASSISTED_PARSING tag is set to YES then doxygen will use the
+# clang parser (see: http://clang.llvm.org/) for more accurate parsing at the
+# cost of reduced performance. This can be particularly helpful with template
+# rich C++ code for which doxygen's built-in parser lacks the necessary type
+# information.
+# Note: The availability of this option depends on whether or not doxygen was
+# generated with the -Duse-libclang=ON option for CMake.
+# The default value is: NO.
+
+CLANG_ASSISTED_PARSING = NO
+
+# If clang assisted parsing is enabled you can provide the compiler with command
+# line options that you would normally use when invoking the compiler. Note that
+# the include paths will already be set by doxygen for the files and directories
+# specified with INPUT and INCLUDE_PATH.
+# This tag requires that the tag CLANG_ASSISTED_PARSING is set to YES.
+
+CLANG_OPTIONS          =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the alphabetical class index
+#---------------------------------------------------------------------------
+
+# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index of all
+# compounds will be generated. Enable this if the project contains a lot of
+# classes, structs, unions or interfaces.
+# The default value is: YES.
+
+ALPHABETICAL_INDEX     = YES
+
+# The COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns in
+# which the alphabetical index list will be split.
+# Minimum value: 1, maximum value: 20, default value: 5.
+# This tag requires that the tag ALPHABETICAL_INDEX is set to YES.
+
+COLS_IN_ALPHA_INDEX    = 5
+
+# In case all classes in a project start with a common prefix, all classes will
+# be put under the same header in the alphabetical index. The IGNORE_PREFIX tag
+# can be used to specify a prefix (or a list of prefixes) that should be ignored
+# while generating the index headers.
+# This tag requires that the tag ALPHABETICAL_INDEX is set to YES.
+
+IGNORE_PREFIX          =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the HTML output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_HTML tag is set to YES, doxygen will generate HTML output
+# The default value is: YES.
+
+GENERATE_HTML          = YES
+
+# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: html.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_OUTPUT            = html
+
+# The HTML_FILE_EXTENSION tag can be used to specify the file extension for each
+# generated HTML page (for example: .htm, .php, .asp).
+# The default value is: .html.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_FILE_EXTENSION    = .html
+
+# The HTML_HEADER tag can be used to specify a user-defined HTML header file for
+# each generated HTML page. If the tag is left blank doxygen will generate a
+# standard header.
+#
+# To get valid HTML the header file that includes any scripts and style sheets
+# that doxygen needs, which is dependent on the configuration options used (e.g.
+# the setting GENERATE_TREEVIEW). It is highly recommended to start with a
+# default header using
+# doxygen -w html new_header.html new_footer.html new_stylesheet.css
+# YourConfigFile
+# and then modify the file new_header.html. See also section "Doxygen usage"
+# for information on how to generate the default header that doxygen normally
+# uses.
+# Note: The header is subject to change so you typically have to regenerate the
+# default header when upgrading to a newer version of doxygen. For a description
+# of the possible markers and block names see the documentation.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_HEADER            =
+
+# The HTML_FOOTER tag can be used to specify a user-defined HTML footer for each
+# generated HTML page. If the tag is left blank doxygen will generate a standard
+# footer. See HTML_HEADER for more information on how to generate a default
+# footer and what special commands can be used inside the footer. See also
+# section "Doxygen usage" for information on how to generate the default footer
+# that doxygen normally uses.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_FOOTER            =
+
+# The HTML_STYLESHEET tag can be used to specify a user-defined cascading style
+# sheet that is used by each HTML page. It can be used to fine-tune the look of
+# the HTML output. If left blank doxygen will generate a default style sheet.
+# See also section "Doxygen usage" for information on how to generate the style
+# sheet that doxygen normally uses.
+# Note: It is recommended to use HTML_EXTRA_STYLESHEET instead of this tag, as
+# it is more robust and this tag (HTML_STYLESHEET) will in the future become
+# obsolete.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_STYLESHEET        =
+
+# The HTML_EXTRA_STYLESHEET tag can be used to specify additional user-defined
+# cascading style sheets that are included after the standard style sheets
+# created by doxygen. Using this option one can overrule certain style aspects.
+# This is preferred over using HTML_STYLESHEET since it does not replace the
+# standard style sheet and is therefore more robust against future updates.
+# Doxygen will copy the style sheet files to the output directory.
+# Note: The order of the extra style sheet files is of importance (e.g. the last
+# style sheet in the list overrules the setting of the previous ones in the
+# list). For an example see the documentation.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_EXTRA_STYLESHEET  =
+
+# The HTML_EXTRA_FILES tag can be used to specify one or more extra images or
+# other source files which should be copied to the HTML output directory. Note
+# that these files will be copied to the base HTML output directory. Use the
+# $relpath^ marker in the HTML_HEADER and/or HTML_FOOTER files to load these
+# files. In the HTML_STYLESHEET file, use the file name only. Also note that the
+# files will be copied as-is; there are no commands or markers available.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_EXTRA_FILES       =
+
+# The HTML_COLORSTYLE_HUE tag controls the color of the HTML output. Doxygen
+# will adjust the colors in the style sheet and background images according to
+# this color. Hue is specified as an angle on a colorwheel, see
+# http://en.wikipedia.org/wiki/Hue for more information. For instance the value
+# 0 represents red, 60 is yellow, 120 is green, 180 is cyan, 240 is blue, 300
+# purple, and 360 is red again.
+# Minimum value: 0, maximum value: 359, default value: 220.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_COLORSTYLE_HUE    = 220
+
+# The HTML_COLORSTYLE_SAT tag controls the purity (or saturation) of the colors
+# in the HTML output. For a value of 0 the output will use grayscales only. A
+# value of 255 will produce the most vivid colors.
+# Minimum value: 0, maximum value: 255, default value: 100.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_COLORSTYLE_SAT    = 100
+
+# The HTML_COLORSTYLE_GAMMA tag controls the gamma correction applied to the
+# luminance component of the colors in the HTML output. Values below 100
+# gradually make the output lighter, whereas values above 100 make the output
+# darker. The value divided by 100 is the actual gamma applied, so 80 represents
+# a gamma of 0.8, The value 220 represents a gamma of 2.2, and 100 does not
+# change the gamma.
+# Minimum value: 40, maximum value: 240, default value: 80.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_COLORSTYLE_GAMMA  = 80
+
+# If the HTML_TIMESTAMP tag is set to YES then the footer of each generated HTML
+# page will contain the date and time when the page was generated. Setting this
+# to YES can help to show when doxygen was last run and thus if the
+# documentation is up to date.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_TIMESTAMP         = NO
+
+# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML
+# documentation will contain sections that can be hidden and shown after the
+# page has loaded.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_DYNAMIC_SECTIONS  = NO
+
+# With HTML_INDEX_NUM_ENTRIES one can control the preferred number of entries
+# shown in the various tree structured indices initially; the user can expand
+# and collapse entries dynamically later on. Doxygen will expand the tree to
+# such a level that at most the specified number of entries are visible (unless
+# a fully collapsed tree already exceeds this amount). So setting the number of
+# entries 1 will produce a full collapsed tree by default. 0 is a special value
+# representing an infinite number of entries and will result in a full expanded
+# tree by default.
+# Minimum value: 0, maximum value: 9999, default value: 100.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+HTML_INDEX_NUM_ENTRIES = 100
+
+# If the GENERATE_DOCSET tag is set to YES, additional index files will be
+# generated that can be used as input for Apple's Xcode 3 integrated development
+# environment (see: http://developer.apple.com/tools/xcode/), introduced with
+# OSX 10.5 (Leopard). To create a documentation set, doxygen will generate a
+# Makefile in the HTML output directory. Running make will produce the docset in
+# that directory and running make install will install the docset in
+# ~/Library/Developer/Shared/Documentation/DocSets so that Xcode will find it at
+# startup. See http://developer.apple.com/tools/creatingdocsetswithdoxygen.html
+# for more information.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_DOCSET        = NO
+
+# This tag determines the name of the docset feed. A documentation feed provides
+# an umbrella under which multiple documentation sets from a single provider
+# (such as a company or product suite) can be grouped.
+# The default value is: Doxygen generated docs.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_FEEDNAME        = "Doxygen generated docs"
+
+# This tag specifies a string that should uniquely identify the documentation
+# set bundle. This should be a reverse domain-name style string, e.g.
+# com.mycompany.MyDocSet. Doxygen will append .docset to the name.
+# The default value is: org.doxygen.Project.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_BUNDLE_ID       = org.doxygen.Project
+
+# The DOCSET_PUBLISHER_ID tag specifies a string that should uniquely identify
+# the documentation publisher. This should be a reverse domain-name style
+# string, e.g. com.mycompany.MyDocSet.documentation.
+# The default value is: org.doxygen.Publisher.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_PUBLISHER_ID    = org.doxygen.Publisher
+
+# The DOCSET_PUBLISHER_NAME tag identifies the documentation publisher.
+# The default value is: Publisher.
+# This tag requires that the tag GENERATE_DOCSET is set to YES.
+
+DOCSET_PUBLISHER_NAME  = Publisher
+
+# If the GENERATE_HTMLHELP tag is set to YES then doxygen generates three
+# additional HTML index files: index.hhp, index.hhc, and index.hhk. The
+# index.hhp is a project file that can be read by Microsoft's HTML Help Workshop
+# (see: http://www.microsoft.com/en-us/download/details.aspx?id=21138) on
+# Windows.
+#
+# The HTML Help Workshop contains a compiler that can convert all HTML output
+# generated by doxygen into a single compiled HTML file (.chm). Compiled HTML
+# files are now used as the Windows 98 help format, and will replace the old
+# Windows help format (.hlp) on all Windows platforms in the future. Compressed
+# HTML files also contain an index, a table of contents, and you can search for
+# words in the documentation. The HTML workshop also contains a viewer for
+# compressed HTML files.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_HTMLHELP      = NO
+
+# The CHM_FILE tag can be used to specify the file name of the resulting .chm
+# file. You can add a path in front of the file if the result should not be
+# written to the html output directory.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+CHM_FILE               =
+
+# The HHC_LOCATION tag can be used to specify the location (absolute path
+# including file name) of the HTML help compiler (hhc.exe). If non-empty,
+# doxygen will try to run the HTML help compiler on the generated index.hhp.
+# The file has to be specified with full path.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+HHC_LOCATION           =
+
+# The GENERATE_CHI flag controls if a separate .chi index file is generated
+# (YES) or that it should be included in the master .chm file (NO).
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+GENERATE_CHI           = NO
+
+# The CHM_INDEX_ENCODING is used to encode HtmlHelp index (hhk), content (hhc)
+# and project file content.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+CHM_INDEX_ENCODING     =
+
+# The BINARY_TOC flag controls whether a binary table of contents is generated
+# (YES) or a normal table of contents (NO) in the .chm file. Furthermore it
+# enables the Previous and Next buttons.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+BINARY_TOC             = NO
+
+# The TOC_EXPAND flag can be set to YES to add extra items for group members to
+# the table of contents of the HTML help documentation and to the tree view.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTMLHELP is set to YES.
+
+TOC_EXPAND             = NO
+
+# If the GENERATE_QHP tag is set to YES and both QHP_NAMESPACE and
+# QHP_VIRTUAL_FOLDER are set, an additional index file will be generated that
+# can be used as input for Qt's qhelpgenerator to generate a Qt Compressed Help
+# (.qch) of the generated HTML documentation.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_QHP           = NO
+
+# If the QHG_LOCATION tag is specified, the QCH_FILE tag can be used to specify
+# the file name of the resulting .qch file. The path specified is relative to
+# the HTML output folder.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QCH_FILE               =
+
+# The QHP_NAMESPACE tag specifies the namespace to use when generating Qt Help
+# Project output. For more information please see Qt Help Project / Namespace
+# (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#namespace).
+# The default value is: org.doxygen.Project.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_NAMESPACE          = org.doxygen.Project
+
+# The QHP_VIRTUAL_FOLDER tag specifies the namespace to use when generating Qt
+# Help Project output. For more information please see Qt Help Project / Virtual
+# Folders (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#virtual-
+# folders).
+# The default value is: doc.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_VIRTUAL_FOLDER     = doc
+
+# If the QHP_CUST_FILTER_NAME tag is set, it specifies the name of a custom
+# filter to add. For more information please see Qt Help Project / Custom
+# Filters (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#custom-
+# filters).
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_CUST_FILTER_NAME   =
+
+# The QHP_CUST_FILTER_ATTRS tag specifies the list of the attributes of the
+# custom filter to add. For more information please see Qt Help Project / Custom
+# Filters (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#custom-
+# filters).
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_CUST_FILTER_ATTRS  =
+
+# The QHP_SECT_FILTER_ATTRS tag specifies the list of the attributes this
+# project's filter section matches. Qt Help Project / Filter Attributes (see:
+# http://qt-project.org/doc/qt-4.8/qthelpproject.html#filter-attributes).
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHP_SECT_FILTER_ATTRS  =
+
+# The QHG_LOCATION tag can be used to specify the location of Qt's
+# qhelpgenerator. If non-empty doxygen will try to run qhelpgenerator on the
+# generated .qhp file.
+# This tag requires that the tag GENERATE_QHP is set to YES.
+
+QHG_LOCATION           =
+
+# If the GENERATE_ECLIPSEHELP tag is set to YES, additional index files will be
+# generated, together with the HTML files, they form an Eclipse help plugin. To
+# install this plugin and make it available under the help contents menu in
+# Eclipse, the contents of the directory containing the HTML and XML files needs
+# to be copied into the plugins directory of eclipse. The name of the directory
+# within the plugins directory should be the same as the ECLIPSE_DOC_ID value.
+# After copying Eclipse needs to be restarted before the help appears.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_ECLIPSEHELP   = NO
+
+# A unique identifier for the Eclipse help plugin. When installing the plugin
+# the directory name containing the HTML and XML files should also have this
+# name. Each documentation set should have its own identifier.
+# The default value is: org.doxygen.Project.
+# This tag requires that the tag GENERATE_ECLIPSEHELP is set to YES.
+
+ECLIPSE_DOC_ID         = org.doxygen.Project
+
+# If you want full control over the layout of the generated HTML pages it might
+# be necessary to disable the index and replace it with your own. The
+# DISABLE_INDEX tag can be used to turn on/off the condensed index (tabs) at top
+# of each HTML page. A value of NO enables the index and the value YES disables
+# it. Since the tabs in the index contain the same information as the navigation
+# tree, you can set this option to YES if you also set GENERATE_TREEVIEW to YES.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+DISABLE_INDEX          = NO
+
+# The GENERATE_TREEVIEW tag is used to specify whether a tree-like index
+# structure should be generated to display hierarchical information. If the tag
+# value is set to YES, a side panel will be generated containing a tree-like
+# index structure (just like the one that is generated for HTML Help). For this
+# to work a browser that supports JavaScript, DHTML, CSS and frames is required
+# (i.e. any modern browser). Windows users are probably better off using the
+# HTML help feature. Via custom style sheets (see HTML_EXTRA_STYLESHEET) one can
+# further fine-tune the look of the index. As an example, the default style
+# sheet generated by doxygen has an example that shows how to put an image at
+# the root of the tree instead of the PROJECT_NAME. Since the tree basically has
+# the same information as the tab index, you could consider setting
+# DISABLE_INDEX to YES when enabling this option.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+GENERATE_TREEVIEW      = YES
+
+# The ENUM_VALUES_PER_LINE tag can be used to set the number of enum values that
+# doxygen will group on one line in the generated HTML documentation.
+#
+# Note that a value of 0 will completely suppress the enum values from appearing
+# in the overview section.
+# Minimum value: 0, maximum value: 20, default value: 4.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+ENUM_VALUES_PER_LINE   = 0
+
+# If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be used
+# to set the initial width (in pixels) of the frame in which the tree is shown.
+# Minimum value: 0, maximum value: 1500, default value: 250.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+TREEVIEW_WIDTH         = 250
+
+# If the EXT_LINKS_IN_WINDOW option is set to YES, doxygen will open links to
+# external symbols imported via tag files in a separate window.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+EXT_LINKS_IN_WINDOW    = NO
+
+# Use this tag to change the font size of LaTeX formulas included as images in
+# the HTML documentation. When you change the font size after a successful
+# doxygen run you need to manually remove any form_*.png images from the HTML
+# output directory to force them to be regenerated.
+# Minimum value: 8, maximum value: 50, default value: 10.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+FORMULA_FONTSIZE       = 10
+
+# Use the FORMULA_TRANPARENT tag to determine whether or not the images
+# generated for formulas are transparent PNGs. Transparent PNGs are not
+# supported properly for IE 6.0, but are supported on all modern browsers.
+#
+# Note that when changing this option you need to delete any form_*.png files in
+# the HTML output directory before the changes have effect.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+FORMULA_TRANSPARENT    = YES
+
+# Enable the USE_MATHJAX option to render LaTeX formulas using MathJax (see
+# http://www.mathjax.org) which uses client side Javascript for the rendering
+# instead of using pre-rendered bitmaps. Use this if you do not have LaTeX
+# installed or if you want to formulas look prettier in the HTML output. When
+# enabled you may also need to install MathJax separately and configure the path
+# to it using the MATHJAX_RELPATH option.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+USE_MATHJAX            = NO
+
+# When MathJax is enabled you can set the default output format to be used for
+# the MathJax output. See the MathJax site (see:
+# http://docs.mathjax.org/en/latest/output.html) for more details.
+# Possible values are: HTML-CSS (which is slower, but has the best
+# compatibility), NativeMML (i.e. MathML) and SVG.
+# The default value is: HTML-CSS.
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_FORMAT         = HTML-CSS
+
+# When MathJax is enabled you need to specify the location relative to the HTML
+# output directory using the MATHJAX_RELPATH option. The destination directory
+# should contain the MathJax.js script. For instance, if the mathjax directory
+# is located at the same level as the HTML output directory, then
+# MATHJAX_RELPATH should be ../mathjax. The default value points to the MathJax
+# Content Delivery Network so you can quickly see the result without installing
+# MathJax. However, it is strongly recommended to install a local copy of
+# MathJax from http://www.mathjax.org before deployment.
+# The default value is: http://cdn.mathjax.org/mathjax/latest.
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_RELPATH        = http://cdn.mathjax.org/mathjax/latest
+
+# The MATHJAX_EXTENSIONS tag can be used to specify one or more MathJax
+# extension names that should be enabled during MathJax rendering. For example
+# MATHJAX_EXTENSIONS = TeX/AMSmath TeX/AMSsymbols
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_EXTENSIONS     =
+
+# The MATHJAX_CODEFILE tag can be used to specify a file with javascript pieces
+# of code that will be used on startup of the MathJax code. See the MathJax site
+# (see: http://docs.mathjax.org/en/latest/output.html) for more details. For an
+# example see the documentation.
+# This tag requires that the tag USE_MATHJAX is set to YES.
+
+MATHJAX_CODEFILE       =
+
+# When the SEARCHENGINE tag is enabled doxygen will generate a search box for
+# the HTML output. The underlying search engine uses javascript and DHTML and
+# should work on any modern browser. Note that when using HTML help
+# (GENERATE_HTMLHELP), Qt help (GENERATE_QHP), or docsets (GENERATE_DOCSET)
+# there is already a search function so this one should typically be disabled.
+# For large projects the javascript based search engine can be slow, then
+# enabling SERVER_BASED_SEARCH may provide a better solution. It is possible to
+# search using the keyboard; to jump to the search box use <access key> + S
+# (what the <access key> is depends on the OS and browser, but it is typically
+# <CTRL>, <ALT>/<option>, or both). Inside the search box use the <cursor down
+# key> to jump into the search results window, the results can be navigated
+# using the <cursor keys>. Press <Enter> to select an item or <escape> to cancel
+# the search. The filter options can be selected when the cursor is inside the
+# search box by pressing <Shift>+<cursor down>. Also here use the <cursor keys>
+# to select a filter and <Enter> or <escape> to activate or cancel the filter
+# option.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_HTML is set to YES.
+
+SEARCHENGINE           = YES
+
+# When the SERVER_BASED_SEARCH tag is enabled the search engine will be
+# implemented using a web server instead of a web client using Javascript. There
+# are two flavors of web server based searching depending on the EXTERNAL_SEARCH
+# setting. When disabled, doxygen will generate a PHP script for searching and
+# an index file used by the script. When EXTERNAL_SEARCH is enabled the indexing
+# and searching needs to be provided by external tools. See the section
+# "External Indexing and Searching" for details.
+# The default value is: NO.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+SERVER_BASED_SEARCH    = NO
+
+# When EXTERNAL_SEARCH tag is enabled doxygen will no longer generate the PHP
+# script for searching. Instead the search results are written to an XML file
+# which needs to be processed by an external indexer. Doxygen will invoke an
+# external search engine pointed to by the SEARCHENGINE_URL option to obtain the
+# search results.
+#
+# Doxygen ships with an example indexer (doxyindexer) and search engine
+# (doxysearch.cgi) which are based on the open source search engine library
+# Xapian (see: http://xapian.org/).
+#
+# See the section "External Indexing and Searching" for details.
+# The default value is: NO.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+EXTERNAL_SEARCH        = NO
+
+# The SEARCHENGINE_URL should point to a search engine hosted by a web server
+# which will return the search results when EXTERNAL_SEARCH is enabled.
+#
+# Doxygen ships with an example indexer (doxyindexer) and search engine
+# (doxysearch.cgi) which are based on the open source search engine library
+# Xapian (see: http://xapian.org/). See the section "External Indexing and
+# Searching" for details.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+SEARCHENGINE_URL       =
+
+# When SERVER_BASED_SEARCH and EXTERNAL_SEARCH are both enabled the unindexed
+# search data is written to a file for indexing by an external tool. With the
+# SEARCHDATA_FILE tag the name of this file can be specified.
+# The default file is: searchdata.xml.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+SEARCHDATA_FILE        = searchdata.xml
+
+# When SERVER_BASED_SEARCH and EXTERNAL_SEARCH are both enabled the
+# EXTERNAL_SEARCH_ID tag can be used as an identifier for the project. This is
+# useful in combination with EXTRA_SEARCH_MAPPINGS to search through multiple
+# projects and redirect the results back to the right project.
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+EXTERNAL_SEARCH_ID     =
+
+# The EXTRA_SEARCH_MAPPINGS tag can be used to enable searching through doxygen
+# projects other than the one defined by this configuration file, but that are
+# all added to the same external search index. Each project needs to have a
+# unique id set via EXTERNAL_SEARCH_ID. The search mapping then maps the id of
+# to a relative location where the documentation can be found. The format is:
+# EXTRA_SEARCH_MAPPINGS = tagname1=loc1 tagname2=loc2 ...
+# This tag requires that the tag SEARCHENGINE is set to YES.
+
+EXTRA_SEARCH_MAPPINGS  =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the LaTeX output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_LATEX tag is set to YES, doxygen will generate LaTeX output.
+# The default value is: YES.
+
+GENERATE_LATEX         = NO
+
+# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: latex.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_OUTPUT           = latex
+
+# The LATEX_CMD_NAME tag can be used to specify the LaTeX command name to be
+# invoked.
+#
+# Note that when enabling USE_PDFLATEX this option is only used for generating
+# bitmaps for formulas in the HTML output, but not in the Makefile that is
+# written to the output directory.
+# The default file is: latex.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_CMD_NAME         = latex
+
+# The MAKEINDEX_CMD_NAME tag can be used to specify the command name to generate
+# index for LaTeX.
+# The default file is: makeindex.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+MAKEINDEX_CMD_NAME     = makeindex
+
+# If the COMPACT_LATEX tag is set to YES, doxygen generates more compact LaTeX
+# documents. This may be useful for small projects and may help to save some
+# trees in general.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+COMPACT_LATEX          = NO
+
+# The PAPER_TYPE tag can be used to set the paper type that is used by the
+# printer.
+# Possible values are: a4 (210 x 297 mm), letter (8.5 x 11 inches), legal (8.5 x
+# 14 inches) and executive (7.25 x 10.5 inches).
+# The default value is: a4.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+PAPER_TYPE             = a4
+
+# The EXTRA_PACKAGES tag can be used to specify one or more LaTeX package names
+# that should be included in the LaTeX output. The package can be specified just
+# by its name or with the correct syntax as to be used with the LaTeX
+# \usepackage command. To get the times font for instance you can specify :
+# EXTRA_PACKAGES=times or EXTRA_PACKAGES={times}
+# To use the option intlimits with the amsmath package you can specify:
+# EXTRA_PACKAGES=[intlimits]{amsmath}
+# If left blank no extra packages will be included.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+EXTRA_PACKAGES         =
+
+# The LATEX_HEADER tag can be used to specify a personal LaTeX header for the
+# generated LaTeX document. The header should contain everything until the first
+# chapter. If it is left blank doxygen will generate a standard header. See
+# section "Doxygen usage" for information on how to let doxygen write the
+# default header to a separate file.
+#
+# Note: Only use a user-defined header if you know what you are doing! The
+# following commands have a special meaning inside the header: $title,
+# $datetime, $date, $doxygenversion, $projectname, $projectnumber,
+# $projectbrief, $projectlogo. Doxygen will replace $title with the empty
+# string, for the replacement values of the other commands the user is referred
+# to HTML_HEADER.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_HEADER           =
+
+# The LATEX_FOOTER tag can be used to specify a personal LaTeX footer for the
+# generated LaTeX document. The footer should contain everything after the last
+# chapter. If it is left blank doxygen will generate a standard footer. See
+# LATEX_HEADER for more information on how to generate a default footer and what
+# special commands can be used inside the footer.
+#
+# Note: Only use a user-defined footer if you know what you are doing!
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_FOOTER           =
+
+# The LATEX_EXTRA_STYLESHEET tag can be used to specify additional user-defined
+# LaTeX style sheets that are included after the standard style sheets created
+# by doxygen. Using this option one can overrule certain style aspects. Doxygen
+# will copy the style sheet files to the output directory.
+# Note: The order of the extra style sheet files is of importance (e.g. the last
+# style sheet in the list overrules the setting of the previous ones in the
+# list).
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_EXTRA_STYLESHEET =
+
+# The LATEX_EXTRA_FILES tag can be used to specify one or more extra images or
+# other source files which should be copied to the LATEX_OUTPUT output
+# directory. Note that the files will be copied as-is; there are no commands or
+# markers available.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_EXTRA_FILES      =
+
+# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated is
+# prepared for conversion to PDF (using ps2pdf or pdflatex). The PDF file will
+# contain links (just like the HTML output) instead of page references. This
+# makes the output suitable for online browsing using a PDF viewer.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+PDF_HYPERLINKS         = YES
+
+# If the USE_PDFLATEX tag is set to YES, doxygen will use pdflatex to generate
+# the PDF file directly from the LaTeX files. Set this option to YES, to get a
+# higher quality PDF documentation.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+USE_PDFLATEX           = YES
+
+# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \batchmode
+# command to the generated LaTeX files. This will instruct LaTeX to keep running
+# if errors occur, instead of asking the user for help. This option is also used
+# when generating formulas in HTML.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_BATCHMODE        = NO
+
+# If the LATEX_HIDE_INDICES tag is set to YES then doxygen will not include the
+# index chapters (such as File Index, Compound Index, etc.) in the output.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_HIDE_INDICES     = NO
+
+# If the LATEX_SOURCE_CODE tag is set to YES then doxygen will include source
+# code with syntax highlighting in the LaTeX output.
+#
+# Note that which sources are shown also depends on other settings such as
+# SOURCE_BROWSER.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_SOURCE_CODE      = NO
+
+# The LATEX_BIB_STYLE tag can be used to specify the style to use for the
+# bibliography, e.g. plainnat, or ieeetr. See
+# http://en.wikipedia.org/wiki/BibTeX and \cite for more info.
+# The default value is: plain.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_BIB_STYLE        = plain
+
+# If the LATEX_TIMESTAMP tag is set to YES then the footer of each generated
+# page will contain the date and time when the page was generated. Setting this
+# to NO can help when comparing the output of multiple runs.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_LATEX is set to YES.
+
+LATEX_TIMESTAMP        = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the RTF output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_RTF tag is set to YES, doxygen will generate RTF output. The
+# RTF output is optimized for Word 97 and may not look too pretty with other RTF
+# readers/editors.
+# The default value is: NO.
+
+GENERATE_RTF           = NO
+
+# The RTF_OUTPUT tag is used to specify where the RTF docs will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: rtf.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_OUTPUT             = rtf
+
+# If the COMPACT_RTF tag is set to YES, doxygen generates more compact RTF
+# documents. This may be useful for small projects and may help to save some
+# trees in general.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+COMPACT_RTF            = NO
+
+# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated will
+# contain hyperlink fields. The RTF file will contain links (just like the HTML
+# output) instead of page references. This makes the output suitable for online
+# browsing using Word or some other Word compatible readers that support those
+# fields.
+#
+# Note: WordPad (write) and others do not support links.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_HYPERLINKS         = NO
+
+# Load stylesheet definitions from file. Syntax is similar to doxygen's config
+# file, i.e. a series of assignments. You only have to provide replacements,
+# missing definitions are set to their default value.
+#
+# See also section "Doxygen usage" for information on how to generate the
+# default style sheet that doxygen normally uses.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_STYLESHEET_FILE    =
+
+# Set optional variables used in the generation of an RTF document. Syntax is
+# similar to doxygen's config file. A template extensions file can be generated
+# using doxygen -e rtf extensionFile.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_EXTENSIONS_FILE    =
+
+# If the RTF_SOURCE_CODE tag is set to YES then doxygen will include source code
+# with syntax highlighting in the RTF output.
+#
+# Note that which sources are shown also depends on other settings such as
+# SOURCE_BROWSER.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_RTF is set to YES.
+
+RTF_SOURCE_CODE        = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the man page output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_MAN tag is set to YES, doxygen will generate man pages for
+# classes and files.
+# The default value is: NO.
+
+GENERATE_MAN           = NO
+
+# The MAN_OUTPUT tag is used to specify where the man pages will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it. A directory man3 will be created inside the directory specified by
+# MAN_OUTPUT.
+# The default directory is: man.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_OUTPUT             = man
+
+# The MAN_EXTENSION tag determines the extension that is added to the generated
+# man pages. In case the manual section does not start with a number, the number
+# 3 is prepended. The dot (.) at the beginning of the MAN_EXTENSION tag is
+# optional.
+# The default value is: .3.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_EXTENSION          = .3
+
+# The MAN_SUBDIR tag determines the name of the directory created within
+# MAN_OUTPUT in which the man pages are placed. If defaults to man followed by
+# MAN_EXTENSION with the initial . removed.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_SUBDIR             =
+
+# If the MAN_LINKS tag is set to YES and doxygen generates man output, then it
+# will generate one additional man file for each entity documented in the real
+# man page(s). These additional files only source the real man page, but without
+# them the man command would be unable to find the correct page.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_MAN is set to YES.
+
+MAN_LINKS              = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the XML output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_XML tag is set to YES, doxygen will generate an XML file that
+# captures the structure of the code including all documentation.
+# The default value is: NO.
+
+GENERATE_XML           = NO
+
+# The XML_OUTPUT tag is used to specify where the XML pages will be put. If a
+# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of
+# it.
+# The default directory is: xml.
+# This tag requires that the tag GENERATE_XML is set to YES.
+
+XML_OUTPUT             = xml
+
+# If the XML_PROGRAMLISTING tag is set to YES, doxygen will dump the program
+# listings (including syntax highlighting and cross-referencing information) to
+# the XML output. Note that enabling this will significantly increase the size
+# of the XML output.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_XML is set to YES.
+
+XML_PROGRAMLISTING     = YES
+
+#---------------------------------------------------------------------------
+# Configuration options related to the DOCBOOK output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_DOCBOOK tag is set to YES, doxygen will generate Docbook files
+# that can be used to generate PDF.
+# The default value is: NO.
+
+GENERATE_DOCBOOK       = NO
+
+# The DOCBOOK_OUTPUT tag is used to specify where the Docbook pages will be put.
+# If a relative path is entered the value of OUTPUT_DIRECTORY will be put in
+# front of it.
+# The default directory is: docbook.
+# This tag requires that the tag GENERATE_DOCBOOK is set to YES.
+
+DOCBOOK_OUTPUT         = docbook
+
+# If the DOCBOOK_PROGRAMLISTING tag is set to YES, doxygen will include the
+# program listings (including syntax highlighting and cross-referencing
+# information) to the DOCBOOK output. Note that enabling this will significantly
+# increase the size of the DOCBOOK output.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_DOCBOOK is set to YES.
+
+DOCBOOK_PROGRAMLISTING = NO
+
+#---------------------------------------------------------------------------
+# Configuration options for the AutoGen Definitions output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_AUTOGEN_DEF tag is set to YES, doxygen will generate an
+# AutoGen Definitions (see http://autogen.sf.net) file that captures the
+# structure of the code including all documentation. Note that this feature is
+# still experimental and incomplete at the moment.
+# The default value is: NO.
+
+GENERATE_AUTOGEN_DEF   = NO
+
+#---------------------------------------------------------------------------
+# Configuration options related to the Perl module output
+#---------------------------------------------------------------------------
+
+# If the GENERATE_PERLMOD tag is set to YES, doxygen will generate a Perl module
+# file that captures the structure of the code including all documentation.
+#
+# Note that this feature is still experimental and incomplete at the moment.
+# The default value is: NO.
+
+GENERATE_PERLMOD       = NO
+
+# If the PERLMOD_LATEX tag is set to YES, doxygen will generate the necessary
+# Makefile rules, Perl scripts and LaTeX code to be able to generate PDF and DVI
+# output from the Perl module output.
+# The default value is: NO.
+# This tag requires that the tag GENERATE_PERLMOD is set to YES.
+
+PERLMOD_LATEX          = NO
+
+# If the PERLMOD_PRETTY tag is set to YES, the Perl module output will be nicely
+# formatted so it can be parsed by a human reader. This is useful if you want to
+# understand what is going on. On the other hand, if this tag is set to NO, the
+# size of the Perl module output will be much smaller and Perl will parse it
+# just the same.
+# The default value is: YES.
+# This tag requires that the tag GENERATE_PERLMOD is set to YES.
+
+PERLMOD_PRETTY         = YES
+
+# The names of the make variables in the generated doxyrules.make file are
+# prefixed with the string contained in PERLMOD_MAKEVAR_PREFIX. This is useful
+# so different doxyrules.make files included by the same Makefile don't
+# overwrite each other's variables.
+# This tag requires that the tag GENERATE_PERLMOD is set to YES.
+
+PERLMOD_MAKEVAR_PREFIX =
+
+#---------------------------------------------------------------------------
+# Configuration options related to the preprocessor
+#---------------------------------------------------------------------------
+
+# If the ENABLE_PREPROCESSING tag is set to YES, doxygen will evaluate all
+# C-preprocessor directives found in the sources and include files.
+# The default value is: YES.
+
+ENABLE_PREPROCESSING   = YES
+
+# If the MACRO_EXPANSION tag is set to YES, doxygen will expand all macro names
+# in the source code. If set to NO, only conditional compilation will be
+# performed. Macro expansion can be done in a controlled way by setting
+# EXPAND_ONLY_PREDEF to YES.
+# The default value is: NO.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+MACRO_EXPANSION        = YES
+
+# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES then
+# the macro expansion is limited to the macros specified with the PREDEFINED and
+# EXPAND_AS_DEFINED tags.
+# The default value is: NO.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+EXPAND_ONLY_PREDEF     = YES
+
+# If the SEARCH_INCLUDES tag is set to YES, the include files in the
+# INCLUDE_PATH will be searched if a #include is found.
+# The default value is: YES.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+SEARCH_INCLUDES        = NO
+
+# The INCLUDE_PATH tag can be used to specify one or more directories that
+# contain include files that are not input files but should be processed by the
+# preprocessor.
+# This tag requires that the tag SEARCH_INCLUDES is set to YES.
+
+INCLUDE_PATH           =
+
+# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard
+# patterns (like *.h and *.hpp) to filter out the header-files in the
+# directories. If left blank, the patterns specified with FILE_PATTERNS will be
+# used.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+INCLUDE_FILE_PATTERNS  =
+
+# The PREDEFINED tag can be used to specify one or more macro names that are
+# defined before the preprocessor is started (similar to the -D option of e.g.
+# gcc). The argument of the tag is a list of macros of the form: name or
+# name=definition (no spaces). If the definition and the "=" are omitted, "=1"
+# is assumed. To prevent a macro definition from being undefined via #undef or
+# recursively expanded use the := operator instead of the = operator.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+PREDEFINED             = "__DOXYGEN__" \
+                         "__attribute__(x)="
+
+# If the MACRO_EXPANSION and EXPAND_ONLY_PREDEF tags are set to YES then this
+# tag can be used to specify a list of macro names that should be expanded. The
+# macro definition that is found in the sources will be used. Use the PREDEFINED
+# tag if you want to use a different macro definition that overrules the
+# definition found in the source code.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+EXPAND_AS_DEFINED      =
+
+# If the SKIP_FUNCTION_MACROS tag is set to YES then doxygen's preprocessor will
+# remove all references to function-like macros that are alone on a line, have
+# an all uppercase name, and do not end with a semicolon. Such function macros
+# are typically used for boiler-plate code, and will confuse the parser if not
+# removed.
+# The default value is: YES.
+# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.
+
+SKIP_FUNCTION_MACROS   = YES
+
+#---------------------------------------------------------------------------
+# Configuration options related to external references
+#---------------------------------------------------------------------------
+
+# The TAGFILES tag can be used to specify one or more tag files. For each tag
+# file the location of the external documentation should be added. The format of
+# a tag file without this location is as follows:
+# TAGFILES = file1 file2 ...
+# Adding location for the tag files is done as follows:
+# TAGFILES = file1=loc1 "file2 = loc2" ...
+# where loc1 and loc2 can be relative or absolute paths or URLs. See the
+# section "Linking to external documentation" for more information about the use
+# of tag files.
+# Note: Each tag file must have a unique name (where the name does NOT include
+# the path). If a tag file is not located in the directory in which doxygen is
+# run, you must also specify the path to the tagfile here.
+
+TAGFILES               =
+
+# When a file name is specified after GENERATE_TAGFILE, doxygen will create a
+# tag file that is based on the input files it reads. See section "Linking to
+# external documentation" for more information about the usage of tag files.
+
+GENERATE_TAGFILE       =
+
+# If the ALLEXTERNALS tag is set to YES, all external class will be listed in
+# the class index. If set to NO, only the inherited external classes will be
+# listed.
+# The default value is: NO.
+
+ALLEXTERNALS           = NO
+
+# If the EXTERNAL_GROUPS tag is set to YES, all external groups will be listed
+# in the modules index. If set to NO, only the current project's groups will be
+# listed.
+# The default value is: YES.
+
+EXTERNAL_GROUPS        = YES
+
+# If the EXTERNAL_PAGES tag is set to YES, all external pages will be listed in
+# the related pages index. If set to NO, only the current project's pages will
+# be listed.
+# The default value is: YES.
+
+EXTERNAL_PAGES         = YES
+
+# The PERL_PATH should be the absolute path and name of the perl script
+# interpreter (i.e. the result of 'which perl').
+# The default file (with absolute path) is: /usr/bin/perl.
+
+PERL_PATH              = /usr/bin/perl
+
+#---------------------------------------------------------------------------
+# Configuration options related to the dot tool
+#---------------------------------------------------------------------------
+
+# If the CLASS_DIAGRAMS tag is set to YES, doxygen will generate a class diagram
+# (in HTML and LaTeX) for classes with base or super classes. Setting the tag to
+# NO turns the diagrams off. Note that this option also works with HAVE_DOT
+# disabled, but it is recommended to install and use dot, since it yields more
+# powerful graphs.
+# The default value is: YES.
+
+CLASS_DIAGRAMS         = NO
+
+# You can define message sequence charts within doxygen comments using the \msc
+# command. Doxygen will then run the mscgen tool (see:
+# http://www.mcternan.me.uk/mscgen/)) to produce the chart and insert it in the
+# documentation. The MSCGEN_PATH tag allows you to specify the directory where
+# the mscgen tool resides. If left empty the tool is assumed to be found in the
+# default search path.
+
+MSCGEN_PATH            =
+
+# You can include diagrams made with dia in doxygen documentation. Doxygen will
+# then run dia to produce the diagram and insert it in the documentation. The
+# DIA_PATH tag allows you to specify the directory where the dia binary resides.
+# If left empty dia is assumed to be found in the default search path.
+
+DIA_PATH               =
+
+# If set to YES the inheritance and collaboration graphs will hide inheritance
+# and usage relations if the target is undocumented or is not a class.
+# The default value is: YES.
+
+HIDE_UNDOC_RELATIONS   = YES
+
+# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is
+# available from the path. This tool is part of Graphviz (see:
+# http://www.graphviz.org/), a graph visualization toolkit from AT&T and Lucent
+# Bell Labs. The other options in this section have no effect if this option is
+# set to NO
+# The default value is: YES.
+
+HAVE_DOT               = NO
+
+# The DOT_NUM_THREADS specifies the number of dot invocations doxygen is allowed
+# to run in parallel. When set to 0 doxygen will base this on the number of
+# processors available in the system. You can set it explicitly to a value
+# larger than 0 to get control over the balance between CPU load and processing
+# speed.
+# Minimum value: 0, maximum value: 32, default value: 0.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_NUM_THREADS        = 0
+
+# When you want a differently looking font in the dot files that doxygen
+# generates you can specify the font name using DOT_FONTNAME. You need to make
+# sure dot is able to find the font, which can be done by putting it in a
+# standard location or by setting the DOTFONTPATH environment variable or by
+# setting DOT_FONTPATH to the directory containing the font.
+# The default value is: Helvetica.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_FONTNAME           = Helvetica
+
+# The DOT_FONTSIZE tag can be used to set the size (in points) of the font of
+# dot graphs.
+# Minimum value: 4, maximum value: 24, default value: 10.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_FONTSIZE           = 10
+
+# By default doxygen will tell dot to use the default font as specified with
+# DOT_FONTNAME. If you specify a different font using DOT_FONTNAME you can set
+# the path where dot can find it using this tag.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_FONTPATH           =
+
+# If the CLASS_GRAPH tag is set to YES then doxygen will generate a graph for
+# each documented class showing the direct and indirect inheritance relations.
+# Setting this tag to YES will force the CLASS_DIAGRAMS tag to NO.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+CLASS_GRAPH            = YES
+
+# If the COLLABORATION_GRAPH tag is set to YES then doxygen will generate a
+# graph for each documented class showing the direct and indirect implementation
+# dependencies (inheritance, containment, and class references variables) of the
+# class with other documented classes.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+COLLABORATION_GRAPH    = YES
+
+# If the GROUP_GRAPHS tag is set to YES then doxygen will generate a graph for
+# groups, showing the direct groups dependencies.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+GROUP_GRAPHS           = YES
+
+# If the UML_LOOK tag is set to YES, doxygen will generate inheritance and
+# collaboration diagrams in a style similar to the OMG's Unified Modeling
+# Language.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+UML_LOOK               = NO
+
+# If the UML_LOOK tag is enabled, the fields and methods are shown inside the
+# class node. If there are many fields or methods and many nodes the graph may
+# become too big to be useful. The UML_LIMIT_NUM_FIELDS threshold limits the
+# number of items for each type to make the size more manageable. Set this to 0
+# for no limit. Note that the threshold may be exceeded by 50% before the limit
+# is enforced. So when you set the threshold to 10, up to 15 fields may appear,
+# but if the number exceeds 15, the total amount of fields shown is limited to
+# 10.
+# Minimum value: 0, maximum value: 100, default value: 10.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+UML_LIMIT_NUM_FIELDS   = 10
+
+# If the TEMPLATE_RELATIONS tag is set to YES then the inheritance and
+# collaboration graphs will show the relations between templates and their
+# instances.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+TEMPLATE_RELATIONS     = NO
+
+# If the INCLUDE_GRAPH, ENABLE_PREPROCESSING and SEARCH_INCLUDES tags are set to
+# YES then doxygen will generate a graph for each documented file showing the
+# direct and indirect include dependencies of the file with other documented
+# files.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+INCLUDE_GRAPH          = NO
+
+# If the INCLUDED_BY_GRAPH, ENABLE_PREPROCESSING and SEARCH_INCLUDES tags are
+# set to YES then doxygen will generate a graph for each documented file showing
+# the direct and indirect include dependencies of the file with other documented
+# files.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+INCLUDED_BY_GRAPH      = YES
+
+# If the CALL_GRAPH tag is set to YES then doxygen will generate a call
+# dependency graph for every global function or class method.
+#
+# Note that enabling this option will significantly increase the time of a run.
+# So in most cases it will be better to enable call graphs for selected
+# functions only using the \callgraph command. Disabling a call graph can be
+# accomplished by means of the command \hidecallgraph.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+CALL_GRAPH             = NO
+
+# If the CALLER_GRAPH tag is set to YES then doxygen will generate a caller
+# dependency graph for every global function or class method.
+#
+# Note that enabling this option will significantly increase the time of a run.
+# So in most cases it will be better to enable caller graphs for selected
+# functions only using the \callergraph command. Disabling a caller graph can be
+# accomplished by means of the command \hidecallergraph.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+CALLER_GRAPH           = NO
+
+# If the GRAPHICAL_HIERARCHY tag is set to YES then doxygen will graphical
+# hierarchy of all classes instead of a textual one.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+GRAPHICAL_HIERARCHY    = YES
+
+# If the DIRECTORY_GRAPH tag is set to YES then doxygen will show the
+# dependencies a directory has on other directories in a graphical way. The
+# dependency relations are determined by the #include relations between the
+# files in the directories.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DIRECTORY_GRAPH        = YES
+
+# The DOT_IMAGE_FORMAT tag can be used to set the image format of the images
+# generated by dot. For an explanation of the image formats see the section
+# output formats in the documentation of the dot tool (Graphviz (see:
+# http://www.graphviz.org/)).
+# Note: If you choose svg you need to set HTML_FILE_EXTENSION to xhtml in order
+# to make the SVG files visible in IE 9+ (other browsers do not have this
+# requirement).
+# Possible values are: png, png:cairo, png:cairo:cairo, png:cairo:gd, png:gd,
+# png:gd:gd, jpg, jpg:cairo, jpg:cairo:gd, jpg:gd, jpg:gd:gd, gif, gif:cairo,
+# gif:cairo:gd, gif:gd, gif:gd:gd, svg, png:gd, png:gd:gd, png:cairo,
+# png:cairo:gd, png:cairo:cairo, png:cairo:gdiplus, png:gdiplus and
+# png:gdiplus:gdiplus.
+# The default value is: png.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_IMAGE_FORMAT       = png
+
+# If DOT_IMAGE_FORMAT is set to svg, then this option can be set to YES to
+# enable generation of interactive SVG images that allow zooming and panning.
+#
+# Note that this requires a modern browser other than Internet Explorer. Tested
+# and working are Firefox, Chrome, Safari, and Opera.
+# Note: For IE 9+ you need to set HTML_FILE_EXTENSION to xhtml in order to make
+# the SVG files visible. Older versions of IE do not have SVG support.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+INTERACTIVE_SVG        = NO
+
+# The DOT_PATH tag can be used to specify the path where the dot tool can be
+# found. If left blank, it is assumed the dot tool can be found in the path.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_PATH               =
+
+# The DOTFILE_DIRS tag can be used to specify one or more directories that
+# contain dot files that are included in the documentation (see the \dotfile
+# command).
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOTFILE_DIRS           =
+
+# The MSCFILE_DIRS tag can be used to specify one or more directories that
+# contain msc files that are included in the documentation (see the \mscfile
+# command).
+
+MSCFILE_DIRS           =
+
+# The DIAFILE_DIRS tag can be used to specify one or more directories that
+# contain dia files that are included in the documentation (see the \diafile
+# command).
+
+DIAFILE_DIRS           =
+
+# When using plantuml, the PLANTUML_JAR_PATH tag should be used to specify the
+# path where java can find the plantuml.jar file. If left blank, it is assumed
+# PlantUML is not used or called during a preprocessing step. Doxygen will
+# generate a warning when it encounters a \startuml command in this case and
+# will not generate output for the diagram.
+
+PLANTUML_JAR_PATH      =
+
+# When using plantuml, the specified paths are searched for files specified by
+# the !include statement in a plantuml block.
+
+PLANTUML_INCLUDE_PATH  =
+
+# The DOT_GRAPH_MAX_NODES tag can be used to set the maximum number of nodes
+# that will be shown in the graph. If the number of nodes in a graph becomes
+# larger than this value, doxygen will truncate the graph, which is visualized
+# by representing a node as a red box. Note that doxygen if the number of direct
+# children of the root node in a graph is already larger than
+# DOT_GRAPH_MAX_NODES then the graph will not be shown at all. Also note that
+# the size of a graph can be further restricted by MAX_DOT_GRAPH_DEPTH.
+# Minimum value: 0, maximum value: 10000, default value: 50.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_GRAPH_MAX_NODES    = 50
+
+# The MAX_DOT_GRAPH_DEPTH tag can be used to set the maximum depth of the graphs
+# generated by dot. A depth value of 3 means that only nodes reachable from the
+# root by following a path via at most 3 edges will be shown. Nodes that lay
+# further from the root node will be omitted. Note that setting this option to 1
+# or 2 may greatly reduce the computation time needed for large code bases. Also
+# note that the size of a graph can be further restricted by
+# DOT_GRAPH_MAX_NODES. Using a depth of 0 means no depth restriction.
+# Minimum value: 0, maximum value: 1000, default value: 0.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+MAX_DOT_GRAPH_DEPTH    = 0
+
+# Set the DOT_TRANSPARENT tag to YES to generate images with a transparent
+# background. This is disabled by default, because dot on Windows does not seem
+# to support this out of the box.
+#
+# Warning: Depending on the platform used, enabling this option may lead to
+# badly anti-aliased labels on the edges of a graph (i.e. they become hard to
+# read).
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_TRANSPARENT        = NO
+
+# Set the DOT_MULTI_TARGETS tag to YES to allow dot to generate multiple output
+# files in one run (i.e. multiple -o and -T options on the command line). This
+# makes dot run faster, but since only newer versions of dot (>1.8.10) support
+# this, this feature is disabled by default.
+# The default value is: NO.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_MULTI_TARGETS      = NO
+
+# If the GENERATE_LEGEND tag is set to YES doxygen will generate a legend page
+# explaining the meaning of the various boxes and arrows in the dot generated
+# graphs.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+GENERATE_LEGEND        = YES
+
+# If the DOT_CLEANUP tag is set to YES, doxygen will remove the intermediate dot
+# files that are used to generate the various graphs.
+# The default value is: YES.
+# This tag requires that the tag HAVE_DOT is set to YES.
+
+DOT_CLEANUP            = YES

+ 46 - 0
inc/hid_usage_button.h

@@ -0,0 +1,46 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_BUTTON_H_
+#define _USB_HID_USAGE_BUTTON_H_
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES_BUTTON HID Usage Tables for Button
+ * \brief Contains USB HID Usages definitions for Button Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_BUTTON                 0x09
+
+#define HID_BUTTON_NO_PRESSED           0x00
+#define HID_BUTTON_1                    0x01
+#define HID_BUTTON_2                    0x02
+#define HID_BUTTON_3                    0x03
+#define HID_BUTTON_4                    0x04
+#define HID_BUTTON_5                    0x05
+
+/** @}  */
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif
+

+ 109 - 0
inc/hid_usage_desktop.h

@@ -0,0 +1,109 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_DESKTOP_H_
+#define _USB_HID_USAGE_DESKTOP_H_
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES_DESKTOP HID Usage Tables for Desktop
+ * \brief Contains USB HID Usages definitions for Generic Desktop Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_DESKTOP                0x01
+
+#define HID_DESKTOP_POINTER             0x01
+#define HID_DESKTOP_MOUSE               0x02
+#define HID_DESKTOP_JOYSTICK            0x04
+#define HID_DESKTOP_GAMEPAD             0x05
+#define HID_DESKTOP_KEYBOARD            0x06
+#define HID_DESKTOP_KEYPAD              0x07
+#define HID_DESKTOP_MULTIAXIS           0x08
+#define HID_DESKTOP_TABLET              0x09
+#define HID_DESKTOP_X                   0x30
+#define HID_DESKTOP_Y                   0x31
+#define HID_DESKTOP_Z                   0x32
+#define HID_DESKTOP_RX                  0x33
+#define HID_DESKTOP_RY                  0x34
+#define HID_DESKTOP_RZ                  0x35
+#define HID_DESKTOP_SLIDER              0x36
+#define HID_DESKTOP_DIAL                0x37
+#define HID_DESKTOP_WHEEL               0x38
+#define HID_DESKTOP_HAT_SWITCH          0x39
+#define HID_DESKTOP_COUNTEDBUF          0x3A
+#define HID_DESKTOP_BYTECOUNT           0x3B
+#define HID_DESKTOP_MOTION_WAKEUP       0x3C
+#define HID_DESKTOP_START               0x3D
+#define HID_DESKTOP_SELECT              0x3C
+#define HID_DESKTOP_VX                  0x40
+#define HID_DESKTOP_VY                  0x41
+#define HID_DESKTOP_VZ                  0x42
+#define HID_DESKTOP_VBRX                0x43
+#define HID_DESKTOP_VBRY                0x44
+#define HID_DESKTOP_VBRZ                0x45
+#define HID_DESKTOP_VNO                 0x46
+#define HID_DESKTOP_FEATURE_NOTIFY      0x47
+#define HID_DESKTOP_RESOLUTION_MULTIPLY 0x48
+#define HID_DESKTOP_SYS_CONTROL         0x80
+#define HID_DESKTOP_SYS_PWR_DOWN        0x81
+#define HID_DESKTOP_SYS_SLEEP           0x82
+#define HID_DESKTOP_SYS_WAKEUP          0x83
+#define HID_DESKTOP_SYS_CONTEXT_MENU    0x84
+#define HID_DESKTOP_SYS_MAIN_MENU       0x85
+#define HID_DESKTOP_SYS_APP_MENU        0x86
+#define HID_DESKTOP_SYS_MENU_HELP       0x87
+#define HID_DESKTOP_SYS_MENU_EXIT       0x88
+#define HID_DESKTOP_SYS_MENU_SELECT     0x89
+#define HID_DESKTOP_SYS_MENU_RIGHT      0x8A
+#define HID_DESKTOP_SYS_MENU_LEFT       0x8B
+#define HID_DESKTOP_SYS_MENU_UP         0x8C
+#define HID_DESKTOP_SYS_MENU_DOWN       0x8D
+#define HID_DESKTOP_SYS_RESTART_COLD    0x8E
+#define HID_DESKTOP_SYS_RESTART_WARM    0x8F
+#define HID_DESKTOP_DPAD_UP             0x90
+#define HID_DESKTOP_DPAD_DOWN           0x91
+#define HID_DESKTOP_DPAD_RIGHT          0x92
+#define HID_DESKTOP_DPAD_LEFT           0x93
+#define HID_DESKTOP_SYS_DOCK            0xA0
+#define HID_DESKTOP_SYS_UNDOCK          0xA1
+#define HID_DESKTOP_SYS_STARTUP         0xA2
+#define HID_DESKTOP_SYS_BREAK           0xA3
+#define HID_DESKTOP_SYS_DBG_BREAK       0xA4
+#define HID_DESKTOP_APP_BREAK           0xA5
+#define HID_DESKTOP_APP_DBG_BREAK       0xA6
+#define HID_DESKTOP_SYS_SPKR_MUTE       0xA7
+#define HID_DESKTOP_SYS_HIBERNATE       0xA8
+#define HID_DESKTOP_SYS_DISP_INVERT     0xB0
+#define HID_DESKTOP_SYS_DISP_INT        0xB1
+#define HID_DESKTOP_SYS_DISP_EXT        0xB2
+#define HID_DESKTOP_SYS_DISP_BOTH       0xB3
+#define HID_DESKTOP_SYS_DISP_DUAL       0xB4
+#define HID_DESKTOP_SYS_DISP_TOGGLE     0xB5
+#define HID_DESKTOP_SYS_DISP_SWAP       0xB6
+#define HID_DESKTOP_SYS_DISP_AUTOSCALE  0xB7
+
+/** @}  */
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif
+

+ 37 - 0
inc/hid_usage_device.h

@@ -0,0 +1,37 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_DEVICE_H_
+#define _USB_HID_USAGE_DEVICE_H_
+
+/**\ingroup USB_HID
+ * \addtogroup ISB_HID_USAGES_DEVICE HID Usages for Device
+ * \brief Contains USB HID Usages definitions for Generic Device Control Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_DEVICE                 0x06
+
+#define HID_DEVICE_BATTERY_STRENGHT     0x20
+#define HID_DEVICE_WIRELESS_CHANNEL     0x21
+#define HID_DEVICE_WIRELESS_ID          0x22
+#define HID_DEVICE_DISCO_WIRELESS_CTL   0x23
+#define HID_DEVICE_SECURITY_CHAR_ENT    0x24
+#define HID_DEVICE_SECURITY_CHAR_ERA    0x25
+#define HID_DEVICE_SCURITY_CODE_CLR     0x26
+
+#endif
+

+ 59 - 0
inc/hid_usage_game.h

@@ -0,0 +1,59 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_H_
+#define _USB_HID_USAGE_H_
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES_GAME HID Usage Tables for Game
+ * \brief Contains USB HID Usages definitions for Game Controls Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_GAME                   0x05
+
+#define HID_GAME_3D_GAME_CONTROLLER     0x01
+#define HID_GAME_PINBALL_DEVICE         0x02
+#define HID_GAME_GUN_DEVICE             0x03
+#define HID_GAME_POINT_OF_VIEW          0x20
+#define HID_GAME_TURN_LEFT_RIGHT        0x21
+#define HID_GAME_PITCH_FWD_BACK         0x22
+#define HID_GAME_ROLL_LEFT_RIGHT        0x23
+#define HID_GAME_MOVE_LEFT_RIGHT        0x24
+#define HID_GAME_MOVE_FWD_BACK          0x25     
+#define HID_GAME_MOVE_UP_DOWN           0x26
+#define HID_GAME_LEAN_LEFT_RIGHT        0x27
+#define HID_GAME_LEAN_FWD_BACK          0x28
+#define HID_GAME_HEIGHT_OF_POV          0x29
+#define HID_GAME_FLIPPER                0x2A
+#define HID_GAME_SECONDARY_FLIPPER      0x2B
+#define HID_GAME_BUMP                   0x2C
+#define HID_GAME_NEW_GAME               0x2D
+#define HID_GAME_SHOOT_BALL             0x2E
+#define HID_GAME_PLAYER                 0x2F
+#define HID_GAME_GUN_BOLT               0x30
+#define HID_GAME_GUN_CLIP               0x31
+#define HID_GAME_GUN_SELECTOR           0x32
+#define HID_GAME_GUN_SINGLE_SHOT        0x33
+#define HID_GAME_GUN_BURST              0x34
+#define HID_GAME_GUN_AUTOMATIC          0x35
+#define HID_GAME_GUN_SAFETY             0x36
+#define HID_GAME_GANEPAD_FIRE_JUMP      0x37
+#define HID_GAME_GAMEPAD_TRIGGER        0x38
+
+
+#endif
+

+ 245 - 0
inc/hid_usage_keyboard.h

@@ -0,0 +1,245 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#ifndef _USB_HID_USAGE_KEYBOARD_H_
+#define _USB_HID_USAGE_KEYBOARD_H_
+
+/**\ingroup USB_HID
+ * \addtogroup ISB_HID_USAGES_KEYBOARD HID Usages for Keyboard
+ * \brief Contains USB HID Usages definitions for Keyboard/Keypad Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_KEYBOARD               0x07
+
+#define HID_KEYBOARD_ERR_ROLL_OVER      0x01
+#define HID_KEYBOARD_POST_FAIL          0x02
+#define HID_KEYBOARD_ERR_UNDEFINED      0x03
+#define HID_KEYBOARD_A                  0x04
+#define HID_KEYBOARD_B                  0x05
+#define HID_KEYBOARD_C                  0x06
+#define HID_KEYBOARD_D                  0x07
+#define HID_KEYBOARD_E                  0x08
+#define HID_KEYBOARD_F                  0x09
+#define HID_KEYBOARD_G                  0x0A
+#define HID_KEYBOARD_H                  0x0B
+#define HID_KEYBOARD_I                  0x0C
+#define HID_KEYBOARD_J                  0x0D
+#define HID_KEYBOARD_K                  0x0E
+#define HID_KEYBOARD_L                  0x0F
+#define HID_KEYBOARD_M                  0x10
+#define HID_KEYBOARD_N                  0x11
+#define HID_KEYBOARD_O                  0x12
+#define HID_KEYBOARD_P                  0x13
+#define HID_KEYBOARD_Q                  0x14
+#define HID_KEYBOARD_R                  0x15
+#define HID_KEYBOARD_S                  0x16
+#define HID_KEYBOARD_T                  0x17
+#define HID_KEYBOARD_U                  0x18
+#define HID_KEYBOARD_V                  0x19
+#define HID_KEYBOARD_W                  0x1A
+#define HID_KEYBOARD_X                  0x1B
+#define HID_KEYBOARD_Y                  0x1C
+#define HID_KEYBOARD_Z                  0x1D
+#define HID_KEYBOARD_1                  0x1E
+#define HID_KEYBOARD_2                  0x1F
+#define HID_KEYBOARD_3                  0x20
+#define HID_KEYBOARD_4                  0x21
+#define HID_KEYBOARD_5                  0x22
+#define HID_KEYBOARD_6                  0x23
+#define HID_KEYBOARD_7                  0x24
+#define HID_KEYBOARD_8                  0x25
+#define HID_KEYBOARD_9                  0x26
+#define HID_KEYBOARD_0                  0x27
+#define HID_KEYBOARD_RETURN             0x28
+#define HID_KEYBOARD_ESCAPE             0x29
+#define HID_KEYBOARD_DELETE             0x2A
+#define HID_KEYBOARD_TAB                0x2B
+#define HID_KEYBOARD_SPACEBAR           0x2C
+#define HID_KEYBOARD_MINUS              0x2D
+#define HID_KEYBOARD_EQUAL_SIGN         0x2E
+#define HID_KEYBOARD_OPEN_BRACKET       0x2F
+#define HID_KEYBOARD_CLOSE_BRACKET      0x30
+#define HID_KEYBOARD_BACKSLASH          0x31
+#define HID_KEYBOARD_NONUS_HASH         0x32
+#define HID_KEYBOARD_SEMICOLON          0x33
+#define HID_KEYBOARD_APOSTROPHE         0x34
+#define HID_KEYBOARD_GRAVE_ACCENT       0x35
+#define HID_KEYBOARD_COLON              0x36
+#define HID_KEYBOARD_DOT                0x37
+#define HID_KEYBOARD_SLASH              0x38
+#define HID_KEYBOARD_CAPS_LOCK          0x39
+#define HID_KEYBOARD_F1                 0x3A
+#define HID_KEYBOARD_F2                 0x3B
+#define HID_KEYBOARD_F3                 0x3C
+#define HID_KEYBOARD_F4                 0x3D
+#define HID_KEYBOARD_F5                 0x3E
+#define HID_KEYBOARD_F6                 0x3F
+#define HID_KEYBOARD_F7                 0x40
+#define HID_KEYBOARD_F8                 0x41
+#define HID_KEYBOARD_F9                 0x42
+#define HID_KEYBOARD_F10                0x43
+#define HID_KEYBOARD_F11                0x44
+#define HID_KEYBOARD_F12                0x45
+#define HID_KEYBOARD_PRINT_SCREEN       0x46
+#define HID_KEYBOARD_SCROLL_LOCK        0x47
+#define HID_KEYBOARD_PAUSE              0x48
+#define HID_KEYBOARD_INSERT             0x49
+#define HID_KEYBOARD_HOME               0x4A
+#define HID_KEYBOARD_PAGE_UP            0x4B
+#define HID_KEYBOARD_DELETE_FORWARD     0x4C
+#define HID_KEYBOARD_END                0x4D
+#define HID_KEYBOARD_PAGE_DOWN          0x4E
+#define HID_KEYBOARD_RIGHT_ARROW        0x4F
+#define HID_KEYBOARD_LEFT_ARROW         0x50
+#define HID_KEYBOARD_DOWN_ARROW         0x51
+#define HID_KEYBOARD_UP_ARROW           0x52
+#define HID_KEYPAD_NUMLOCK              0x53
+#define HID_KEYPAD_SLASH                0x54
+#define HID_KEYPAD_ASTERISK             0x55
+#define HID_KEYPAD_MINUS                0x56
+#define HID_KEYPAD_PLUS                 0x57
+#define HID_KEYPAD_ENTER                0x58
+#define HID_KEYPAD_1                    0x59
+#define HID_KEYPAD_2                    0x5A
+#define HID_KEYPAD_3                    0x5B
+#define HID_KEYPAD_4                    0x5C
+#define HID_KEYPAD_5                    0x5D
+#define HID_KEYPAD_6                    0x5E
+#define HID_KEYPAD_7                    0x5F
+#define HID_KEYPAD_8                    0x60
+#define HID_KEYPAD_9                    0x61
+#define HID_KEYPAD_0                    0x62
+#define HID_KEYPAD_DOT                  0x63
+#define HID_KEYBOARD_NONUS_BACKSLASH    0x64
+#define HID_KEYBOARD_APPLICATION        0x65
+#define HID_KEYBOARD_POWER              0x66
+#define HID_KEYPAD_EQUAL                0x67
+#define HID_KEYBOARD_F13                0x68
+#define HID_KEYBOARD_F14                0x69
+#define HID_KEYBOARD_F15                0x6A
+#define HID_KEYBOARD_F16                0x6B
+#define HID_KEYBOARD_F17                0x6C
+#define HID_KEYBOARD_F18                0x6D
+#define HID_KEYBOARD_F19                0x6E
+#define HID_KEYBOARD_F20                0x6F
+#define HID_KEYBOARD_F21                0x70
+#define HID_KEYBOARD_F22                0x71
+#define HID_KEYBOARD_F23                0x72
+#define HID_KEYBOARD_F24                0x73
+#define HID_KEYBOARD_EXECUTE            0x74
+#define HID_KEYBOARD_HELP               0x75
+#define HID_KEYBOARD_MENU               0x76
+#define HID_KEYBOARD_SELECT             0x77
+#define HID_KEYBOARD_STOP               0x78
+#define HID_KEYBOARD_AGAIN              0x79
+#define HID_KEYBOARD_UNDO               0x7A
+#define HID_KEYBOARD_CUT                0x7B
+#define HID_KEYBOARD_COPY               0x7C
+#define HID_KEYBOARD_PASTE              0x7D
+#define HID_KEYBOARD_FIND               0x7E
+#define HID_KEYBOARD_MUTE               0x7F
+#define HID_KEYBOARD_VOLUME_UP          0x80
+#define HID_KEYBOARD_VOLUME_DOWN        0x81
+#define HID_KEYBOARD_LOCK_CAPS_LOCK     0x82
+#define HID_KEYBOARD_LOCK_NUM_LOCK      0x83
+#define HID_KEYBOARD_LOCK_SCROLL_LOCK   0x84
+#define HID_KEYPAD_COMMA                0x85
+#define HID_KEYPAD_EQUAL_SIGN           0x86
+#define HID_KEYBOARD_INTERNATIONAL_1    0x87
+#define HID_KEYBOARD_INTERNATIONAL_2    0x88
+#define HID_KEYBOARD_INTERNATIONAL_3    0x89
+#define HID_KEYBOARD_INTERNATIONAL_4    0x8A
+#define HID_KEYBOARD_INTERNATIONAL_5    0x8B
+#define HID_KEYBOARD_INTERNATIONAL_6    0x8C
+#define HID_KEYBOARD_INTERNATIONAL_7    0x8D
+#define HID_KEYBOARD_INTERNATIONAL_8    0x8E
+#define HID_KEYBOARD_INTERNATIONAL_9    0x8F
+#define HID_KEYBOARD_LANG_1             0x90
+#define HID_KEYBOARD_LANG_2             0x91
+#define HID_KEYBOARD_LANG_3             0x92
+#define HID_KEYBOARD_LANG_4             0x93
+#define HID_KEYBOARD_LANG_5             0x94
+#define HID_KEYBOARD_LANG_6             0x95
+#define HID_KEYBOARD_LANG_7             0x96
+#define HID_KEYBOARD_LANG_8             0x97
+#define HID_KEYBOARD_LANG_9             0x98
+#define HID_KEYBOARD_ALTERNATE_ERASE    0x99
+#define HID_KEYBOARD_SYSREQ             0x9A
+#define HID_KEYBOARD_CANCEL             0x9B
+#define HID_KEYBOARD_CLEAR              0x9C
+#define HID_KEYBOARD_PRIOR              0x9D
+#define HID_KEYBOARD_RETURN_1           0x9E
+#define HID_KEYBOARD_SEPARATOR          0x9F
+#define HID_KEYBOARD_OUT                0xA0
+#define HID_KEYBOARD_OPER               0xA1
+#define HID_KEYBOARD_CLEAR_AGAIN        0xA2
+#define HID_KEYBOARD_CRSEL_PROPS        0xA3
+#define HID_KEYBOARD_EXSEL              0xA4
+#define HID_KEYPAD_00                   0xB0
+#define HID_KEYPAD_000                  0xB1
+#define HID_KEYPAD_OPEN_PARENTHESIS     0xB6
+#define HID_KEYPAD_CLOSE_PARENTHESIS    0xB7
+#define HID_KEYPAD_OPEN_BRACE           0xB8
+#define HID_KEYPAD_CLOSE_BRACE          0xB9
+#define HID_KEYPAD_TAB                  0xBA
+#define HID_KEYPAD_BACKSPACE            0xBB
+#define HID_KEYPAD_A                    0xBC
+#define HID_KEYPAD_B                    0xBD
+#define HID_KEYPAD_C                    0xBE
+#define HID_KEYPAD_D                    0xBF
+#define HID_KEYPAD_E                    0xC0
+#define HID_KEYPAD_F                    0xC1
+#define HID_KEYPAD_XOR                  0xC2
+#define HID_KEYPAD_CARET                0xC3
+#define HID_KEYPAD_PERCENT              0xC4
+#define HID_KEYPAD_LESS_THEN            0xC5
+#define HID_KEYPAD_GREATER_THEN         0xC6
+#define HID_KEYPAD_AMPERSAND            0xC7
+#define HID_KEYPAD_DOUBLE_AMPERSAND     0xC8
+#define HID_KEYPAD_PIPE                 0xC9
+#define HID_KEYPAD_DOUBLE_PIPE          0xCA
+#define HID_KEYPAD_COLON                0xCB
+#define HID_KEYPAD_HASH                 0xCC
+#define HID_KEYPAD_SPACE                0xCD
+#define HID_KEYPAD_AT                   0xCE
+#define HID_KEYPAD_BANG                 0xCF
+#define HID_KEYPAD_MEM_STORE            0xD0
+#define HID_KEYPAD_MEM_RECALL           0xD1
+#define HID_KEYPAD_MEM_CLEAR            0xD2
+#define HID_KEYPAD_MEM_ADD              0xD3
+#define HID_KEYPAD_MEM_SUBTRACT         0xD4
+#define HID_KEYPAD_MEM_MULTIPLY         0xD5
+#define HID_KEYPAD_MEM_DIVIDE           0xD6
+#define HID_KEYPAD_PLUS_MINUS           0xD7
+#define HID_KEYPAD_CLEAR                0xD8
+#define HID_KEYPAD_CLEAR_ENTRY          0xD9
+#define HID_KEYPAD_BINARY               0xDA
+#define HID_KEYPAD_OCTAL                0xDB
+#define HID_KEYPAD_DECIMAL              0xDC
+#define HID_KEYPAD_HEXADECIMAL          0xDD
+#define HID_KEYBOARD_L_CTRL             0xE0
+#define HID_KEYBOARD_L_SHIFT            0xE1
+#define HID_KEYBOARD_L_ALT              0xE2
+#define HID_KEYBOARD_L_GUI              0xE3
+#define HID_KEYBOARD_R_CTRL             0xE4
+#define HID_KEYBOARD_R_SHIFT            0xE5
+#define HID_KEYBOARD_R_ALT              0xE6
+#define HID_KEYBOARD_R_GUI              0xE7
+
+/** @}  */
+
+#endif
+

+ 107 - 0
inc/hid_usage_led.h

@@ -0,0 +1,107 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_LED_H_
+#define _USB_HID_USAGE_LED_H_
+
+/**\ingroup USB_HID
+ * \addtogroup ISB_HID_USAGES_DEVICE HID Usages for LED's
+ * \brief Contains USB HID Usages definitions for LED's Control Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_LED                    0x08
+
+#define HID_LED_NUM_LOCK                0x01
+#define HID_LED_CAPS_LOCK               0x02
+#define HID_LED_SCROLL_LOCK             0x03
+#define HID_LED_COMPOSE                 0x04
+#define HID_LED_KANA                    0x05
+#define HID_LED_POWER                   0x06
+#define HID_LED_SHIFT                   0x07
+#define HID_LED_DO_NOT_DISTURB          0x08
+#define HID_LED_MUTE                    0x09
+#define HID_LED_TONE_ENABLE             0x0A
+#define HID_LED_HIGH_CUT_FILTER         0x0B
+#define HID_LED_LOW_CUT_FILTER          0x0C
+#define HID_LED_EQUALIZER_ENABLE        0x0D
+#define HID_LED_SOUND_FIELD_ON          0x0E
+#define HID_LED_SURROUND_ON             0x0F
+#define HID_LED_REPEAT                  0x10
+#define HID_LED_STEREO                  0x11
+#define HID_LED_SAMPLING_RATE_DETECT    0x12
+#define HID_LED_SPINNING                0x13
+#define HID_LED_CAV                     0x14
+#define HID_LED_CLV                     0x15
+#define HID_LED_REC_FORMAT_DETECT       0x16
+#define HID_LED_OFF_HOOK                0x17
+#define HID_LED_RING                    0x18
+#define HID_LED_MESSAGE_WAITING         0x19
+#define HID_LED_DATA_MODE               0x1A
+#define HID_LED_BATTERY_OPERATION       0x1B
+#define HID_LED_BATTERY_OK              0x1C
+#define HID_LED_BATTERY_LOW             0x1D
+#define HID_LED_SPEAKER                 0x1E
+#define HID_LED_HEADSET                 0x1F
+#define HID_LED_HOLD                    0x20
+#define HID_LED_MICROPHONE              0x21
+#define HID_LED_COVERAGE                0x22
+#define HID_LED_NIGHT_MODE              0x23
+#define HID_LED_SEND_CALLS              0x24
+#define HID_LED_CALL_PICKUP             0x25
+#define HID_LED_CONFERENCE              0x26
+#define HID_LED_STANDBY                 0x27
+#define HID_LED_CAMERA_ON               0x28
+#define HID_LED_CAMERA_OFF              0x29
+#define HID_LED_ONLINE                  0x2A
+#define HID_LED_OFFLINE                 0x2B
+#define HID_LED_BUSY                    0x2C
+#define HID_LED_READY                   0x2D
+#define HID_LED_PAPER_OUT               0x2E
+#define HID_LED_PAPER_JAM               0x2F
+#define HID_LED_REMOTE                  0x30
+#define HID_LED_FORWARD                 0x31
+#define HID_LED_REVERSE                 0x32
+#define HID_LED_STOP                    0x33
+#define HID_LED_REWIND                  0x34
+#define HID_LED_FAST_FORWARD            0x35
+#define HID_LED_PLAY                    0x36
+#define HID_LED_PAUSE                   0x37
+#define HID_LED_RECORD                  0x38
+#define HID_LED_ERROR                   0x39
+#define HID_LED_USAGE_SELECTED_IND      0x3A
+#define HID_LED_USAGE_INUSE_IND         0x3B
+#define HID_LED_USAGE_MULTIMODE_IND     0x3C
+#define HID_LED_INDICATOR_ON            0x3D
+#define HID_LED_INDICATOR_FLASH         0x3E
+#define HID_LED_INDICATOR_SLOW_BLINK    0x3F
+#define HID_LED_INDICATOR_FAST_BLINK    0x40
+#define HID_LED_INDICATOR_OFF           0x41
+#define HID_LED_FLASH_ON_TIME           0x42
+#define HID_LED_SLOW_BLINK_ON_TIME      0x43
+#define HID_LED_SLOW_BLINK_OFF_TIME     0x44
+#define HID_LED_FAST_BLINK_ON_TIME      0x45
+#define HID_LED_FAST_BLINK_OFF_TIME     0x46
+#define HID_LED_USAGE_INDICATOR_COLOR   0x47
+#define HID_LED_INDICATOR_RED           0x48
+#define HID_LED_INDICATOR_GREEN         0x49
+#define HID_LED_INDICATOR_AMBER         0x4A
+#define HID_LED_GENERIC_INDICATOR       0x4B
+#define HID_LED_SYSTEM_SUSPEND          0x4C
+#define HID_LED_EXT_POWER_CONNECTED     0x4D
+
+#endif
+

+ 45 - 0
inc/hid_usage_ordinal.h

@@ -0,0 +1,45 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_ORDINAL_H_
+#define _USB_HID_USAGE_ORDINAL_H_
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES_ORDINAL HID Usage Tables for Ordinal
+ * \brief Contains USB HID Usages definitions for Ordinal Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_ORDINAL                0x0A
+
+#define HID_ORDINAL_INSTANCE_1          0x01
+#define HID_ORDINAL_INSTANCE_2          0x02
+#define HID_ORDINAL_INSTANCE_3          0x03
+#define HID_ORDINAL_INSTANCE_4          0x04
+#define HID_ORDINAL_INSTANCE_5          0x05
+
+/** @}  */
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif
+

+ 91 - 0
inc/hid_usage_simulation.h

@@ -0,0 +1,91 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_SIMUL_H_
+#define _USB_HID_USAGE_SUMUL_H_
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES HID Usage Tables for Simulation
+ * \brief Contains USB HID Usages definitions for Simulation Controls Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_SIMULATION             0x02
+
+#define HID_SIMUL_FLIGHT                0x01
+#define HID_SIMUL_AUTOMOBILE            0x02
+#define HID_SIMUL_TANK                  0x03
+#define HID_SIMUL_SPACESHIP             0x04
+#define HID_SIMUL_SUBMARINE             0x05
+#define HID_SIMUL_SAILING               0x06
+#define HID_SIMUL_MOTOCYCLE             0x07
+#define HID_SIMUL_SPORTS                0x08
+#define HID_SIMUL_AIRPLANE              0x09
+#define HID_SIMUL_HELICOPTER            0x0A
+#define HID_SIMUL_MAGIC_CARPET          0x0B
+#define HID_SIMUL_BICYCLE               0x0C
+#define HID_SIMUL_FLIGHT_CONTROL_STICK  0x20
+#define HID_SIMUL_FLIGHT_STICK          0x21
+#define HID_SIMUL_CYCLIC_CONTROL        0x22
+#define HID_SIMUL_CYCLIC_TRIM           0x23
+#define HID_SIMUL_FLIGHT_YOKE           0x24
+#define HID_SIMUL_TRACK_CONTROL         0x25
+#define HID_SIMUL_ALIERON               0xB0
+#define HID_SIMUL_ALIERIN_TRIM          0xB1
+#define HID_SIMUL_ANTI_TORQUE           0xB2
+#define HID_SIMUL_AUTOPILOT_ENABLE      0xB3
+#define HID_SIMUL_CHAFF_RELEASE         0xB4
+#define HID_SIMUL_COLLECTIVE_CONTROL    0xB5
+#define HID_SIMUL_DRIVE_BRAKE           0xB6
+#define HID_SIMUL_ELECTR_COUNTERMEAS    0xB7
+#define HID_SIMUL_ELEVATOR              0xB8
+#define HID_SIMUL_ELEVATOR_TRIM         0xB9
+#define HID_SIMUL_RUDDER                0xBA
+#define HID_SIMUL_THROTTLE              0xBB
+#define HID_SIMUL_FLIGHT_COMM           0xBC
+#define HID_SIMUL_FLARE_RELEASE         0xBD
+#define HID_SIMUL_LANDING_GEAR          0xBE
+#define HID_SIMUL_TOE_BRAKE             0xBF
+#define HID_SIMUL_TRIGGER               0xC0
+#define HID_SIMUL_WEAPONS_ARM           0xC1
+#define HID_SIMUL_WEAPONS_SELECT        0xC2
+#define HID_SIMUL_WING_FLAPS            0xC3
+#define HID_SIMUL_ACCELERATOR           0xC4
+#define HID_SIMUL_BRAKE                 0xC5
+#define HID_SIMUL_CLUTCH                0xC6
+#define HID_SIMUL_SHIFTER               0xC7
+#define HID_SIMUL_STEERING              0xC8
+#define HID_SIMUL_TURRET_DIRECTION      0xC9
+#define HID_SIMUL_BARREL_ELEVATION      0xCA
+#define HID_SIMUL_DRIVE_PLANE           0xCB
+#define HID_SIMUL_BALLAST               0xCC
+#define HID_SIMUL_BICYCLE_CRANK         0xCD
+#define HID_SIMUL_HANDLE_BARS           0xCE
+#define HID_SIMUL_FRONT_BRAKE           0xCF
+#define HID_SIMUL_REAR_BRAKE            0xD0
+
+/** @}  */
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif
+

+ 74 - 0
inc/hid_usage_sport.h

@@ -0,0 +1,74 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_SPORT_H_
+#define _USB_HID_USAGE_SPORT_H_
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES_SPORT HID Usage Tables for Sport
+ * \brief Contains USB HID Usages definitions for Sport Controls Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_SPORT                  0x04
+
+#define HID_SPORT_BASEBALL_BAT          0x01
+#define HID_SPORT_GOLF_CLUB             0x02
+#define HID_SPORT_ROWING_MACHINE        0x03
+#define HID_SPORT_TREADMILL             0x04
+#define HID_SPORT_OAR                   0x30
+#define HID_SPORT_SLOPE                 0x31
+#define HID_SPORT_RATE                  0x32
+#define HID_SPORT_STICK_SPEED           0x33
+#define HID_SPORT_STICK_FACE_ANGLE      0x34
+#define HID_SPORT_STICK_HEEL_TOE        0x35
+#define HID_SPORT_STICK_FOLLOW_THROUGH  0x36
+#define HID_SPORT_STICK_TEMPO           0x37
+#define HID_SPORT_STICK_TYPE            0x38
+#define HID_SPORT_STICK_HEIGHT          0x39
+#define HID_SPORT_PUTTER                0x50
+#define HID_SPORT_1_IRON                0x51
+#define HID_SPORT_2_IRON                0x52
+#define HID_SPORT_3_IRON                0x53
+#define HID_SPORT_4_IRON                0x54
+#define HID_SPORT_5_IRON                0x55
+#define HID_SPORT_6_IRON                0x56
+#define HID_SPORT_7_IRON                0x57
+#define HID_SPORT_8_IRON                0x58
+#define HID_SPORT_9_IRON                0x59
+#define HID_SPORT_10_IRON               0x5A
+#define HID_SPORT_11_IRON               0x5B
+#define HID_SPORT_SAND_WEDGE            0x5C
+#define HID_SPORT_LOFT_WEDGE            0x5D
+#define HID_SPORT_POWER_WEDGE           0x5E
+#define HID_SPORT_1_WOOD                0x5F
+#define HID_SPORT_3_WOOD                0x60
+#define HID_SPORT_5_WOOD                0x61
+#define HID_SPORT_7_WOOD                0x62
+#define HID_SPORT_9_WOOD                0x63
+
+/** @}  */
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif
+

+ 105 - 0
inc/hid_usage_telephony.h

@@ -0,0 +1,105 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_TELEPHONY_H_
+#define _USB_HID_USAGE_TELEPHONY_H_
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES_TELEPHONY HID Usage Tables for Telephony
+ * \brief Contains USB HID Usages definitions for Telephony Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_TELEPHONY              0x0B
+
+#define HID_PHONE_PHONE                 0x01
+#define HID_PHONE_ANSWERING_MACHINE     0x02
+#define HID_PHONE_MESSAGE_CONTROLS      0x03
+#define HID_PHONE_HANDSET               0x04
+#define HID_PHONE_HEADSET               0x05
+#define HID_PHONE_TELEPHONY_KEYPAD      0x06
+#define HID_PHONE_PROGRAMMABLE_BUTTON   0x07
+#define HID_PHONE_HOOK_SWITCH           0x20
+#define HID_PHONE_FLASH                 0x21
+#define HID_PHONE_FEATURE               0x22
+#define HID_PHONE_HOLD                  0x23
+#define HID_PHONE_REDIAL                0x24
+#define HID_PHONE_TRANSFER              0x25
+#define HID_PHONE_DROP                  0x26
+#define HID_PHONE_PARK                  0x27
+#define HID_PHONE_FORWARD_CALLS         0x28
+#define HID_PHONE_ALTERNATE_FUNCTION    0x29
+#define HID_PHONE_LINE                  0x2A
+#define HID_PHONE_SPEAKERPHONE          0x2B
+#define HID_PHONE_CONFERENCE            0x2C
+#define HID_PHONE_RING_ENABLE           0x2D
+#define HID_PHONE_RING_SELECT           0x2E
+#define HID_PHONE_PHONE_MUTE            0x2F
+#define HID_PHONE_CALLER_ID             0x30
+#define HID_PHONE_SEND                  0x31
+#define HID_PHONE_SPEED_DIAL            0x50
+#define HID_PHONE_STORE_NUMBER          0x51
+#define HID_PHONE_RECALL_NUMBER         0x52
+#define HID_PHONE_PHONE_DIRECTORY       0x53
+#define HID_PHONE_VOICE_MAIL            0x70
+#define HID_PHONE_SCREEN_CALLS          0x71
+#define HID_PHONE_DO_NOT_DISTURB        0x72
+#define HID_PHONE_MESSAGE               0x73
+#define HID_PHONE_ANSWER_ON_OFF         0x74
+#define HID_PHONE_INSIDE_DIAL_TONE      0x90
+#define HID_PHONE_OUTSIDE_DIAL_TONE     0x91
+#define HID_PHONE_INSIDE_RING_TONE      0x92
+#define HID_PHONE_OUTSIDE_RING_TONE     0x93
+#define HID_PHONE_PRIORITY_RING_TONE    0x94
+#define HID_PHONE_INSIDE_RINGBACK       0x95
+#define HID_PHONE_PRIORITY_RINGBACK     0x96
+#define HID_PHONE_LINE_BUSY_TONE        0x97
+#define HID_PHONE_REORDER_TONE          0x98
+#define HID_PHONE_CALL_WAITING_TONE     0x99
+#define HID_PHONE_CONFIRMATION_TONE_1   0x9A
+#define HID_PHONE_CONFIRMATION_TONE_2   0x9B
+#define HID_PHONE_TONES_OFF             0x9C
+#define HID_PHONE_OUTSIDE_RINGBACK      0x9D
+#define HID_PHONE_RINGER                0x9E
+#define HID_PHONE_KEY_0                 0xB0
+#define HID_PHONE_KEY_1                 0xB1
+#define HID_PHONE_KEY_2                 0xB2
+#define HID_PHONE_KEY_3                 0xB3
+#define HID_PHONE_KEY_4                 0xB4
+#define HID_PHONE_KEY_5                 0xB5
+#define HID_PHONE_KEY_6                 0xB6
+#define HID_PHONE_KEY_7                 0xB7
+#define HID_PHONE_KEY_8                 0xB8
+#define HID_PHONE_KEY_9                 0xB9
+#define HID_PHONE_KEY_STAR              0xBA
+#define HID_PHONE_KEY_POUND             0xBB
+#define HID_PHONE_KEY_A                 0xBC
+#define HID_PHONE_KEY_B                 0xBD
+#define HID_PHONE_KEY_C                 0xBE
+#define HID_PHONE_KEY_D                 0xBF
+
+/** @}  */
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif
+

+ 44 - 0
inc/hid_usage_vr.h

@@ -0,0 +1,44 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_USAGE_VR_H_
+#define _USB_HID_USAGE_VR_H_
+
+/**\ingroup USB_HID
+ * \addtogroup USB_HID_USAGES_VR HID Usage Tables for VR
+ * \brief Contains USB HID Usages definitions for VR Control Page
+ * \details This module based on
+ * + [HID Usage Tables Version 1.12](http://www.usb.org/developers/hidpage/Hut1_12v2.pdf)
+ * @{ */
+
+#define HID_PAGE_VR                     0x03
+
+#define HID_VR_BELT                     0x01
+#define HID_VR_BODY_SUIT                0x02
+#define HID_VR_FLEXTOR                  0x03
+#define HID_VR_GLOVE                    0x04
+#define HID_VR_HEAD_TRACKER             0x05
+#define HID_VR_HEAD_MOUNTED_DISPLAY     0x06
+#define HID_VR_HAND_TRACKER             0x07
+#define HID_VR_OCULOMETER               0x08
+#define HID_VR_VEST                     0x09
+#define HID_VR_ANIMATRONIC_DEVICE       0x0A
+#define HID_VR_STEREO_ENABLE            0x20
+#define HID_VR_DISPLAY_ENABLE           0x21
+
+/** @}  */
+
+#endif
+

+ 226 - 0
inc/usb_cdc.h

@@ -0,0 +1,226 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#ifndef _USB_CDC_H_
+#define _USB_CDC_H_
+
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+/**\addtogroup USB_CDC USB CDC class
+ * \brief Generic USB CDC class definitions
+ * \details This module based on
+ * + Universal Serial Bus Class Definitions for Communications Devices Revision 1.2 (Errata 1)
+ * @{ */
+
+/**\name USB CDC Class codes
+ * @{ */
+#define USB_CLASS_CDC                       0x02 /**< Device/Interface belongs to the Communicational device class */
+#define USB_CLASS_CDC_DATA                  0x0A /**< Interface belongs to the Data Interface class */
+/** @} */
+
+/**\name USB CDC subclass codes
+ * @{ */
+#define USB_CDC_SUBCLASS_ACM                0x02 /**< Abstract Control Model */ 
+ /** @} */
+
+/**\name Communications Class Protocol Codes
+ * @{ */
+#define USB_CDC_PROTO_V25TER                0x01 /**< AT Commands: V.250 etc */
+ /** @} */
+
+
+/** \name Data Interface Class Protocol Codes 
+ * @{ */
+#define USB_CDC_PROTO_NTB                   0x01 /**< Network Transfer Block */ 
+#define USB_CDC_PROTO_HOST                  0xFD /**< Host based driver. \note This protocol code should only be used in messages between
+                                                  * host and device to identify the host driver portion of a protocol stack.*/
+#define USB_CDC_PROTO_CDCSPEC               0xFE /**< The protocol(s) are described using a Protocol Unit Functional Descriptors on Communication Class Interface.*/
+/** @} */
+
+/**\name USB CDC class-specified functional descriptors 
+ * @{ */
+#define USB_DTYPE_CDC_HEADER                0x00 /**< Header Functional Descriptor. \ref usb_cdc_header_desc */
+#define USB_DTYPE_CDC_CALL_MANAGEMENT       0x01 /**< Call Management Functional Descriptor. \ref usb_cdc_call_mgmt_desc */ 
+#define USB_DTYPE_CDC_ACM                   0x02 /**< Abstract Control Management Functional Descriptor. \ref usb_cdc_acm_desc */
+#define USB_DTYPE_CDC_UNION                 0x06 /**< Union Functional descriptor */
+#define USB_DTYPE_CDC_COUNTRY               0x07 /**< Country Selection Functional Descriptor */
+/** @} */
+
+
+
+/** \name USB CDC class-specific requests
+ * @{ */
+#define USB_CDC_SEND_ENCAPSULATED_CMD       0x00 /**< Used to issue a command in the format of the supported control protocol of the Communication Class interface. */
+#define USB_CDC_GET_ENCAPSULATED_RESP       0x01 /**< Used to request a response in the format of the supported control protocol of the Communication Class interface. */
+#define USB_CDC_SET_COMM_FEATURE            0x02 /**< Controls the settings for a particular communication feature of a particular target */
+#define USB_CDC_GET_COMM_FEATURE            0x03 /**< Returns the current settings for the communication feature as selected */
+#define USB_CDC_CLEAR_COMM_FEATURE          0x04 /**< Controls the settings for a particular communication feature of a particular 
+                                                  * target, setting the selected feature to its default state. */
+#define USB_CDC_SET_LINE_CODING             0x20 /**< Allows the host to specify typical asynchronous line-character formatting properties. */
+#define USB_CDC_GET_LINE_CODING             0x21 /**< Allows the host to find out the currently configured line coding. */
+#define USB_CDC_SET_CONTROL_LINE_STATE      0x22 /**< Generates RS-232/V.24 style control signals. */
+#define USB_CDC_SEND_BREAK                  0x23 /**< Sends special carrier modulation that generates an RS-232 style break. */
+/** @} */
+
+
+/**\name Generic CDC specific notifications
+ * @{ */
+#define USB_CDC_NTF_NETWORK_CONNECTION      0x00  /**< Allows the device to notify the host about network connection status. */
+#define USB_CDC_NTF_RESPONSE_AVAILABLE      0x01  /**< Allows the device to notify the host that a response is available. */
+#define USB_CDC_NTF_SERIAL_STATE            0x20  /**< Sends asynchronous notification of UART status. */ 
+#define USB_CDC_NTF_SPEED_CHANGE            0x2A  /**< allows the device to inform the host-networking driver that a change in either the uplink 
+                                                   * or the downlink bit rate of the connection has occurred. */
+/** @} */
+
+
+/**\anchor USB_CDC_ACMGMNTCAP
+ * \name USB CDC Abstract Control Management capabilities 
+ * @{ */
+#define USB_CDC_COMM_FEATURE                0x01 /**< Supports the request combination of Set_Comm_Feature, Clear_Comm_Feature, and Get_Comm_Feature. */
+#define USB_CDC_CAP_LINE                    0x02 /**< Supports the request combination of Set_Line_Coding, Set_Control_Line_State, Get_Line_Coding, and the notification Serial_State. */
+#define USB_CDC_CAP_BRK                     0x04 /**< Supports the request Send_Break */
+#define USB_CDC_CAP_NOTIFY                  0x08 /**< Supports notification Network_Connection. */
+/** @} */
+
+/**\anchor USB_CDC_CALLMGMTCAP
+ * \name USB CDC Call Management capabilities
+ * @{ */
+#define USB_CDC_CALL_MGMT_CAP_CALL_MGMT     0x01 /**< Device handles call management itself. */
+#define USB_CDC_CALL_MGMT_CAP_DATA_INTF     0x02 /**< Device can send/receive call management information over a Data Class interface. */
+/** @} */
+
+/**\anchor USB_CDC_LINECODE
+ * \name Line coding structire bit fields
+ * @{ */
+#define USB_CDC_1_STOP_BITS                 0x00
+#define USB_CDC_1_5_STOP_BITS               0x01
+#define USB_CDC_2_STOP_BITS                 0x02
+
+#define USB_CDC_NO_PARITY                   0x00
+#define USB_CDC_ODD_PARITY                  0x01
+#define USB_CDC_EVEN_PARITY                 0x02
+#define USB_CDC_MARK_PARITY                 0x03
+#define USB_CDC_SPACE_PARITY                0x04
+/** @} */
+
+/**\name SERIAL_STATE notification data values
+ * @{ */
+#define USB_CDC_STATE_RX_CARRIER          0x0001 /**< State of receiver carrier detection mechanism of device. This signal corresponds to V.24 signal 109 and RS-232 signal DCD. */
+#define USB_CDC_STATE_TX_CARRIER          0x0002 /**< State of transmission carrier. This signal corresponds to V.24 signal 106 and RS-232 signal DSR. */
+#define USB_CDC_STATE_BREAK               0x0004 /**< State of break detection mechanism of the device. */
+#define USB_CDC_STATE_RING                0x0008 /**< State of ring signal detection of the device. */
+#define USB_CDC_STATE_FRAMING             0x0010 /**< A framing error has occurred. */
+#define USB_CDC_STATE_PARITY              0x0020 /**< A parity error has occurred. */
+#define USB_CDC_STATE_OVERRUN             0x0040 /**< Received data has been discarded due to overrun in the device */
+/** @} */
+
+/** \brief Header Functional Descriptor
+ * \details Header Functional Descriptor marks the beginning of the concatenated set of functional descriptors for the interface. */
+
+struct usb_cdc_header_desc {
+    uint8_t     bFunctionLength;    /**< Size of this descriptor in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Header functional descriptor subtype \ref USB_DTYPE_CDC_HEADER */
+    uint16_t    bcdCDC;             /**< USB CDC Specification release number in binary-coded decimal. \see \ref VERSION_BCD macro */
+} __attribute__ ((packed));
+
+/** \brief Union Functional Descriptor
+ * \details The Union functional descriptor describes the relationship between a group of interfaces that can be considered to form
+ * a functional unit. It can only occur within the class-specific portion of an Interface descriptor. One of the interfaces in
+ * the group is designated as a master or controlling interface for the group, and certain class-specific messages can be
+ * sent to this interface to act upon the group as a whole.
+ */
+struct usb_cdc_union_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Union Functional Descriptor. \ref USB_DTYPE_CDC_UNION */
+    uint8_t     bMasterInterface0;  /**< The interface number of the CDC interface, designated as the master or controlling interface for the union. */
+    uint8_t     bSlaveInterface0;   /**< Interface number of first slave or associated interface in the union. */
+    /* ... and there could be other slave interfaces */
+} __attribute__ ((packed));
+
+/** \brief Country Selection Functional Descriptor
+ * \details The Country Selection functional descriptor identifies the countries in which the communication device is qualified to
+ * operate. The parameters of the network connection often vary from one country to another, especially in Europe. Also
+ * legal requirements impose certain restrictions on devices because of different regulations by the governing body of the
+ * network to which the device must adhere. This descriptor can only occur within the class-specific portion of an
+ * Interface descriptor and should only be provided to a master Communication Class interface of a union. The country
+ * codes used in the Country Selection Functional Descriptor are not the same as the country codes used in dialing
+ * international telephone calls. Implementers should refer to the ISO 3166 specification for more information.
+ */
+struct usb_cdc_country_desc {
+    uint8_t     bFunctionLength;     /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;     /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType;  /**< Country Selection Functional Descriptor \ref USB_DTYPE_CDC_COUNTRY */
+    uint8_t     iCountryCodeRelDate; /**< Index of a string giving the release date for the implemented ISO 3166 Country Codes. */
+    uint8_t     wCountyCode0;        /**< Country code in hexadecimal format as defined in ISO 3166, release date as specified
+                                      * in iCountryCodeRelDate for the first supported country. */
+    /* ... and there can be a lot of country codes */
+} __attribute__ ((packed));
+
+/** \brief Call Management Functional Descriptor.
+ * \details The Call Management functional descriptor describes the processing of calls for the Communication Class interface. It
+ * can only occur within the class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_call_mgmt_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Call Management functional descriptor subtype \ref USB_DTYPE_CDC_CALL_MANAGEMENT */
+    uint8_t     bmCapabilities;     /**< The \ref USB_CDC_CALLMGMTCAP "capabilities" that this configuration supports */
+    uint8_t     bDataInterface;     /**< Interface number of Data Class interface optionally used for call management. */
+} __attribute__ ((packed));
+
+/** \brief Abstract Control Management Functional Descriptor
+ * \details The Abstract Control Management functional descriptor describes the commands supported by the Communication
+ * Class interface, as defined in Section 3.6.2, with the SubClass code of Abstract Control Model. It can only occur
+ * within the class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_acm_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Abstract Control Management functional descriptor subtype \ref USB_DTYPE_CDC_ACM */
+    uint8_t     bmCapabilities;     /**< The \ref USB_CDC_ACMGMNTCAP "capabilities" that this configuration supports */
+} __attribute__ ((packed));
+
+///\brief Notification structure from CDC
+struct usb_cdc_notification {
+    uint8_t     bmRequestType;
+    uint8_t     bNotificationType;
+    uint16_t    wValue;
+    uint16_t    wIndex;
+    uint16_t    wLength;
+    uint8_t     Data[];
+} __attribute__ ((packed));
+
+/**\brief Line Coding Structure
+ * \details used in GET_LINE_CODING and SET_LINE_CODING requests
+ */
+struct usb_cdc_line_coding {
+    uint32_t    dwDTERate;          /**< Data terminal rate, in bits per second. */
+    uint8_t     bCharFormat;        /**< Stop bits */
+    uint8_t     bParityType;        /**< Parity */
+    uint8_t     bDataBits;          /**< Data bits (5,6,7,8 or 16) */
+} __attribute__ ((packed));
+
+
+/** @} */
+
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif /* _USB_CDC_H_ */

+ 85 - 0
inc/usb_cdca.h

@@ -0,0 +1,85 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/** \ingroup USB_CDC
+ *  \addtogroup USB_CDC_ATM USB CDC ATM subclass
+ *  \brief USB CDC ATM subclass definitions
+ *  \details This module based on "Universal Serial Bus Communications Class Subclass Specification for Asynchronous Transfer Mode Devices" Revision 1.2
+ * @{ */
+
+#ifndef _USB_CDC_ATM_H_
+#define _USB_CDC_ATM_H_
+
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\name Communications Class Subclass Codes
+ * @{ */
+#define USB_CDC_SUBCLASS_ATM                0x07 /**< ATM Networking Control Model */ 
+ /* @} */
+
+
+/**\name CDC ATM subclass specific Functional Descriptors codes
+ * @{ */
+#define USB_DTYPE_CDC_ATM                   0x10 /**< ATM Networking Functional Descriptor */
+/** @} */    	
+
+/**\name CDC ATM subclass specific requests
+ * @{ */
+#define USB_CDC_SET_ATM_DATA_FORMAT         0x50 /**< Chooses which ATM data format will be exchanged between the host and the ATM Networking device. */
+#define USB_CDC_GET_ATM_DEVICE_STATISTICS   0x51 /**< Retrieves global statistics from the ATM Networking device. */
+#define USB_CDC_SET_ATM_DEFAULT_VC          0x52 /**< Pre-selects the VPI/VCI value for subsequent GET_ATM_DEVICE_STATISTICS requests */
+#define USB_CDC_GET_ATM_VC_STATISTICS       0x53 /**< Retrieves statistics from the ATM Networking device for a particular VPI/VCI. */
+/** @} */
+
+
+/**\name ATM Device Statistics Feature Selector Codes
+ * @{ */
+#define ATM_STAT_US_CELLS_SENT              0x01 /**< The number of cells that have been sent upstream to the WAN link by the ATM layer. */
+#define ATM_STAT_DS_CELLS_RECEIVED          0x02 /**< The number of cells that have been received downstream from the WAN link by the ATM layer */
+#define ATM_STAT_DS_CELLS_USB_CONGESTION    0x03 /**< The number of cells that have been received downstream from the WAN link by the ATM
+                                                  * layer and discarded due to congestion on the USB link. */
+#define ATM_STAT_DS_CELLS_AAL5_CRC_ERROR    0x04 /**< The number of cells that have been received downstream from the WAN link by the ATM
+                                                  * layer and discarded due to AAL5 CRC errors. */
+#define ATM_STAT_DS_CELLS_HEC_ERROR         0x05 /**< The number of cells that have been received downstream from the WAN link and discarded
+                                                  * due to HEC errors in the cell header. */
+#define ATM_STAT_DS_CELLS_HEC_ERROR_CORRT   0x06 /**< The number of cells that have been received downstream from the WAN link and have 
+                                                  * been detected with HEC errors in the cell header and successfully corrected. */
+/** @} */
+
+/**\brief ATM Networking Functional Descriptor */        
+struct usb_cdc_atm_desc {
+    uint8_t     bFunctionLength;        /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;        /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType;     /**< ATM Networking Functional Descriptor subtype \ref USB_DTYPE_CDC_ATM */
+    uint8_t     iEndSystemIdentifier;   /**< The string descriptor holds the End System Identifier. */
+    uint8_t     bmDataCapabilities;     /**< The ATM data types the device supports */
+    uint8_t     bmATMDeviceStatistics;  /**< Indicates which optional statistics functions the device collects. */
+    uint16_t    wType2MaxSegmentSize;   /**< The maximum segment size that the Type 2 device is capable of supporting */
+    uint16_t    wType3MaxSegmentSize;   /**< The maximum segment size that the Type 3 device is capable of supporting */
+    uint16_t    wMaxVC;                 /**< The maximum number of simultaneous virtual circuits the device is capable
+                                         * of supporting (Type 3 only) */
+} __attribute__((packed));
+
+/** @} */
+
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif /* _USB_CDC_ATM_H_ */    	

+ 77 - 0
inc/usb_cdce.h

@@ -0,0 +1,77 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/** \ingroup USB_CDC
+ *  \addtogroup USB_CDC_ECM USB CDC ECM subclass
+ *  \brief USB CDC ECM subclass definitions
+ *  \details Includes following subclasses
+ * + Ethernet Control Model
+ * @{ */
+
+#ifndef _USB_CDC_ECM_H_
+#define _USB_CDC_ECM_H_
+
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\name Communications Class Subclass Codes
+ * @{ */
+#define USB_CDC_SUBCLASS_ETH                0x06 /**< Ethernet Networking Control Model */
+ /* @} */
+
+/**\name CDC ECM subclass specific Functional Descriptors codes
+ * @{ */
+#define USB_DTYPE_CDC_ETHERNET              0x0F /**< Ethernet Networking Functional Descriptor*/
+/** @} */    	
+
+/**\name CDC ECM subclass specific requests
+ * @{ */
+#define USB_CDC_SET_ETH_MULTICAST_FILTERS   0x40 /**<  */
+#define USB_CDC_SET_ETH_PM_PATTERN_FILTER   0x41 /**<  */
+#define USB_CDC_GET_ETH_PM_PATTERN_FILTER   0x42 /**<  */
+#define USB_CDC_SET_ETH_PACKET_FILTER       0x43 /**< Sets device filter for running a network analyzer application on the host machine */
+#define USB_CDC_GET_ETH_STATISTIC           0x44 /**< Retrieves Ethernet device statistics such as frames transmitted, frames received, and bad frames received. */
+/** @} */
+
+
+/**\brief Ethernet Networking Functional Descriptor
+ * \details describes the operational modes supported by the
+ * Communications Class interface, as defined in Section 3.4, with the SubClass code of Ethernet
+ * Networking Control. It can only occur within the class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_ether_desc {
+    uint8_t     bFunctionLength;				/**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;				/**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType;				/**< Ethernet Networking Functional Descriptor. \ref USB_DTYPE_CDC_ETHERNET */
+    uint8_t     iMACAddress;					/**< Index of string descriptor that holds the 48bit Ethernet MAC address. */
+    uint32_t    bmEthernetStatistics;			/**< Indicates which Ethernet statistics functions the device collects. */
+    uint16_t    wMaxSegmentSize;				/**< The maximum segment size that the Ethernet device is capable of supporting. */
+    uint16_t    wNumberMCFilters;				/**< Contains the number of multicast filters that can be configured by the host. */
+    uint8_t     bNumberPowerFilters;			/**< Contains the number of pattern filters that are available for causing wake-up of the host. */
+} __attribute__ ((packed));
+
+
+
+
+/** @} */
+
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif /* _USB_CDC_ECM_H_ */    	

+ 185 - 0
inc/usb_cdci.h

@@ -0,0 +1,185 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/** \ingroup USB_CDC
+ *  \addtogroup USB_CDC_ISDN USB CDC ISDN subclass
+ *  \brief USB CDC ISDN subclass definitions
+ *  \details This module based on "Universal Serial Bus Communications Class Subclass Specification for ISDN Devices" Revision 1.2
+ *  \details This module cotains definitions for
+ * + Multiple Line Control Model
+ * + CAPI Control Model
+ * @{ */
+
+#ifndef _USB_CDC_ISDN_H_
+#define _USB_CDC_ISDN_H_
+
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\name Communications Class Subclass Codes
+ * @{ */
+#define USB_CDC_SUBCLASS_MCNL               0x04 /**< Multi-Channel Control Model */
+#define USB_CDC_SUBCLASS_CAPI               0x05 /**< CAPI Control Model */
+ /* @} */
+
+/** \name CDC ISDN Data Interface Class Protocol Codes 
+ * @{ */
+#define USB_CDC_PROTO_I340                  0x30 /**< Physical interface protocol for ISDN BRI */
+#define USB_CDC_PROTO_HDLC                  0x31 /**< HDLC */
+#define USB_CDC_PROTO_TRANSPARENT           0x32 /**< Transparent */
+#define USB_CDC_PROTO_Q921M                 0x50 /**< Management protocol for Q.921 data link protocol */
+#define USB_CDC_PROTO_Q921                  0x51 /**< Data link protocol for Q.931 */
+#define USB_CDC_PROTO_Q921TM                0x52 /**< TEI-multiplexor for Q.921 data link protocol */
+#define USB_CDC_PROTO_V42BIS                0x90 /**< Data compression procedures */
+#define USB_CDC_PROTO_Q931                  0x91 /**< Euro-ISDN protocol control */
+#define USB_CDC_PROTO_V120                  0x92 /**< V.24 rate adaptation to ISDN */
+#define USB_CDC_PROTO_CAPI20                0x93 /**< CAPI Commands */
+/** @} */
+
+/**\name CDC ISDN subclass specific Functional Descriptors codes
+ * @{ */
+#define USB_DTYPE_CDC_TERMINAL              0x09 /**< USB Terminal Functional Descriptor \ref usb_cdc_terminal_desc */
+#define USB_DTYPE_CDC_NETWORK_TERMINAL      0x0A /**< Network Channel Terminal Descriptor \ref usb_cdc_network_terminal_desc*/
+#define USB_DTYPE_CDC_PROTOCOL_UNIT         0x0B /**< Protocol Unit Functional Descriptor \ref usb_cdc_proto_unit_desc*/
+#define USB_DTYPE_CDC_EXTENSION_UNIT        0x0C /**< Extension Unit Functional Descriptor \ref usb_cdc_ext_unit_desc*/
+#define USB_DTYPE_CDC_MCNL_MANAGEMENT       0x0D /**< Multi-Channel Management Functional Descriptor \ref usb_cdc_mcnl_managemnt_desc */
+#define USB_DTYPE_CDC_CAPI_CONTROL          0x0E /**< CAPI Control Management Functional Descriptor */
+/** @} */    	
+
+/**\name CDC ISDN subclass specific requests
+ * @{ */
+#define USB_CDC_SET_UNIT_PARAMETER          0x37 /**< Used to set a Unit specific parameter. */
+#define USB_CDC_GET_UNIT_PARAMETER          0x38 /**< Used to retrieve a Unit specific parameter */
+#define USB_CDC_CLEAR_UNIT_PARAMETER        0x39 /**< Used to set a Unit specific parameter to its default state. */
+#define USB_CDC_GET_PROFILE                 0x3A /**< Returns the implemented capabilities of the device */
+/** @} */
+
+/**\anchor USB_DFU_MCNHCAP
+ * \name Multi-Channel Management Functional Descriptor capabilities
+ * @{ */
+#define USB_CDC_MCHN_UNIT_NVRAM             0x01 /**< Device stores Unit parameters in non-volatile memory. */
+#define USB_CDC_MCHN_UNIT_CLR               0x02 /**< Device supports the request Clear_Unit_Parameter. */
+#define USB_CDC_MCHN_UNIR_SET               0x04 /**< Device supports the request Set_Unit_Parameter.*/
+/** @} */
+
+/**\anchor USB_DFU_CAPICAP
+ * \name CAPI Control Management Functional Descriptor capabilities
+ * @{ */
+#define USB_CDC_CAPI_SIMPLE                 0x00 /**< Device is a Simple CAPI device. */
+#define USB_CDC_CAPI_INTELLIGENT            0x01 /**< Device is an Intelligent CAPI device. */
+/** @} */
+
+/** \brief USB Terminal Functional Descriptor
+ * \details The USB Terminal Functional Descriptor provides a means to indicate a relationship between a Unit and an USB
+ * Interface. It also defines parameters specific to the interface between the device and the host. It can only occur within
+ * the class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_terminal_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< USB Terminal Functional Descriptor \ref USB_DTYPE_CDC_TERMINAL */
+    uint8_t     bEntityId;          /**< Constant uniquely identifying the Terminal */
+    uint8_t     bInInterfaceNo;     /**< The input interface number of the associated USB interface. */
+    uint8_t     bOutInterfaceNo;    /**< The output interface number of the associated USB interface. */
+    uint8_t     bmOptions;          /**< D0: Protocol wrapper usage */
+    uint8_t     bChildId0;          /**< First ID of lower Terminal or Unit to which this Terminal is connected. */
+    /* ... and there can be a lot of Terminals or Units */
+} __attribute__ ((packed));
+
+/** \brief Network Channel Terminal Functional Descriptor
+ * \details The Network Channel Terminal Functional descriptor provides a means to indicate a relationship between a Unit and a
+ * Network Channel. It can only occur within the class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_network_terminal_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Network Channel Terminal Functional Descriptor \ref USB_DTYPE_CDC_NETWORK_TERMINAL */
+    uint8_t     bEntityId;          /**< Constant uniquely identifying the Terminal */
+    uint8_t     iName;              /**< Index of string descriptor, describing the name of the Network Channel Terminal. */
+    uint8_t     bChannelIndex;      /**< The channel index of the associated network channel according to indexing rules below. */
+    uint8_t     bPhysicalInterface; /**< Type of physical interface. 
+                                     *  + 0 none
+                                     *  + 1 ISDN
+                                     *  + 2-200 RESERVED
+                                     *  + 201 -255 Vendor specific */
+} __attribute__ ((packed));
+
+/** \brief Protocol Unit Functional Descriptor
+ * \details A communication protocol stack is a combination of communication functions (protocols) into a layered structure.
+ * Each layer in the stack presents some abstract function for the layer above according to some layer-interface-standard,
+ * making it possible to replace a function with another as long as it conforms to the standard. Each layer may have a set
+ * of protocol parameters, defined in Appendix E, to configure it for proper operation in the actual environment and the
+ * parameters may be retrieved and/or modified. The Unit state is initially reset. See Section 6.2.23 “SetUnitParameter”,
+ * Section 6.2.24 “GetUnitParameter”, and Section 6.2.25 “ClearUnitParameter” for details.
+ * A Protocol Unit Functional Descriptor identifies with bEntityId a specific protocol instance of bProtocol in a stack. It
+ * can only occur within the class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_proto_unit_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Network Channel Terminal Functional Descriptor \ref USB_DTYPE_CDC_PROTOCOL_UNIT */
+    uint8_t     bEntityId;          /**< Constant uniquely identifying the Unit */
+    uint8_t     bProtocol;          /**< Protocol code */
+
+} __attribute__ ((packed));
+
+/** \brief Extension Unit Functional Descriptor
+ * \details The Extension Unit Functional Descriptor provides minimal information about the Extension Unit for a
+ * generic driver at least to notice the presence of vendor-specific components within the protocol stack.
+ */
+struct usb_cdc_ext_unit_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Network Channel Terminal Functional Descriptor \ref USB_DTYPE_CDC_EXTENSION_UNIT */
+    uint8_t     bEntityId;          /**< Constant uniquely identifying the Unit */
+    uint8_t     bExtensionCode;     /**< Vendor specific code identifying the Extension Unit. */
+    uint8_t     iName;              /**< Index of string descriptor, describing the name of the Extension Unit. */
+    uint8_t     bChildId0;          /**< First ID of lower Terminal or Unit to which this Terminal is connected. */
+    /* ... and there can be a lot of Terminals or Units */
+} __attribute__ ((packed));
+
+/**\brief Multi-Channel Management Functional Descriptor
+ * \details The Multi-Channel Management functional descriptor describes the commands supported by the
+ * Communications Class interface, as defined in CDC , with the SubClass code of Multi-Channel.
+ */
+struct usb_cdc_mcnl_managemnt_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Multi-Channel Management Functional Descriptor \ref USB_DTYPE_CDC_MCNL_MANAGEMENT */
+    uint8_t     bmCapabilities;     /**< The capabilities that this configuration supports. \ref USB_DFU_MCNHCAP */
+} __attribute__ ((packed));
+
+/**\brief CAPI Control Management Functional Descriptor
+ * \details The CAPI control management functional descriptor describes the commands supported by the CAPI
+ * Control Model over the Data Class interface with the protocol code of CAPI control.
+ */
+struct usb_cdc_capi_ctl_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< CAPI Control Management Functional Descriptor \ref USB_DTYPE_CDC_CAPI_CONTROL */
+    uint8_t     bmCapabilities;     /**< The capabilities that this configuration supports. \ref USB_DFU_CAPICAP */    
+} __attribute__ ((packed));
+
+
+/** @} */
+
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif /* _USB_CDC_ISDN_H_ */    	

+ 166 - 0
inc/usb_cdcp.h

@@ -0,0 +1,166 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/** \ingroup USB_CDC
+ *  \addtogroup USB_CDC_PSTN USB CDC PSTN subclass
+ *  \brief USB CDC PSTN subclass definitions
+ *  \details This module based on "Universal Serial Bus Communications Class Subclass Specification for PSTN Devices" Revision 1.2
+ *  \details This module contains definitions for
+ * + Direct Line Control Model
+ * + Telephony Control Model
+ * @{ */
+
+#ifndef _USB_CDC_PSTN_H_
+#define _USB_CDC_PSTN_H_
+
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\name Communications Class Subclass Codes
+ * @{ */
+#define USB_CDC_SUBCLASS_DLC                0x01 /**< Direct Line Control Model */  
+#define USB_CDC_SUBCLASS_TEL                0x03 /**< Telephone Control Model */
+ /* @} */
+
+/**\name CDC PSTN subclass specific Functional Descriptors codes
+ * @{ */
+#define USB_DTYPE_CDC_ACM                   0x02 /**< Abstract Control Management Functional Descriptor. \ref usb_cdc_acm_desc */
+#define USB_DTYPE_CDC_LINE_MANAGEMENT       0x03 /**< Direct Line Management Functional Descriptor.\ref usb_cdc_dlm_desc */
+#define USB_DTYPE_CDC_TEL_RING              0x04 /**< Telephone Ringer Functional Descriptor. \ref usb_cdc_tring_desc */
+#define USB_DTYPE_CDC_TEL_CALL              0x05 /**< Telephone Call and Line State Reporting Capabilities Functional Descriptor. */
+#define USB_DTYPE_CDC_TEL_OPMODE            0x08 /**< Telephone Operational Modes Functional Descriptor */
+/** @} */    	
+
+/**\name CDC PSTN subclass specific requests
+ * @{ */
+#define USB_CDC_SET_AUX_LINE_STATE          0x10 /**< Used to connect or disconnect a secondary jack to POTS circuit or CODEC, depending on hook state. */
+#define USB_CDC_SET_HOOK_STATE              0x11 /**< Used to set the necessary POTS line relay code for on-hook, off-hook, and caller ID states. */
+#define USB_CDC_PULSE_SETUP                 0x12 /**< Used to prepare for a pulse-dialing cycle. */
+#define USB_CDC_SEND_PULSE                  0x13 /**< Used to generate a specified number of make/break pulse cycles. */
+#define USB_CDC_SET_PULSE_TIME              0x14 /**< Sets the timing of the make and break periods for pulse dialing. */
+#define USB_CDC_RING_AUX_JACK               0x15 /**< Used to generate a ring signal on a secondary phone jack. */
+#define USB_CDC_SET_RINGER_PARMS            0x30 /**< Configures the ringer for the communication device. */
+#define USB_CDC_GET_RINGER_PARMS            0x31 /**< Returns the ringer capabilities of the device and the current status of the device’s ringer. */
+#define USB_CDC_SET_OPERATION_PARMS         0x32 /**< Sets the operational mode for the device, between a simple mode, standalone mode and a host centric mode. */
+#define USB_CDC_GET_OPERATION_PARMS         0x33 /**< Gets the current operational mode for the device. */
+#define USB_CDC_SET_LINE_PARMS              0x34 /**< Used to change the state of the line. */
+#define USB_CDC_GET_LINE_PARMS              0x35 /**< Used to report the state of the line. */
+#define USB_CDC_DIAL_DIGITS                 0x36 /**< Dials the DTMF digits over the specified line. */
+/** @} */
+
+/**\name CDC PSTN subclass specific notifications
+ * @{ */
+#define USB_CDC_NTF_AUX_JACK_HOOK_STATE		0x08  /**< Indicates the loop has changed on the auxiliary phone interface. */
+#define USB_CDC_NTF_RING_DETECT				0x09  /**< Indicates ring voltage on the POTS line interface */
+#define USB_CDC_NTF_CALL_STATE_CHANGE		0x28  /**< Identifies that a change has occurred to the state of a call on the line corresponding to 
+												   * the interface or union for the line. */
+#define USB_CDC_NTF_LINE_STATE_CHANGE		0x29  /**< identifies that a change has occurred to the state of the line corresponding to theinterface
+												   * or master interface of a union */
+/** @} */
+
+
+/**\anchor USB_CDC_DLMGMNTCAP
+ * \name USB CDC Direct Line Management capabilities 
+ * @{ */
+#define USB_CDC_DLM_PULSE                   0x01 /**< Supports the request combination of Pulse_Setup, Send_Pulse, and Set_Pulse_Time. */
+#define USB_CDC_DLM_AUX                     0x02 /**< Supports the request combination of Set_Aux_Line_State, Ring_Aux_Jack, and notification Aux_Jack_Hook_State. */
+#define USB_CDC_DLM_XTRAPULSE               0x04 /**< Device requires extra Pulse_Setup request during pulse dialing sequence to disengage holding circuit */
+/** @} */
+
+/**\anchor USB_CDC_TOMCAP
+ * \name USB CDC Telephone Operational Modes capabilities
+ * @{ */
+#define USB_CDC_TOM_SIMPLE                  0x01 /**< Supports Simple mode. */
+#define USB_CDC_TOM_STANDALONE              0x02 /**< Supports Standalone mode. */
+#define USB_CDC_TOM_CENTRIC                 0x04 /**< Supports Computer Centric mode. */
+ /** @} */
+
+/**\anchor USB_CDC_TCSCAP
+ * \name USB CDC Telephone Call State Reporting capabilities
+ * @{ */
+#define USB_CDC_TCS_DIALTONE                0x01 /**< Reports interrupted dialtone in addition to normal dialtone. */
+#define USB_CDC_TCS_STATE                   0x02 /**< Reports ringback, busy, and fast busy states. */
+#define USB_CDC_TCS_CALLERID                0x04 /**< Reports caller ID information. */
+#define USB_CDC_TCS_RINGING                 0x08 /**< Reports incoming distinctive ringing patterns. */
+#define USB_CDC_TCS_DTMF                    0x10 /**< Can report DTMF digits input remotely over the telephone line. */
+#define USB_CDC_TCS_NOTIFY                  0x20 /**< Does support line state change notification. */
+ /** @} */
+
+
+
+
+/** \brief Direct Line Management Functional Descriptor
+ * \details The Direct Line Management functional descriptor describes the commands supported by the Communication Class
+ * interface, as defined in Section 3.6.1, with the SubClass code of Direct Line Control Model. It can only occur within
+ * the class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_dlm_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Direct Line Management Functional Descriptor. \ref USB_DTYPE_CDC_LINE_MANAGEMENT */
+    uint8_t     bmCapabilities;     /**< The \ref USB_CDC_DLMGMNTCAP "capabilities" that this configuration supports */    
+} __attribute__ ((packed));
+
+/** \brief Telephone Ringer Functional Descriptor
+ * \details The Telephone Ringer functional descriptor describes the ringer capabilities supported by the Communication Class
+ * interface, as defined in Section 3.6.3.1, with the SubClass code of Telephone Control. It can only occur within the
+ * class-specific portion of an Interface descriptor.
+ */
+struct usb_cdc_tring_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Direct Line Management Functional Descriptor. \ref USB_DTYPE_CDC_TEL_RING */
+    uint8_t     bRingerVolSteps;    /**< Number of discrete steps in volume supported by the ringer, values are:
+                                     * + 0: 256 discrete volume steps.
+                                     * + 1: Fixed volume. Value 0 will be ringer off
+                                     * + N: N volume steps. Value 0 will be ringer off. */
+    uint8_t     bNumRingerPatterns; /**< Number of ringer patterns supported */
+} __attribute__ ((packed));
+
+/** \brief Telephone Operational Modes Functional Descriptor
+ * \details The Telephone Operational Modes functional descriptor describes the operational modes supported by the
+ * Communication Class interface, as defined in Section 3.6.3.1, with the SubClass code of Telephone Control. It can
+ * only occur within the class-specific portion of an Interface descriptor. The modes supported are Simple, Standalone,
+ * and Computer Centric. See Section 6.2.18, “SetOperationParms” for a definition of the various operational modes and
+ * Table 53 for the definition of the operational mode values.
+ */
+struct usb_cdc_tom_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Direct Line Management Functional Descriptor. \ref USB_DTYPE_CDC_TEL_OPMODE */
+    uint8_t     bmCapabilities;     /**< The \ref USB_CDC_TOMCAP "capabilities" that this configuration supports */    
+} __attribute__ ((packed));
+
+/** \brief Telephone Call State Reporting Capabilities Descriptor
+ * \details The Telephone Call and Line State Reporting Capabilities functional descriptor describes the abilities of a telephone
+ * device to report optional call and line states.
+ */
+struct usb_cdc_tcs_desc {
+    uint8_t     bFunctionLength;    /**< Size of this functional descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t     bDescriptorSubType; /**< Direct Line Management Functional Descriptor. \ref USB_DTYPE_CDC_TEL_CALL */
+    uint32_t    bmCapabilities;     /**< The \ref USB_CDC_TCSCAP "capabilities" that this configuration supports */    
+} __attribute__ ((packed));
+
+/** @} */
+
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif /* _USB_CDC_PSTN_H_ */    	

+ 133 - 0
inc/usb_cdcw.h

@@ -0,0 +1,133 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/** \ingroup USB_CDC
+ *  \addtogroup USB_CDC_WCM USB CDC WCM subclass
+ *  \brief USB CDC WCM subclass definitions
+ *  \details Wireless Mobile Communications  Devices subclass
+ * + Wireless Handset Control Model
+ * + Device Management Model
+ * + Mobile Direct Line Model
+ * + OBEX Model
+ * @{ */
+
+#ifndef _USB_CDC_WCM_H_
+#define _USB_CDC_WCM_H_
+
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\name Communications Class Subclass Codes
+ * @{ */
+#define USB_CDC_SUBCLASS_WHCM               0x08 /**< Wireless Handset Control Model */ 
+#define USB_CDC_SUBCLASS_DMM                0x09 /**< Device Management Model*/ 
+#define USB_CDC_SUBCLASS_MDLM               0x0A /**< Mobile Direct Line Model */ 
+#define USB_CDC_SUBCLASS_OBEX               0x0B /**< OBEX Model */ 
+ /* @} */
+
+/**\name Communications Class Protocol Codes
+ * @{ */
+#define USB_CDC_PROTO_PCCA101               0x02 /**< AT Commands defined by PCCA-101 */
+#define USB_CDC_PROTO_PCCA101O              0x03 /**< AT Commands defined by PCCA-101 & Annex O */
+#define USB_CDC_PROTO_GSM                   0x04 /**< AT Commands defined by GSM 07.07 */
+#define USB_CDC_PROTO_3G                    0x05 /**< AT Commands defined by 3GPP 27.007 */
+#define USB_CDC_PROTO_CDMA                  0x06 /**< AT Commands defined by TIA for CDMA */
+/** @} */    	
+
+/**\name CDC WCM subclass specific Functional Descriptors codes
+ * @{ */
+#define USB_DTYPE_CDC_WHCM                  0x11 /**< Wireless Handset Control Model Functional Descriptor \ref usb_cdc_whcm_desc*/
+#define USB_DTYPE_CDC_MDLM                  0x12 /**< Mobile Direct Line Model Functional Descriptor \ref usb_cdc_mdlm_desc */
+#define USB_DTYPE_CDC_MDLM_DETAIL           0x13 /**< MDLM Detail Functional Descriptor \ref usb_cdc_mdlm_detail_desc*/
+#define USB_DTYPE_CDC_DMM                   0x14 /**< Device Management Model Functional Descriptor \ref usb_cdc_dmm_desc */
+#define USB_DTYPE_CDC_OBEX                  0x15 /**< OBEX Functional Descriptor use \ref usb_cdc_header_desc*/
+#define USB_DTYPE_CDC_CMDSET                0x16 /**< Command Set Functional Descriptor */
+#define USB_DTYPE_CDC_CMDSET_DETAIL         0x17 /**< Command Set Detail Functional Descriptor */
+#define USB_DTYPE_CDC_TEL_CONRTOL           0x18 /**< Telephone Control Model Functional Descriptor */
+#define USB_DTYPE_CDC_OBEX_SERVICE          0x19 /**< OBEX Service Identifier Functional Descriptor \ref usb_cdc_obex_serv_desc*/
+
+/** @} */    	
+
+/**\name CDC WCM subclass specific requests
+ * @{ */
+
+/** @} */
+
+/**\brief Wireless Handset Control Model Functional Descriptor */
+struct usb_cdc_whcm_desc {
+    uint8_t    bFunctionLength;				/**< Size of this functional descriptor, in bytes. */
+    uint8_t    bDescriptorType;				/**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t    bDescriptorSubType;			/**< Wireless Handset Control Model Functional Descriptor \ref USB_DTYPE_CDC_WHCM */
+    uint16_t   bcdVersion;					/**< Version number for this subclass specification. \see \ref VERSION_BCD macro */
+} __attribute__ ((packed));
+
+/**\brief Mobile Direct Line Model Functional Descriptor
+ * \details This descriptor is mandatory. It conveys the GUID that uniquely identifies the kind of MDLM interface that is being provided.
+ */
+struct usb_cdc_mdlm_desc {
+    uint8_t    bFunctionLength;				/**< Size of this functional descriptor, in bytes. */
+    uint8_t    bDescriptorType;				/**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t    bDescriptorSubType;			/**< Mobile Direct Line Model Functional Descriptor \ref USB_DTYPE_CDC_MDLM */
+    uint16_t   bcdVersion;					/**< Version number for this subclass specification. \see \ref VERSION_BCD macro */
+    uint8_t    bGUID[16];					/**< Uniquely identifies the detailed transport protocol provided by this MDLM interface. */
+} __attribute__ ((packed));
+
+/**\brief Mobile Direct Line Model Detail Functional Descriptor
+ * \details This descriptor is optional, and may be repeated as necessary. It conveys any additional information required by
+ * the MDLM transport specification identified by the MDLM Functional Descriptor.
+ */
+struct usb_cdc_mdlm_detail_desc {
+    uint8_t    bFunctionLength;				/**< Size of this functional descriptor, in bytes. */
+    uint8_t    bDescriptorType;				/**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t    bDescriptorSubType;			/**< Mobile Direct Line Model Details Functional Descriptor \ref USB_DTYPE_CDC_MDLM_DETAIL */
+    uint8_t    bGuidDescriptorType; 		/**< Discriminator, interpreted according to the semantic model specified by the GUID in the
+	  									     * MDLM Functional Descriptor */
+    uint8_t    bDetailData[0];				/**< Information associated with this GUID and discriminator, according to the semantic model
+	   									 	 * specified by the GUID in the MDLM Functional Descriptor */
+} __attribute__ ((packed));
+
+/**\brief Device Management Functional Descriptor */
+struct usb_cdc_dmm_desc {
+    uint8_t    bFunctionLength;				/**< Size of this functional descriptor, in bytes. */
+    uint8_t    bDescriptorType;				/**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t    bDescriptorSubType;			/**< Wireless Handset Control Model Functional Descriptor \ref USB_DTYPE_CDC_DMM */
+    uint16_t   bcdVersion;					/**< Version number for this subclass specification. \see \ref VERSION_BCD macro */
+	uint16_t   wMaxCommand;					/**< The buffer size allocated in the device for data sent from the host using SEND_ENCAPSULATED_CMD. */
+} __attribute__ ((packed));
+
+/**\brief OBEX Service Identification Functional Descriptor
+ * \details This optional functional descriptor indicates the mode supported by this OBEX function. This corresponds to an
+ * OBEX role (client or server), a particular OBEX service, and an OBEX service version.
+ */
+struct usb_cdc_obex_serv_desc {
+    uint8_t    bFunctionLength;				/**< Size of this functional descriptor, in bytes. */
+    uint8_t    bDescriptorType;				/**< CS_INTERFACE descriptor type. \see \ref USB_DTYPE_CS_INTERFACE */
+    uint8_t    bDescriptorSubType;			/**< OBEX Service Identifier Functional Descriptor \ref USB_DTYPE_CDC_OBEX_SERVICE */
+	uint8_t    bmOBEXRole;					/**< Represents the OBEX role to be played by the function */
+	uint8_t    bOBEXServiceUUID[16];		/**< A 16 byte UUID value used to indicate the particular OBEX service associated with this function. */
+	uint16_t   wOBEXServiceVersion;			/**< A 16 bit value indicating the version of the OBEX service associated with this function. */
+
+} __attribute__ ((packed));
+
+/** @} */
+
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif /* _USB_CDC_WCM_H_ */    	

+ 124 - 0
inc/usb_dfu.h

@@ -0,0 +1,124 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_DFU_H_
+#define _USB_DFU_H_
+
+#if defined(__cplusplus)
+    extern "C" {
+#endif
+
+/** \addtogroup USB_MODULE_DFU USB DFU class
+ * \brief This module contains USB Device Firmware Upgrade class definitions.
+ * \details This module based on
+ * + [USB Device Firmware Upgrade Specification, Revision 1.1](http://www.usb.org/developers/docs/devclass_docs/DFU_1.1.pdf)
+ * @{ */
+
+/**\name USB DFU class subclass and protocol definitions
+ * @{ */
+#define USB_CLASS_DFU                   0xFE    /**< USB DFU class is an application-specified class */
+#define USB_DFU_SUBCLASS_DFU            0x01    /**< USB DFU subclass code */
+#define USB_DFU_PROTO_RUNTIME           0x01    /**< USB DFU runtime-mode protocol */
+#define USB_DFU_PROTO_DFU               0x02    /**< USB DFU DFU-mode protocol */
+/** @{ */
+
+/**\name USB DFU descriptor types */
+#define USB_DTYPE_DFU_FUNCTIONAL        0x21    /**< USB DFU functional descriptor type */
+
+/**\name USB DFU class-specific requests
+ * @{ */
+#define USB_DFU_DETACH                  0x00    /**< Initiates a detach-attach sequence on the bus when it sees this request. */
+#define USB_DFU_DNLOAD                  0x01    /**< Initiates firmware image downloading */
+#define USB_DFU_UPLOAD                  0x02    /**< This request is employed by the host to solicit firmware from the device.*/
+#define USB_DFU_GETSTATUS               0x03    /**< The host employs this request to facilitate synchronization with the device. \see usb_dfu_status */
+#define USB_DFU_CLRSTATAUS              0x04    /**< This request resets DFU machine state to DFU_IDLE*/
+#define USB_DFU_GETSATAE                0x05    /**< This request solicits a report about the state of the device. */
+#define USB_DFU_ABORT                   0x06    /**< This request enables the host to exit from certain states and return to the DFU_IDLE state*/
+/** @} */
+
+/**\anchor USB_DFU_CAPAB
+ * \name USB DFU capabilities
+ * @{ */
+#define USB_DFU_ATTR_WILL_DETACH        0x08    /**< Device will perform a bus detach-attach sequence when it receives a DFU_DETACH request. */
+#define USB_DFU_ATTR_MANIF_TOL          0x04    /**< Device is able to communicate via USB after Manifestation phase. */
+#define USB_DFU_ATTR_CAN_UPLOAD         0x02    /**< Upload capable. */
+#define USB_DFU_ATTR_CAN_DNLOAD         0x01    /**< Download capable. */
+/** @} */
+
+/**\name USB DFU status codes
+ * @{ */
+#define USB_DFU_STATUS_OK               0x00 /**< No error condition is present. */
+#define USB_DFU_STATUS_ERR_TARGET       0x01 /**< File is not targeted for use by this device. */
+#define USB_DFU_STATUS_ERR_FILE         0x02 /**< File is for this device but fails some vendor specific verification test. */
+#define USB_DFU_STATIS_ERR_WRITE        0x03 /**< Device is unable to write memory. */
+#define USB_DFU_STATUS_ERR_ERASE        0x04 /**< Memory erase function failed. */
+#define USB_DFU_STATUS_ERR_CHECK_ERASED 0x05 /**< Memory erase check failed. */
+#define USB_DFU_STATUS_ERR_PROG         0x06 /**< Program memory function failed. */
+#define USB_DFU_STATUS_ERR_VERIFY       0x07 /**< Programmed memory failed verification. */
+#define USB_DFU_STATUS_ERR_ADDRESS      0x08 /**< Cannot program memory due to received address that is out of range. */
+#define USB_DFU_STATUS_ERR_NOTDONE      0x09 /**< Received DFU_DNLOAD with wLength = 0, but device does not think it has all of the data yet. */
+#define USB_DFU_STATUS_ERR_FIRMWARE     0x0A /**< Device's firmware is corrupt.  It cannot return to run-time (non-DFU) operations. */
+#define USB_DFU_STATUS_ERR_VENDOR       0x0B /**< iString indicates a vendor-specific error. */
+#define USB_DFU_STATUS_ERR_USBR         0x0C /**< Device detected unexpected USB reset signaling. */
+#define USB_DFU_STATUS_ERR_POR          0x0D /**< Device detected unexpected power on reset. */
+#define USB_DFU_STATUS_ERR_UNKNOWN      0x0E /**< Something went wrong, but the device does not know what it was. */
+#define USB_DFU_STATUS_ERR_STALLEDPKT   0x0F /**< Device stalled an unexpected request. */
+/** @} */
+
+/**\name USB DFU state codes
+ * @{ */
+#define USB_DFU_STATE_APP_IDLE          0x00 /**< Device is running its normal application. */
+#define USB_DFU_STATE_APP_DETACH        0x01 /**< Device is running its normal application, has received the DFU_DETACH request, and is waiting for a USB reset. */
+#define USB_DFU_STATE_DFU_IDLE          0x02 /**< Device is operating in the DFU mode and is waiting for requests. */
+#define USB_DFU_STATE_DFU_DNLOADSYNC    0x03 /**< Device has received a block and is waiting for the host to solicit the status via DFU_GETSTATUS. */
+#define USB_DFU_STATE_DFU_DNBUSY        0x04 /**< Device is programming a control-write block into its nonvolatile memories. */
+#define USB_DFU_STATE_DFU_DNLOADIDLE    0x05 /**< Device is processing a download operation.  Expecting DFU_DNLOAD requests. */
+#define USB_DFU_STATE_DFU_MANIFESTSYNC  0x06 /**< Device has received the final block of firmware from the host
+                                              * and is waiting for receipt of DFU_GETSTATUS to begin the Manifestation
+                                              * phase; or device has completed the Manifestation phase and is waiting
+                                              * for receipt of DFU_GETSTATUS.  (Devices that can enter this state
+                                              * after the Manifestation phase set bmAttributes bit bitManifestationTolerant to 1.) */
+#define USB_DFU_STATE_DFU_MANIFEST      0x07 /**< Device is in the Manifestation phase.  (Not all devices will be able to respond to DFU_GETSTATUS when in this state.) */
+#define USB_DFU_STATE_DFU_MANIFESTWR    0x08 /**< Device has programmed its memories and is waiting for a USB reset or a
+                                              * power on reset.  (Devices that must enter this state clear bitManifestationTolerant to 0.) */
+#define USB_DFU_STATE_DFU_UPLOADIDLE    0x09 /**< The device is processing an upload operation.  Expecting DFU_UPLOAD requests. */
+#define USB_DFU_STATE_DFU_ERROR         0x0A /**< An error has occurred. Awaiting the DFU_CLRSTATUS request. */
+/** @} */
+
+/** \brief USB DFU functional descriptor */
+struct usb_dfu_func_desc {
+    uint8_t     bLength;            /**< Descriptor length in bytes. */
+    uint8_t     bDescriptorType;    /**< Descriptor type, set it to \ref USB_DTYPE_DFU_FUNCTIONAL */
+    uint8_t     bmAttributes;       /**< Bitmap field of the \ref USB_DFU_CAPAB "USB DFU capabilities"*/
+    uint16_t    wDetachTimeout;     /**< USB DFU detach timeout in ms */
+    uint16_t    wTransferSize;      /**< USB DFU maximum transfer block size in bytes */
+    uint16_t    bcdDFUVersion;      /**< USB DFU version \ref VERSION_BCD utility macro */
+}__attribute__((packed));
+
+/** \brief Payload packet to response in DFU_GETSTATUS request */
+struct usb_dfu_status {
+    uint8_t     bStatus;            /**< An indication of the status resulting from the execution of the most recent request.*/
+    uint8_t     bPollTimeout;
+    uint16_t    wPollTimeout;       /**< Minimum time, (ms), that the host should wait before sending a subsequent \ref USB_DFU_GETSTATUS "DFU_GETSTATUS" request. */
+    uint8_t     bState;             /**< An indication of the state that the device is going to enter immediately following transmission of this response. */
+    uint8_t     iString;            /**< Index of the status \ref usb_string_descriptor "string descriptor". */
+};
+
+/** @} */
+
+#if defined(__cplusplus)
+    }
+#endif
+#endif /* _USB_DFU_H_ */

+ 212 - 0
inc/usb_hid.h

@@ -0,0 +1,212 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_HID_H_
+#define _USB_HID_H_
+#ifdef __cplusplus
+    extern "C" {
+#endif
+
+
+/**\addtogroup USB_HID USB HID class
+ * \brief This module contains USB Human Interface Devices class definitions
+ * \details This module based on
+ * + [Device Class Definition for Human Interface Devices (HID) Version 1.11](http://www.usb.org/developers/hidpage/HID1_11.pdf)
+ * + [LUFA - the Lightweight USB Framework for AVRs.](https://github.com/abcminiuser/lufa)
+ * @{ */
+
+/**\name USB HID class code */
+#define USB_CLASS_HID               0x03 /**< Interface belongs to the Human Interface device class */
+
+/**\name USB HID subclass codes
+ * @{ */
+#define USB_HID_SUBCLASS_NONBOOT    0x00
+#define USB_HID_SUBCLASS_BOOT       0x01
+/** @} */
+
+/**\name USB HID protocol codes
+ * @{ */
+#define USB_HID_PROTO_NONBOOT       0x00
+#define USB_HID_PROTO_KEYBOARD      0x01
+#define USB_HID_PROTO_MOUSE         0x02
+/** @} */
+
+#define USB_HID_REPORT_IN           0 /**< \brief Indicates that the item is an IN report type. */
+#define USB_HID_REPORT_OUT          1 /**< \brief Indicates that the item is an OUT report type. */
+#define USB_HID_REPORT_FEATURE      2 /**< \brief Indicates that the item is a FEATURE report type. */
+
+
+/**\name USB HID class-specified requests
+ * @{ */
+#define USB_HID_GETREPORT  			0x01 /**< Request to get the current HID report from the device. */
+#define USB_HID_GETIDLE    			0x02 /**< Request to get the current device idle count. */
+#define USB_HID_GETPROTOCOL			0x03 /**< Request to get the current HID report protocol mode. */
+#define USB_HID_SETREPORT  			0x09 /**< Request to set the current HID report to the device. */
+#define USB_HID_SETIDLE    			0x0A /**< Request to set the device's idle count. */
+#define USB_HID_SETPROTOCOL			0x0B /**< Request to set the current HID report protocol mode. */
+/** @} */
+
+/**\name USB HID class-specified descriptor types
+ * @{ */
+#define	USB_DTYPE_HID           	0x21 /**< Descriptor header type value, to indicate a HID class HID descriptor. */
+#define	USB_DTYPE_HID_REPORT     	0x22 /**< Descriptor header type value, to indicate a HID class HID report descriptor. */
+/** @} */
+
+/**\name USB HID country codes
+ * @{ */
+#define USB_HID_COUNTRY_NONE 		0 	/**< Not supported */
+#define USB_HID_COUNTRY_AR   		1 	/**< Arabic */
+#define USB_HID_COUNTRY_BE   		2 	/**< Belgian */
+#define USB_HID_COUNTRY_CA_BI		3 	/**< Canadian-Bilingual */
+#define USB_HID_COUNTRY_CA_FR		4 	/**< Canadian-French */
+#define USB_HID_COUNTRY_CZ   		5 	/**< Czech Republic */
+#define USB_HID_COUNTRY_DK   		6 	/**< Danish */
+#define USB_HID_COUNTRY_FI   		7 	/**< Finnish */
+#define USB_HID_COUNTRY_FR   		8 	/**< French */
+#define USB_HID_COUNTRY_DE   		9 	/**< German */
+#define USB_HID_COUNTRY_GR   		10	/**< Greek */
+#define USB_HID_COUNTRY_HEB  		11	/**< Hebrew */
+#define USB_HID_COUNTRY_HU   		12	/**< Hungary */
+#define USB_HID_COUNTRY_ISO  		13	/**< International (ISO) */
+#define USB_HID_COUNTRY_IT   		14	/**< Italian */
+#define USB_HID_COUNTRY_JP   		15	/**< Japan (Katakana) */
+#define USB_HID_COUNTRY_KR   		16	/**< Korean */
+#define USB_HID_COUNTRY_LAT  		17	/**< Latin American */
+#define USB_HID_COUNTRY_NL   		18	/**< Netherlands/Dutch */
+#define USB_HID_COUNTRY_NO   		19	/**< Norwegian */
+#define USB_HID_COUNTRY_PER  		20	/**< Persian (Farsi) */
+#define USB_HID_COUNTRY_PL   		21	/**< Poland */
+#define USB_HID_COUNTRY_PO   		22	/**< Portuguese */
+#define USB_HID_COUNTRY_RU   		23	/**< Russia */
+#define USB_HID_COUNTRY_SK   		24	/**< Slovakia */
+#define USB_HID_COUNTRY_ES   		25	/**< Spanish */
+#define USB_HID_COUNTRY_SE   		26	/**< Swedish */
+#define USB_HID_COUNTRY_CH_FR		26	/**< Swiss-French */
+#define USB_HID_COUNTRY_CH_DE		27	/**< Swiss-German */
+#define USB_HID_COUNTRY_CH   		29	/**< Switzerland */
+#define USB_HID_COUNTRY_TW   		30	/**< Taiwan */
+#define USB_HID_COUNTRY_TR_Q 		31	/**< Turkish-Q */
+#define USB_HID_COUNTRY_UK   		32	/**< UK */
+#define USB_HID_COUNTRY_US   		33	/**< US */
+#define USB_HID_COUNTRY_YU   		34	/**< Yugoslavia */
+#define USB_HID_COUNTRY_TR_F 		35	/**< Turkish-F */
+/** @} */
+
+/** \brief USB HID functional descriptor */
+struct usb_hid_descriptor {
+    uint8_t     bLength;            /**< Size of the descriptor, in bytes. */
+    uint8_t     bDescriptorType;    /**< Type of the descriptor, set to \ref USB_DTYPE_HID */
+	uint16_t    bcdHID;             /**< BCD encoded version that the HID descriptor and device complies to. \ref VERSION_BCD() */
+    uint8_t     bCountryCode;       /**< Country code of the localized device, or zero if universal. */
+	uint8_t     bNumDescriptors;    /**< Total number of HID report descriptors for the interface. */
+	uint8_t     bDescriptorType0;   /**< 1'st HID report descriptor type, set to \ref USB_DTYPE_HID_REPORT */
+	uint16_t    wDescriptorLength0; /**< 1'sr HID report descriptor length in bytes. */
+} __attribute__((packed));
+
+/**\brief USB HID report descriptor */
+struct usb_hid_report_descriptor {
+	uint8_t     bDescriptorType;   /**< Type of HID report, set to \ref USB_DTYPE_HID_REPORT */
+    uint16_t    wDescriptorLength; /**< Length of the associated HID report descriptor, in bytes. */
+} __attribute__((packed));
+
+
+	/* Private Interface - For use in library only: */
+	#if !defined(__DOXYGEN__)
+		/* Macros: */
+            #define CONCAT(x, y)            x ## y
+            #define CONCAT_EXPANDED(x, y)   CONCAT(x, y)
+
+			#define HID_RI_DATA_SIZE_MASK                   0x03
+			#define HID_RI_TYPE_MASK                        0x0C
+			#define HID_RI_TAG_MASK                         0xF0
+
+			#define HID_RI_TYPE_MAIN                        0x00
+			#define HID_RI_TYPE_GLOBAL                      0x04
+			#define HID_RI_TYPE_LOCAL                       0x08
+
+			#define HID_RI_DATA_BITS_0                      0x00
+			#define HID_RI_DATA_BITS_8                      0x01
+			#define HID_RI_DATA_BITS_16                     0x02
+			#define HID_RI_DATA_BITS_32                     0x03
+			#define HID_RI_DATA_BITS(DataBits)              CONCAT_EXPANDED(HID_RI_DATA_BITS_, DataBits)
+
+			#define _HID_RI_ENCODE_0(Data)
+			#define _HID_RI_ENCODE_8(Data)                  , (Data & 0xFF)
+			#define _HID_RI_ENCODE_16(Data)                 _HID_RI_ENCODE_8(Data)  _HID_RI_ENCODE_8(Data >> 8)
+			#define _HID_RI_ENCODE_32(Data)                 _HID_RI_ENCODE_16(Data) _HID_RI_ENCODE_16(Data >> 16)
+			#define _HID_RI_ENCODE(DataBits, ...)           CONCAT_EXPANDED(_HID_RI_ENCODE_, DataBits(__VA_ARGS__))
+
+			#define _HID_RI_ENTRY(Type, Tag, DataBits, ...) (Type | Tag | HID_RI_DATA_BITS(DataBits)) _HID_RI_ENCODE(DataBits, (__VA_ARGS__))
+	#endif
+
+	/* Public Interface - May be used in end-application: */
+		/* Macros: */
+		/** \name HID Input, Output and Feature Report Descriptor Item Flags */
+		//@{
+			#define HID_IOF_CONSTANT                        (1 << 0)
+			#define HID_IOF_DATA                            (0 << 0)
+			#define HID_IOF_VARIABLE                        (1 << 1)
+			#define HID_IOF_ARRAY                           (0 << 1)
+			#define HID_IOF_RELATIVE                        (1 << 2)
+			#define HID_IOF_ABSOLUTE                        (0 << 2)
+			#define HID_IOF_WRAP                            (1 << 3)
+			#define HID_IOF_NO_WRAP                         (0 << 3)
+			#define HID_IOF_NON_LINEAR                      (1 << 4)
+			#define HID_IOF_LINEAR                          (0 << 4)
+			#define HID_IOF_NO_PREFERRED_STATE              (1 << 5)
+			#define HID_IOF_PREFERRED_STATE                 (0 << 5)
+			#define HID_IOF_NULLSTATE                       (1 << 6)
+			#define HID_IOF_NO_NULL_POSITION                (0 << 6)
+			#define HID_IOF_VOLATILE                        (1 << 7)
+			#define HID_IOF_NON_VOLATILE                    (0 << 7)
+			#define HID_IOF_BUFFERED_BYTES                  (1 << 8)
+			#define HID_IOF_BITFIELD                        (0 << 8)
+		//@}
+
+		/** \name HID Report Descriptor Item Macros */
+		//@{
+			#define HID_RI_INPUT(DataBits, ...)             _HID_RI_ENTRY(HID_RI_TYPE_MAIN  , 0x80, DataBits, __VA_ARGS__)
+			#define HID_RI_OUTPUT(DataBits, ...)            _HID_RI_ENTRY(HID_RI_TYPE_MAIN  , 0x90, DataBits, __VA_ARGS__)
+			#define HID_RI_COLLECTION(DataBits, ...)        _HID_RI_ENTRY(HID_RI_TYPE_MAIN  , 0xA0, DataBits, __VA_ARGS__)
+			#define HID_RI_FEATURE(DataBits, ...)           _HID_RI_ENTRY(HID_RI_TYPE_MAIN  , 0xB0, DataBits, __VA_ARGS__)
+			#define HID_RI_END_COLLECTION(DataBits, ...)    _HID_RI_ENTRY(HID_RI_TYPE_MAIN  , 0xC0, DataBits, __VA_ARGS__)
+			#define HID_RI_USAGE_PAGE(DataBits, ...)        _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x00, DataBits, __VA_ARGS__)
+			#define HID_RI_LOGICAL_MINIMUM(DataBits, ...)   _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x10, DataBits, __VA_ARGS__)
+			#define HID_RI_LOGICAL_MAXIMUM(DataBits, ...)   _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x20, DataBits, __VA_ARGS__)
+			#define HID_RI_PHYSICAL_MINIMUM(DataBits, ...)  _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x30, DataBits, __VA_ARGS__)
+			#define HID_RI_PHYSICAL_MAXIMUM(DataBits, ...)  _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x40, DataBits, __VA_ARGS__)
+			#define HID_RI_UNIT_EXPONENT(DataBits, ...)     _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x50, DataBits, __VA_ARGS__)
+			#define HID_RI_UNIT(DataBits, ...)              _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x60, DataBits, __VA_ARGS__)
+			#define HID_RI_REPORT_SIZE(DataBits, ...)       _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x70, DataBits, __VA_ARGS__)
+			#define HID_RI_REPORT_ID(DataBits, ...)         _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x80, DataBits, __VA_ARGS__)
+			#define HID_RI_REPORT_COUNT(DataBits, ...)      _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0x90, DataBits, __VA_ARGS__)
+			#define HID_RI_PUSH(DataBits, ...)              _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0xA0, DataBits, __VA_ARGS__)
+			#define HID_RI_POP(DataBits, ...)               _HID_RI_ENTRY(HID_RI_TYPE_GLOBAL, 0xB0, DataBits, __VA_ARGS__)
+			#define HID_RI_USAGE(DataBits, ...)             _HID_RI_ENTRY(HID_RI_TYPE_LOCAL , 0x00, DataBits, __VA_ARGS__)
+			#define HID_RI_USAGE_MINIMUM(DataBits, ...)     _HID_RI_ENTRY(HID_RI_TYPE_LOCAL , 0x10, DataBits, __VA_ARGS__)
+			#define HID_RI_USAGE_MAXIMUM(DataBits, ...)     _HID_RI_ENTRY(HID_RI_TYPE_LOCAL , 0x20, DataBits, __VA_ARGS__)
+		//@}
+
+
+
+
+/** @}  */
+
+#ifdef __cplusplus
+    }
+#endif
+
+#endif
+

+ 399 - 0
inc/usb_std.h

@@ -0,0 +1,399 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USB_STD_H_
+#define _USB_STD_H_
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+/**\addtogroup USB_STD USB Standard
+ * \brief This module contains generic USB device framework definitions
+ * \details This module based on
+ * + Chapter 9 of the [Universal Serial Bus Specification Revision 2.0](http://www.usb.org/developers/docs/usb20_docs/usb_20_080416.zip)
+ * + [LUFA - the Lightweight USB Framework for AVRs.](https://github.com/abcminiuser/lufa)
+ * @{
+ *\name Utility functional macros
+ * @{ */
+/** Macro to encode major/minor/version number into BCD code
+ * \param maj Major version
+ * \param min Minor version
+ * \param rev Revision
+ */
+#define VERSION_BCD(maj, min, rev)  (((maj & 0xFF) << 8) | ((min & 0x0F) << 4) | (rev & 0x0F))
+
+/** Macro to create \ref usb_string_descriptor from array of characters */
+#define USB_STRING_DESC(...)        {.bLength = 2 + sizeof((uint16_t[]){__VA_ARGS__}), .bDescriptorType = USB_DTYPE_STRING, .wString = {__VA_ARGS__}}
+
+/**\brief Macro to */
+#define USB_CFG_POWER_MA(mA)        ((mA) >> 1)
+/** @} */
+
+/**\name USB device configuration definitions
+ * @{ */
+#define USB_CFG_ATTR_RESERVED       0x80
+#define USB_CFG_ATTR_SELFPOWERED    0x40
+/** @} */
+
+/** \anchor USB_ENDPOINT_DEF
+ *  \name USB endpoint attributes definitions
+ * @{ */
+#define USB_EPTYPE_CONTROL          0x00
+#define USB_EPTYPE_ISOCHRONUS       0x01
+#define USB_EPTYPE_BULK             0x02
+#define USB_EPTYPE_INTERRUPT        0x03
+#define USB_EPATTR_NO_SYNC          0x00
+#define USB_EPATTR_ASYNC            0x04
+#define USB_EPATTR_ADAPTIVE         0x08
+#define USB_EPATTR_SYNC             0x0C
+#define USB_EPUSAGE_DATA            0x00
+#define USB_EPUSAGE_FEEDBACK        0x10
+#define USB_EPUSAGE_IMP_FEEDBACK    0x20
+/** @} */
+
+/**\name Special string descriptor indexes
+ * @{ */
+#define NO_DESCRIPTOR               0x00    /**< \brief Indicates that a given string descriptor doesn't exists in the device */
+#define INTSERIALNO_DESCRIPTOR      0xFE    /**< \brief Indicates that a given string descriptor is a internal serial number provided by hardware driver */
+/** @} */
+
+/**\name USB class definitions
+ * @{ */
+#define USB_CLASS_PER_INTERFACE     0x00 /**< Class defined on interface level */
+#define USB_SUBCLASS_NONE           0x00
+#define USB_PROTO_NONE              0x00
+#define USB_CLASS_AUDIO             0x01 /**< Interface belongs to the Audio device class. */
+#define USB_CLASS_PHYSICAL          0x05 /**< Interface belongs to the Physical device class. */
+#define USB_CLASS_STILL_IMAGE       0x06 /**< Interface belongs to the Still Imaging device class. */
+#define USB_CLASS_PRINTER           0x07 /**< Interface belongs to the Printer device class. */
+#define USB_CLASS_MASS_STORAGE      0x08 /**< Interface belongs to the Mass Storage device class. */
+#define USB_CLASS_HUB               0x09 /**< Device belongs to the HUB device class. */
+#define USB_CLASS_CSCID             0x0B /**< Interface belongs to the Smart Card device class. */
+#define USB_CLASS_CONTENT_SEC       0x0D /**< Interface belongs to the Content Security device class. */
+#define USB_CLASS_VIDEO             0x0E /**< Interface belongs to the Video device class. */
+#define USB_CLASS_HEALTHCARE        0x0F /**< Interface belongs to the Personal Healthcare device class. */
+#define USB_CLASS_AV                0x10 /**< Interface belongs to the Audio/Video device class. */
+#define USB_CLASS_BILLBOARD         0x11 /**< Device belongs to the Billboard device class. */
+#define USB_CLASS_CBRIDGE           0x12 /**< Interface belongs to the USB Type-C Bridge device class. */
+#define USB_CLASS_DIAGNOSTIC        0xDC /**< Device/Interface belongs to the Diagnostic device class. */
+#define USB_CLASS_WIRELESS          0xE0 /**< Interface belongs to the Wireless controller class. */
+#define USB_CLASS_MISC              0xEF /**< Device/Interface belongs to the Miscellanious device class. */
+#define USB_CLASS_APP_SPEC          0xFE /**< Interface belongs to the Application Specific class. */
+#define USB_CLASS_VENDOR            0xFF /**< Device belongs to a vendor specific class. */
+#define USB_SUBCLASS_VENDOR         0xFF /**< Subclass belongs to a vendor specific subclass. */
+#define USB_PROTO_VENDOR            0xFF /**< Protocol belongs to a vendor specific protocol. */
+/** @} */
+
+/**\name USB Standard descriptor types
+ * @{ */
+#define USB_DTYPE_DEVICE            0x01 /**< Indicates that the descriptor is a \ref usb_device_descriptor*/
+#define USB_DTYPE_CONFIGURATION     0x02 /**< Indicates that the descriptor is a \ref usb_config_descriptor */
+#define USB_DTYPE_STRING            0x03 /**< Indicates that the descriptor is a \ref usb_string_descriptor */
+#define USB_DTYPE_INTERFACE         0x04 /**< Indicates that the descriptor is a \ref usb_interface_descriptor */
+#define USB_DTYPE_ENDPOINT          0x05 /**< Indicates that the descriptor is an endpoint descriptor. */
+#define USB_DTYPE_QUALIFIER         0x06 /**< Indicates that the descriptor is a \ref usb_qualifier_descriptor */
+#define USB_DTYPE_OTHER             0x07 /**< Indicates that the descriptor is of other type. */
+#define USB_DTYPE_INTERFACEPOWER    0x08 /**< Indicates that the descriptor is an interface power descriptor. */
+#define USB_DTYPE_OTG               0x09 /**< Indicates that the descroptor is an OTG descriptor */
+#define USB_DTYPE_DEBUG             0x0A /**< Indicates that the descriptor is a Debug descriptor */
+#define USB_DTYPE_INTERFASEASSOC    0x0B /**< Indicates that the descriptor is an interface association descriptor. */
+#define USB_DTYPE_CS_INTERFACE      0x24 /**< Indicates that the descriptor is a class specific interface descriptor. */
+#define USB_DTYPE_CS_ENDPOINT       0x25 /**< Indicates that the descriptor is a class specific endpoint descriptor. */
+/** @} */
+
+/**\name USB Standard requests
+ * @{ */
+#define USB_STD_GET_STATUS          0x00 /**< This request returns status for the specified recipient */
+#define USB_STD_CLEAR_FEATURE       0x01 /**< This request is used to clear or disable a specific feature */
+#define USB_STD_SET_FEATURE         0x03 /**< This request is used to set or enable a specific feature */
+#define USB_STD_SET_ADDRESS         0x05 /**< This request sets the device address for all future device accesses */
+#define USB_STD_GET_DESCRIPTOR      0x06 /**< This request returns the specified descriptor if the descriptor exists */
+#define USB_STD_SET_DESCRIPTOR      0x07 /**< This request is optional and may be used to update existing descriptors or new descriptors may be added */
+#define USB_STD_GET_CONFIG          0x08 /**< This request returns the current device configuration value */
+#define USB_STD_SET_CONFIG          0x09 /**< This request sets the device configuration */
+#define USB_STD_GET_INTERFACE       0x0A /**< This request returns the selected alternate setting for the specified interface */
+#define USB_STD_SET_INTERFACE       0x0B /**< This request allows the host to select an alternate setting for the specified interface */
+#define USB_STD_SYNCH_FRAME         0x0C /**< This request is used to set and then report an endpoint's synchronization frame */
+/** @} */
+
+/** \brief USB standard LANGID codes */
+enum usb_std_langid_codes {
+    USB_LANGID_AFR      = 0x0436,   /**< Afrikaans */
+    USB_LANGID_SQI      = 0x041c,   /**< Albanian */
+    USB_LANGID_ARA_SA   = 0x0401,   /**< Arabic (Saudi Arabia) */
+    USB_LANGID_ARA_IQ   = 0x0801,   /**< Arabic (Iraq) */
+    USB_LANGID_ARA_EG   = 0x0c01,   /**< Arabic (Egypt) */
+    USB_LANGID_ARA_LY   = 0x1001,   /**< Arabic (Libya) */
+    USB_LANGID_ARA_DZ   = 0x1401,   /**< Arabic (Algeria) */
+    USB_LANGID_ARA_MA   = 0x1801,   /**< Arabic (Morocco) */
+    USB_LANGID_ARA_TN   = 0x1c01,   /**< Arabic (Tunisia) */
+    USB_LANGID_ARA_OM   = 0x2001,   /**< Arabic (Oman) */
+    USB_LANGID_ARA_YE   = 0x2401,   /**< Arabic (Yemen) */
+    USB_LANGID_ARA_SY   = 0x2801,   /**< Arabic (Syria) */
+    USB_LANGID_ARA_JO   = 0x2c01,   /**< Arabic (Jordan) */
+    USB_LANGID_ARA_LB   = 0x3001,   /**< Arabic (Lebanon) */
+    USB_LANGID_ARA_KW   = 0x3401,   /**< Arabic (Kuwait) */
+    USB_LANGID_ARA_AE   = 0x3801,   /**< Arabic (U.A.E.) */
+    USB_LANGID_ARA_BH   = 0x3c01,   /**< Arabic (Bahrain) */
+    USB_LANGID_ARA_QA   = 0x4001,   /**< Arabic (Qatar) */
+    USB_LANGID_HYE      = 0x042b,   /**< Armenian */
+    USB_LANGID_ASM      = 0x044d,   /**< Assamese */
+    USB_LANGID_AZE_LAT  = 0x042c,   /**< Azeri (Latin) */
+    USB_LANGID_AZE_CYR  = 0x082c,   /**< Azeri (Cyrillic) */
+    USB_LANGID_EUS      = 0x042d,   /**< Basque */
+    USB_LANGID_BEL      = 0x0423,   /**< Belarussian */
+    USB_LANGID_BEN      = 0x0445,   /**< Bengali */
+    USB_LANGID_BUL      = 0x0402,   /**< Bulgarian */
+    USB_LANGID_MYA      = 0x0455,   /**< Burmese */
+    USB_LANGID_CAT      = 0x0403,   /**< Catalan */
+    USB_LANGID_ZHO_TW   = 0x0404,   /**< Chinese (Taiwan) */
+    USB_LANGID_ZHO_CN   = 0x0804,   /**< Chinese (PRC) */
+    USB_LANGID_ZHO_HK   = 0x0c04,   /**< Chinese (Hong Kong SAR, PRC) */
+    USB_LANGID_ZHO_SG   = 0x1004,   /**< Chinese (Singapore) */
+    USB_LANGID_ZHO_MO   = 0x1404,   /**< Chinese (Macau SAR) */
+    USB_LANGID_HRV      = 0x041a,   /**< Croatian */
+    USB_LANGID_CZE      = 0x0405,   /**< Czech */
+    USB_LANGID_DAN      = 0x0406,   /**< Danish */
+    USB_LANGID_NLD_NL   = 0x0413,   /**< Dutch (Netherlands) */
+    USB_LANGID_NLD_BE   = 0x0813,   /**< Dutch (Belgium) */
+    USB_LANGID_ENG_US   = 0x0409,   /**< English (United States) */
+    USB_LANGID_ENG_UK   = 0x0809,   /**< English (United Kingdom) */
+    USB_LANGID_ENG_AU   = 0x0c09,   /**< English (Australian) */
+    USB_LANGID_ENG_CA   = 0x1009,   /**< English (Canadian) */
+    USB_LANGID_ENG_NZ   = 0x1409,   /**< English (New Zealand) */
+    USB_LANGID_ENG_IE   = 0x1809,   /**< English (Ireland) */
+    USB_LANGID_ENG_ZA   = 0x1c09,   /**< English (South Africa) */
+    USB_LANGID_ENG_JM   = 0x2009,   /**< English (Jamaica) */
+    USB_LANGID_ENG_CAR  = 0x2409,   /**< English (Caribbean) */
+    USB_LANGID_ENG_BZ   = 0x2809,   /**< English (Belize) */
+    USB_LANGID_ENG_TH   = 0x2c09,   /**< English (Trinidad) */
+    USB_LANGID_ENG_ZW   = 0x3009,   /**< English (Zimbabwe) */
+    USB_LANGID_ENG_PH   = 0x3409,   /**< English (Philippines) */
+    USB_LANGID_EST      = 0x0425,   /**< Estonian */
+    USB_LANGID_FAO      = 0x0438,   /**< Faeroese */
+    USB_LANGID_FAS      = 0x0429,   /**< Farsi */
+    USB_LANGID_FIN      = 0x040b,   /**< Finnish */
+    USB_LANGID_FRA      = 0x040c,   /**< French (Standard) */
+    USB_LANGID_FRA_BE   = 0x080c,   /**< French (Belgian) */
+    USB_LANGID_FRA_CA   = 0x0c0c,   /**< French (Canadian) */
+    USB_LANGID_FRA_SZ   = 0x100c,   /**< French (Switzerland) */
+    USB_LANGID_FRA_LU   = 0x140c,   /**< French (Luxembourg) */
+    USB_LANGID_FRA_MC   = 0x180c,   /**< French (Monaco) */
+    USB_LANGID_KAT      = 0x0437,   /**< Georgian */
+    USB_LANGID_DEU      = 0x0407,   /**< German (Standard) */
+    USB_LANGID_DEU_SZ   = 0x0807,   /**< German (Switzerland) */
+    USB_LANGID_DEU_AT   = 0x0c07,   /**< German (Austria) */
+    USB_LANGID_DEU_LU   = 0x1007,   /**< German (Luxembourg) */
+    USB_LANGID_DEU_LI   = 0x1407,   /**< German (Liechtenstein) */
+    USB_LANGID_ELL      = 0x0408,   /**< Greek */
+    USB_LANGID_GUJ      = 0x0447,   /**< Gujarati */
+    USB_LANGID_HEB      = 0x040d,   /**< Hebrew */
+    USB_LANGID_HIN      = 0x0439,   /**< Hindi */
+    USB_LANGID_HUN      = 0x040e,   /**< Hungarian */
+    USB_LANGID_ISL      = 0x040f,   /**< Icelandic */
+    USB_LANGID_IND      = 0x0421,   /**< Indonesian */
+    USB_LANGID_ITA      = 0x0410,   /**< Italian (Standard) */
+    USB_LANGID_ITA_SZ   = 0x0810,   /**< Italian (Switzerland) */
+    USB_LANGID_JPN      = 0x0411,   /**< Japanese */
+    USB_LANGID_KAN      = 0x044b,   /**< Kannada */
+    USB_LANGID_KAS      = 0x0860,   /**< Kashmiri (India) */
+    USB_LANGID_KAZ      = 0x043f,   /**< Kazakh */
+    USB_LANGID_KOK      = 0x0457,   /**< Konkani */
+    USB_LANGID_KOR      = 0x0412,   /**< Korean */
+    USB_LANGID_KOR_JOH  = 0x0812,   /**< Korean (Johab) */
+    USB_LANGID_LAV      = 0x0426,   /**< Latvian */
+    USB_LANGID_LIT      = 0x0427,   /**< Lithuanian */
+    USB_LANGID_LIT_CLS  = 0x0827,   /**< Lithuanian (Classic) */
+    USB_LANGID_MKD      = 0x042f,   /**< Macedonian */
+    USB_LANGID_MSA      = 0x043e,   /**< Malay (Malaysian) */
+    USB_LANGID_MSA_BN   = 0x083e,   /**< Malay (Brunei Darussalam) */
+    USB_LANGID_MAL      = 0x044c,   /**< Malayalam */
+    USB_LANGID_MNI      = 0x0458,   /**< Manipuri */
+    USB_LANGID_MAR      = 0x044e,   /**< Marathi */
+    USB_LANGID_NEP      = 0x0861,   /**< Nepali (India) */
+    USB_LANGID_NOB      = 0x0414,   /**< Norwegian (Bokmal) */
+    USB_LANGID_NNO      = 0x0814,   /**< Norwegian (Nynorsk) */
+    USB_LANGID_ORI      = 0x0448,   /**< Oriya */
+    USB_LANGID_POL      = 0x0415,   /**< Polish */
+    USB_LANGID_POR_BR   = 0x0416,   /**< Portuguese (Brazil) */
+    USB_LANGID_POR      = 0x0816,   /**< Portuguese (Standard) */
+    USB_LANGID_PAN      = 0x0446,   /**< Punjabi */
+    USB_LANGID_RON      = 0x0418,   /**< Romanian */
+    USB_LANGID_RUS      = 0x0419,   /**< Russian */
+    USB_LANGID_SAN      = 0x044f,   /**< Sanskrit */
+    USB_LANGID_SRB_CYR  = 0x0c1a,   /**< Serbian (Cyrillic) */
+    USB_LANGID_SRB_LAT  = 0x081a,   /**< Serbian (Latin) */
+    USB_LANGID_SND      = 0x0459,   /**< Sindhi */
+    USB_LANGID_SLK      = 0x041b,   /**< Slovak */
+    USB_LANGID_SLV      = 0x0424,   /**< Slovenian */
+    USB_LANGID_SPA      = 0x040a,   /**< Spanish (Traditional Sort) */
+    USB_LANGID_SPA_MX   = 0x080a,   /**< Spanish (Mexican) */
+    USB_LANGID_SPA_MDN  = 0x0c0a,   /**< Spanish (Modern Sort) */
+    USB_LANGID_SPA_GT   = 0x100a,   /**< Spanish (Guatemala) */
+    USB_LANGID_SPA_CR   = 0x140a,   /**< Spanish (Costa Rica) */
+    USB_LANGID_SPA_PA   = 0x180a,   /**< Spanish (Panama) */
+    USB_LANGID_SPA_DO   = 0x1c0a,   /**< Spanish (Dominican Republic) */
+    USB_LANGID_SPA_VE   = 0x200a,   /**< Spanish (Venezuela) */
+    USB_LANGID_SPA_CO   = 0x240a,   /**< Spanish (Colombia) */
+    USB_LANGID_SPA_PE   = 0x280a,   /**< Spanish (Peru) */
+    USB_LANGID_SPA_AR   = 0x2c0a,   /**< Spanish (Argentina) */
+    USB_LANGID_SPA_EC   = 0x300a,   /**< Spanish (Ecuador) */
+    USB_LANGID_SPA_CL   = 0x340a,   /**< Spanish (Chile) */
+    USB_LANGID_SPA_UY   = 0x380a,   /**< Spanish (Uruguay) */
+    USB_LANGID_SPA_PY   = 0x3c0a,   /**< Spanish (Paraguay) */
+    USB_LANGID_SPA_BO   = 0x400a,   /**< Spanish (Bolivia) */
+    USB_LANGID_SPA_SV   = 0x440a,   /**< Spanish (El Salvador) */
+    USB_LANGID_SPA_HN   = 0x480a,   /**< Spanish (Honduras) */
+    USB_LANGID_SPA_NI   = 0x4c0a,   /**< Spanish (Nicaragua) */
+    USB_LANGID_SPA_PR   = 0x500a,   /**< Spanish (Puerto Rico) */
+    USB_LANGID_NSO      = 0x0430,   /**< Sutu, Sotho. */
+    USB_LANGID_SWA      = 0x0441,   /**< Swahili (Kenya) */
+    USB_LANGID_SWE      = 0x041d,   /**< Swedish */
+    USB_LANGID_SWE_FI   = 0x081d,   /**< Swedish (Finland) */
+    USB_LANGID_TAM      = 0x0449,   /**< Tamil */
+    USB_LANGID_TAT      = 0x0444,   /**< Tatar (Tatarstan) */
+    USB_LANGID_TEL      = 0x044a,   /**< Telugu */
+    USB_LANGID_THA      = 0x041e,   /**< Thai */
+    USB_LANGID_TUR      = 0x041f,   /**< Turkish */
+    USB_LANGIG_UKR      = 0x0422,   /**< Ukrainian */
+    USB_LANGID_URD_PK   = 0x0420,   /**< Urdu (Pakistan) */
+    USB_LANGID_URD_IN   = 0x0820,   /**< Urdu (India) */
+    USB_LANGID_UZB_LAT  = 0x0443,   /**< Uzbek (Latin) */
+    USB_LANGID_UZB_CYR  = 0x0843,   /**< Uzbek (Cyrillic) */
+    USB_LANGID_VIE      = 0x042a,   /**< Vietnamese. */
+};
+
+/** \brief common USB descriptor header */
+struct usb_header_descriptor {
+    uint8_t bLength;                /**< Size of the descriptor, in bytes. */
+    uint8_t bDescriptorType;        /**< Type of the descriptor. */
+} __attribute__((packed));
+
+/** \brief Represents a USB device descriptor
+ *  \details A device descriptor describes general information about a USB device. It includes information that applies
+ *           globally to the device and all of the device’s configurations. A USB device has only one device descriptor.
+ *           A high-speed capable device that has different device information for full-speed and high-speed must also
+ *           have a \ref usb_qualifier_descriptor
+ */
+struct usb_device_descriptor {
+    uint8_t  bLength;               /**< Size of the descriptor, in bytes. */
+    uint8_t  bDescriptorType;       /**< Type of the descriptor, must be a \ref USB_DTYPE_DEVICE. */
+    uint16_t bcdUSB;                /**< BCD of the supported USB specification. \ref VERSION_BCD utility macro. */
+    uint8_t  bDeviceClass;          /**< USB device class. */
+    uint8_t  bDeviceSubClass;       /**< USB device subclass. */
+    uint8_t  bDeviceProtocol;       /**< USB device protocol. */
+    uint8_t  bMaxPacketSize0;       /**< Size of the control (address 0) endpoint's bank in bytes. */
+    uint16_t idVendor;              /**< Vendor ID for the USB product. */
+    uint16_t idProduct;             /**< Unique product ID for the USB product. */
+    uint16_t bcdDevice;             /**< Product release (version) number. \ref VERSION_BCD utility macro. */
+    uint8_t  iManufacturer;         /**< String index for the manufacturer's name. */
+    uint8_t  iProduct;              /**< String index for the product name/details. */
+    uint8_t  iSerialNumber;         /**< String index for the product serial number, \ref INTSERIALNO_DESCRIPTOR can be used*/
+    uint8_t  bNumConfigurations;    /**< Total number of configurations supported by the device. */
+} __attribute__((packed));
+
+/** \brief USB device qualifier descriptor
+ *  \details The device_qualifier descriptor describes information about a high-speed capable device that would
+ *           change if the device were operating at the other speed. For example, if the device is currently operating
+ *           at full-speed, the device qualifier returns information about how it would operate at high-speed and vice-versa.
+ */
+struct usb_qualifier_descriptor {
+    uint8_t  bLength;               /**< Size of the descriptor, in bytes. */
+    uint8_t  bDescriptorType;       /**< Type of the descriptor, must be a \ref USB_DTYPE_QUALIFIER. */
+    uint16_t bcdUSB;                /**< BCD of the supported USB specification. \ref VERSION_BCD utility macro. */
+    uint8_t  bDeviceClass;          /**< USB device class. */
+    uint8_t  bDeviceSubClass;       /**< USB device subclass. */
+    uint8_t  bDeviceProtocol;       /**< USB device protocol. */
+    uint8_t  bMaxPacketSize0;       /**< Size of the control (address 0) endpoint's bank in bytes. */
+    uint8_t  bNumConfigurations;    /**< Total number of configurations supported by the device. */
+    uint8_t  bReserved;             /**< Reserved for future use, must be 0. */
+} __attribute__((packed));
+/** \brief USB device configuration descriptor
+ *  \details The configuration descriptor describes information about a specific device configuration. The descriptor
+ *           contains a bConfigurationValue field with a value that, when used as a parameter to the SetConfiguration()
+ *           request, causes the device to assume the described configuration.
+ */
+struct usb_config_descriptor {
+    uint8_t  bLength;               /**< Size of the descriptor, in bytes. */
+    uint8_t  bDescriptorType;       /**< Type of the descriptor, must be a \ref USB_DTYPE_CONFIGURATION. */
+    uint16_t wTotalLength;          /**< Size of the configuration descriptor header, and all sub descriptors inside the configuration. */
+    uint8_t  bNumInterfaces;        /**< Total number of interfaces in the configuration. */
+    uint8_t  bConfigurationValue;   /**< Configuration index of the current configuration. */
+    uint8_t  iConfiguration;        /**< Index of a string descriptor describing the configuration. */
+    uint8_t  bmAttributes;          /**< Configuration attributes, comprised of a mask of \c USB_CONFIG_ATTR_* masks. On all devices, this should include USB_CONFIG_ATTR_RESERVED at a minimum. */
+    uint8_t  bMaxPower;             /**< Maximum power consumption of the device while in the current configuration, calculated by the \ref USB_CFG_POWER_MA() macro. */
+} __attribute__((packed));
+/** \brief USB interface descriptor
+ *  \details The interface descriptor describes a specific interface within a configuration. A configuration provides one or more interfaces,
+ *           each with zero or more endpoint descriptors describing a unique set of endpoints within the configuration.
+ */
+struct usb_interface_descriptor {
+    uint8_t bLength;                /**< Size of the descriptor, in bytes. */
+    uint8_t bDescriptorType;        /**< Type of the descriptor, must be \ref USB_DTYPE_INTERFACE */
+    uint8_t bInterfaceNumber;       /**< Index of the interface in the current configuration. */
+    uint8_t bAlternateSetting;      /**< Alternate setting for the interface number. */
+    uint8_t bNumEndpoints;          /**< Total number of endpoints in the interface. */
+    uint8_t bInterfaceClass;        /**< Interface class ID. */
+    uint8_t bInterfaceSubClass;     /**< Interface subclass ID. */
+    uint8_t bInterfaceProtocol;     /**< Interface protocol ID. */
+    uint8_t iInterface;             /**< Index of the string descriptor describing the interface. */
+} __attribute__((packed));
+struct usb_iad_descriptor {
+    uint8_t bLength;                /**< Size of the descriptor, in bytes. */
+    uint8_t bDescriptorType;        /**< Type of the descriptor, either a value in */
+    uint8_t bFirstInterface;        /**< Index of the first associated interface. */
+    uint8_t bInterfaceCount;        /**< Total number of associated interfaces. */
+    uint8_t bFunctionClass;         /**< Interface class ID. */
+    uint8_t bFunctionSubClass;      /**< Interface subclass ID. */
+    uint8_t bFunctionProtocol;      /**< Interface protocol ID. */
+    uint8_t iFunction;              /**< Index of the string descriptor describing the interface association. */
+} __attribute__((packed));
+/** \brief USB endpoint descriptor
+ *  \details This descriptor contains the information required by the host to determine the bandwidth requirements of each endpoint.
+ */
+struct usb_endpoint_descriptor {
+    uint8_t  bLength;               /**< Size of the descriptor, in bytes. */
+    uint8_t  bDescriptorType;       /**< Type of the descriptor, must be \ref USB_DTYPE_ENDPOINT */
+    uint8_t  bEndpointAddress;      /**< Logical address of the endpoint within the device for the current configuration, including direction mask. */
+    uint8_t  bmAttributes;          /**< Endpoint attributes, \ref USB_ENDPOINT_DEF. */
+    uint16_t wMaxPacketSize;        /**< Size of the endpoint bank, in bytes. This indicates the maximum packet size that the endpoint can receive at a time. */
+    uint8_t  bInterval;             /**< Polling interval in milliseconds for the endpoint if it is an INTERRUPT or ISOCHRONOUS type. */
+} __attribute__((packed));
+
+/** \brief USB string descriptor
+ *  \details String descriptors are referenced by their one-based index number. A string descriptor contains one or more not NULL-terminated Unicode strings.
+ *  \note String descriptors are optional. if a device does not support string descriptors, all references to string descriptors within device, configuration,
+ *        and interface descriptors must be reset to zero.
+ */
+struct usb_string_descriptor {
+    uint8_t  bLength;               /**< Size of the descriptor, in bytes. */
+    uint8_t  bDescriptorType;       /**< Type of the descriptor, must be \ref USB_DTYPE_STRING */
+    uint16_t wString[];             /**< String data, as unicode characters (alternatively, array of \ref USB_STD_LANGIDS ). */
+} __attribute__((packed));
+
+struct usb_debug_descriptor {
+    uint8_t  bLength;
+    uint8_t  bDescriptorType;
+    uint8_t  bDebugInEndpoint;      /**< Endpoint number of the Debug Data IN endpoint. This is a Bulk-type endpoint with a maximum packet size of 8 bytes.  */
+    uint8_t  bDebugOutEndpoint;     /**< Endpoint number of the Debug Data OUTendpoint. This is a Bulk-type endpoint with a maximum packet size of 8 bytes.  */
+} __attribute__((packed));
+
+
+/** @} */
+
+#if defined (__cplusplus)
+}
+#endif
+#endif //_USB_STD_H_

+ 399 - 0
inc/usbd_core.h

@@ -0,0 +1,399 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef _USBD_CORE_H_
+#define _USBD_CORE_H
+#if defined(__cplusplus)
+    extern "C" {
+#endif
+#include <stdbool.h>
+
+/** \addtogroup USBD_CORE USB device core
+ * \brief This module contains core and hardware driver framework definitions
+ * \details
+ *
+ * @{ */
+#define USB_EPTYPE_DBLBUF       0x04        /**< indicates a doublebuffered endpoint (bulk endpoint only) */
+#define USB_EPDIR_IN            0x00        /**< indicates host-to-device endpoint direction  */
+#define USB_EPDIR_OUT           0x80        /**< indicates device-to-host endpoint direction */
+
+
+/** \name bmRequestType bitmapped field
+ * @{ */
+#define USB_REQ_DIRECTION       (1 << 7)
+#define USB_REQ_HOSTTODEV       (0 << 7)
+#define USB_REQ_DEVTOHOST       (1 << 7)
+#define USB_REQ_TYPE            (3 << 5)
+#define USB_REQ_STANDARD        (0 << 5)
+#define USB_REQ_CLASS           (1 << 5)
+#define USB_REQ_VENDOR          (2 << 5)
+#define USB_REQ_RECIPIENT       (3 << 0)
+#define USB_REQ_DEVICE          (0 << 0)
+#define USB_REQ_INTERFACE       (1 << 0)
+#define USB_REQ_ENDPOINT        (2 << 0)
+#define USB_REQ_OTHER           (3 << 0)
+/** @} */
+
+
+#if defined(__ASSEMBLER__)
+    #define usbd_evt_reset      0
+    #define usbd_evt_sof        1
+    #define usbd_evt_susp       2
+    #define usbd_evt_wkup       3
+    #define usbd_evt_eptx       4
+    #define usbd_evt_eprx       5
+    #define usbd_evt_epsetup    6
+    #define usbd_evt_error      7
+    #define usbd_evt_esof       8
+#else
+
+/** USB device events */
+enum usbd_evt {
+    usbd_evt_reset,             /**< Reset */
+    usbd_evt_sof,               /**< Start Of Frame */
+    usbd_evt_susp,              /**< Suspend */
+    usbd_evt_wkup,              /**< Wakeup */
+    usbd_evt_eptx,              /**< Transmit completed */
+    usbd_evt_eprx,              /**< Data packet received */
+    usbd_evt_epsetup,           /**< Setup packet received */
+    usbd_evt_error,             /**< Data error */
+    usbd_evt_esof,              /**< Missed SOF */
+    usbd_evt_count, /* this is trick to count qty */
+};
+
+/** USB device machine state */
+enum usbd_machine_state {
+    usbd_state_disabled,
+    usbd_state_disconnected,
+    usbd_state_default,         /**< Default */
+    usbd_state_addressed,       /**< Addressed */
+    usbd_state_configured,      /**< Configured */
+};
+
+/** USB device control endpoint machine state */
+enum usbd_ctl_state {
+    usbd_ctl_idle,              /**< Idle. Awaiting for SETUP packet */
+    usbd_ctl_rxdata,            /**< RX. Receiving DATA-OUT payload */
+    usbd_ctl_txdata,            /**< TX. Transmitting DATA-IN payload */
+    usbd_ctl_ztxdata,           /**< TX. Transmitting DATA-IN payload. Zero length packet maybe required. */
+    usbd_ctl_lastdata,          /**< TX. Last DATA-IN packed passed to buffer. Awaiting for the TX completion */
+    usbd_ctl_statusin,          /**< STATUS-IN stage */
+    usbd_ctl_statusout,         /**< STATUS-OUT stage */
+};
+
+/** Asynchronous device control commands  */
+enum usbd_commands {
+    usbd_cmd_enable,            /**< Enables device */
+    usbd_cmd_disable,           /**< Disables device */
+    usbd_cmd_connect,           /**< Connects device to host */
+    usbd_cmd_disconnect,        /**< Disconnects device from host */
+    usbd_cmd_reset,             /**< Resets device */
+};
+
+typedef struct usbd_device usbd_device;
+typedef struct usbd_ctlreq usbd_ctlreq;
+typedef struct usbd_status usbd_status;
+
+/**\name USB Device middleware callbacks function prototypes
+ * @{ */
+ /** Generic USB device event callback for events and endpoints processing
+  * \param[in] dev pointer to USB device
+  * \param event \ref usbd_evt "USB event"
+  * \param ep active endpoint number
+  * \note endpoints with same indexes i.e. 0x01 and 0x81 shares same callback.
+  */
+typedef void (*usbd_evt_callback)(usbd_device *dev, uint8_t event, uint8_t ep);
+
+/** USB control transfer completed callback.
+ * \param[in] dev pointer to USB device
+ * \param[in] req pointer to usb request structure
+ */
+typedef void (*usbd_ctl_complete)(usbd_device *dev, usbd_ctlreq *req);
+
+/** USB control callback.
+ * \details Uses for the control request processing.
+ *          Some requests will be handled by core if callback don't process it (returns FALSE). If request was not processed STALL PID will be issued.
+ *          - GET_CONFIGURATION
+ *          - SET_CONFIGURATION (passes to \ref usbd_cfg_callback)
+ *          - GET_DESCRIPTOR (passes to \ref usbd_dsc_callback)
+ *          - GET_STATUS
+ *          - SET_FEATURE, CLEAR_FEATURE (endpoints only)
+ *          - SET_ADDRESS
+ * \param[in] dev points to USB device
+ * \param[in] req pointer to usb request structure
+ * \param[out] *callback \ref usbd_ctl_complete "pointer to USB control transfer completed callback", default is NULL (no callback)
+ * \return TRUE if control request processed successfully, false otherwise.
+ */
+typedef bool (*usbd_ctl_callback)(usbd_device *dev, usbd_ctlreq *req, usbd_ctl_complete *callback);
+
+/** USB get descriptor callback
+ * \details Called when GET_DESCRIPTOR request issued
+ * \param[in] req pointer to usb control request structure
+ * \param[in,out] address pointer to the descriptor in memory. Points to req->data by default. You can use this buffer.
+ * \param[in,out] dsize descriptor size. req->data buffer size by default.
+ * \return TRUE if you passed the correct descriptor, FALSE otherwise.
+ */
+typedef bool (*usbd_dsc_callback)(usbd_ctlreq *req, void **address, uint16_t *dsize);
+
+/** USB set configuration callback
+ * \details called when SET_CONFIGURATION request issued
+ * \param[in] dev pointer to USB device
+ * \param[in] cfg configuration number.
+ * \note if config is 0 all device endpoints EP0 will be de-configured by core before entering this callback
+ * \return TRUE if success
+ */
+typedef bool (*usbd_cfg_callback)(usbd_device *dev, uint8_t cfg);
+
+/** @} */
+
+/**\name USB Hardware driver API function prototypes
+ * @{ */
+
+/** Enables or disables USB hardware
+ * \param enable Enables USB when TRUE disables otherwise
+ */
+typedef void (*usbd_hw_enable)(bool enable);
+
+/** Resets USB hardware */
+typedef void (*usbd_hw_reset)(void);
+
+/** Connects or disconnects USB hardware to/from usb host
+ * \param connect Connects USB to host if TRUE, disconnects otherwise
+ */
+typedef void (*usbd_hw_connect)(bool connect);
+
+/** Sets USB hardware address
+ * \param address USB address
+ */
+typedef void (*usbd_hw_setaddr)(uint8_t address);
+
+/** Configures endpoint
+ * \param ep endpoint address. Use USB_EPDIR_ macros to set endpoint direction
+ * \param eptype endpoint type. Use USB_EPTYPE_* macros.
+ * \param epsize endpoint size in bytes
+ * \return TRUE if success
+ */
+typedef bool (*usbd_hw_ep_config)(uint8_t ep, uint8_t eptype, uint16_t epsize);
+
+/** De-configures, cleans and disables endpoint
+ * \param ep endpoint index
+ * \note if you have two one-direction single-buffered endpoints with same index (i.e. 0x02 and 0x82) both will be deconfigured.
+ */
+typedef void (*usbd_hw_ep_deconfig)(uint8_t ep);
+
+/** Reads data from OUT or control endpoint
+ * \param ep endpoint index, should belong to OUT or CONTROL endpoint.
+ * \param buf pointer to read buffer
+ * \param blen size of the read buffer in bytes
+ * \return size of the actually received data
+ */
+typedef uint16_t (*usbd_hw_ep_read)(uint8_t ep, void *buf, uint16_t blen);
+
+/** Writes data to IN or control endpoint
+ * \param ep endpoint index, hould belong to IN or CONTROL endpoint
+ * \param buf pointer to data buffer
+ * \param blen size of data will be written
+ * \return number of written bytes
+ */
+typedef uint16_t (*usbd_hw_ep_write)(uint8_t ep, void *buf, uint16_t blen);
+
+/** Stalls and unstalls endpoint
+ * \param ep endpoint address
+ * \param stall endpoint will be stalled if TRUE and unstalled otherwise.
+ * \note Has no effect on inactive endpoints.
+ */
+typedef void (*usbd_hw_ep_setstall)(uint8_t ep, bool stall);
+
+/** Checks endpoint for stalled state
+ * \param ep endpoint address
+ * \return TRUE if endpoint is stalled
+ */
+typedef bool (*usbd_hw_ep_isstalled)(uint8_t ep);
+
+/** Polls USB hardware for the events
+ * \param[in] dev pointer to usb device structure
+ * \param drv_callback callback to event processing subroutine
+ */
+typedef void (*usbd_hw_poll)(usbd_device *dev, usbd_evt_callback drv_callback);
+
+/** Makes a string descriptor contains unique serial number from hardware ID's
+ * \param[in] buffer pointer to buffer for the descriptor
+ * \return of the descriptor in bytes
+ */
+typedef uint16_t (*usbd_hw_get_serialno)(void *buffer);
+
+/** @} */
+
+/** Represents generic USB control request */
+struct usbd_ctlreq {
+    uint8_t     bmRequestType;  /**< This bitmapped field identifies the characteristics of the specific request. */
+    uint8_t     bRequest;       /**< This field specifies the particular request. */
+    uint16_t    wValue;         /**< It is used to pass a parameter to the device, specific to the request. */
+    uint16_t    wIndex;         /**< It is used to pass a parameter to the device, specific to the request. */
+    uint16_t    wLength;        /**< This field specifies the length of the data transferred during the second phase of the control transfer */
+    uint8_t     data[];         /**< Request data payload */
+} __attribute__((packed));
+
+
+/** USB device status data for control endpoint */
+struct usbd_status {
+    void        *data_buf;
+    void        *data_ptr;      /**< Pointer to control endpoint current data buffer */
+    uint16_t    data_count;     /**< Control endpoint data counter */
+    uint16_t    data_maxsize;   /**< Size of the data buffer for control endpoint */
+    uint8_t     ep0size;        /**< Size of the control endpoint */
+    uint8_t     device_cfg;     /**< Current device configuration ID */
+    uint8_t     device_state;   /**< Current \ref usbd_machine_state */
+    uint8_t     control_state;  /**< Current \ref usbd_ctl_state */
+};
+
+/** Structure represents a hardware USB driver call table */
+struct usbd_driver {
+    usbd_hw_enable          enable;
+    usbd_hw_reset           reset;
+    usbd_hw_connect         connect;
+    usbd_hw_setaddr         setaddr;
+    usbd_hw_ep_config       ep_config;
+    usbd_hw_ep_deconfig     ep_deconfig;
+    usbd_hw_ep_read         ep_read;
+    usbd_hw_ep_write        ep_write;
+    usbd_hw_ep_setstall     ep_setstall;
+    usbd_hw_ep_isstalled    ep_isstalled;
+    usbd_hw_poll            poll;
+    usbd_hw_get_serialno    get_serialno_desc;
+};
+
+/** Structure represents a USB device data. No other data used by USB core and driver
+ *  \note use helper \ref usbd_device typedef
+ *  \note structure must be aligned
+ */
+struct usbd_device {
+    const struct usbd_driver    *driver;
+    usbd_ctl_callback           control_callback;
+    usbd_ctl_complete           complete_callback;
+    usbd_cfg_callback           config_callback;
+    usbd_dsc_callback           descriptor_callback;
+    usbd_evt_callback           events[usbd_evt_count];     /**< events callbacks array */
+    usbd_evt_callback           endpoint[8];                /**< endpoint callbacks array for tx, rx and setup events */
+    usbd_status                 status;
+};
+
+
+/** Initializes device structure
+ * \param dev USB device that will be initialized
+ * \param drv Pointer to hardware driver
+ * \param ep0size Control endpoint 0 size
+ * \param buffer Pointer to control request data buffer
+ * \param bsize Size of the data buffer
+ */
+void usbd_init(usbd_device *dev, const struct usbd_driver *drv, const uint8_t ep0size, void *buffer, const uint16_t bsize);
+
+/** Polls USB for events
+ * \param dev Pointer to device structure
+ * \note can be called as from main routine as from USB interrupt
+ */
+void usbd_poll(usbd_device *dev);
+
+/** Asynchronous devise control
+ * \param dev USB device
+ * \param cmd control command
+ */
+void usbd_control(usbd_device *dev, enum usbd_commands cmd);
+
+
+
+/** \name API macro functions
+ * @{ */
+
+/** Macro to register control callback
+ * \param dev pointer to \ref usbd_device structure
+ * \param cb pointer to user \ref usbd_ctl_callback
+ */
+#define usbd_reg_control(dev, cb) (dev)->control_callback = (cb)
+
+/** Macro to register set configuration callback
+ * \param dev pointer to \ref usbd_device structire
+ * \param cb pointer to user \ref usbd_ctl_callback
+ */
+#define usbd_reg_config(dev, cb) (dev)->config_callback = (cb)
+
+/** Macro to register GET_DESCRIPTOR callback
+ * \param dev USB device
+ * \param cb callback
+ */
+#define usbd_reg_descr(dev, cb) (dev)->descriptor_callback = (cb)
+
+/** Macro to register endpoint callback
+ * \param dev pointer to \ref usbd_device structure
+ * \param ep endpoint index
+ * \param cb pointer to user \ref usbd_evt_callback callback for endpoint events
+ */
+#define usbd_reg_endpoint(dev, ep, cb) (dev)->endpoint[(ep) & 0x07] = (cb)
+
+/** Macro to registers event callback
+ * \param dev pointer to \ref usbd_device structure
+ * \param evt device \ref usbd_evt "event" wants to be registered
+ * \param cb pointer to user \ref usbd_evt_callback for this event
+ */
+#define usbd_reg_event(dev, evt, cb) (dev)->events[(evt)] = (cb)
+
+/** Macro to configure endpoint
+ * \param dev pointer to \ref usbd_device structure
+ * \copydetails usbd_hw_ep_config
+ */
+#define usbd_ep_config(dev, ep, eptype, epsize) (dev)->driver->ep_config((ep), (eptype), (epsize))
+
+/** Macro to deconfigure endpoint
+ * \param dev pointer to \ref usbd_device structure
+ * \copydetails usbd_hw_ep_deconfig
+ */
+#define usbd_ep_deconfig(dev, ep) (dev)->driver->ep_deconfig(ep)
+
+/** Macro to write data to endpoint
+ * \param dev pointer to \ref usbd_device structure
+ * \copydetails usbd_hw_ep_write
+ */
+#define usbd_ep_write(dev, ep, buf, blen) (dev)->driver->ep_write((ep), (buf), (blen))
+
+/** Macro to read data from endpoint
+ * \param dev pointer to \ref usbd_device structure
+ * \copydetails usbd_hw_ep_read
+ */
+#define usbd_ep_read(dev, ep, buffer, length) (dev)->driver->ep_read((ep), (buf), (blen))
+
+/** Macro to stall endpoint
+ * \param dev pointer to \ref usbd_device structure
+ * \param ep endpoint address
+ */
+#define usbd_ep_stall(dev, ep) (dev)->driver->ep_setstall((ep), 1)
+
+/** Macro to unstall endpoint
+ * \param dev pointer to \ref usbd_device structure
+ * \param ep endpoint address
+ */
+#define usbd_ep_unstall(dev, ep) (dev)->driver->ep_setstall((ep), 0)
+
+/** @} */
+
+
+#endif //(__ASSEMBLER__)
+
+/**@} */
+
+
+#if defined(__cplusplus)
+    }
+#endif
+#endif //_USBD_STD_H_

+ 31 - 0
readme.md

@@ -0,0 +1,31 @@
+### Lightweight USB Device Stack ###
+
++ Lightweight and fast
++ Event-driven process workflow
++ Completely separated USB hardware driver and middleware
++ Easy to use.
+
+### Supported hardware ###
+
+| MCU series | Driver Name | Written on | Endpoints (1) | Internal S/N | Doublebuffered transfer   |
+| ---------- | ----------- | ---------- | ------------- |------------- | ------------------------- |
+| STM32L0    | usb_stml0a  | GCC ASM    |             8 | FNV1A 32bit  | ISO, BULK OUT, BULK IN (2)|
+
+
+1. Single physicsl endpoint can be used to implement
+  + one bi-directional/single-buffer logical endpoint (CONTROL)
+  + one mono-directional/double-buffer logical endpoint (BULK OR ISOCHRONOUS)
+  + two mono-directional/single-buffer logical endpoints (BULK OR INTERRUPT)
+
+2. At this moment BULK IN endpoint can use both buffers, but it is not **real** doublebuffered.
+
+### Implemented definitions for classes ###
+1. USB HID based on [Device Class Definition for Human Interface Devices (HID) Version 1.11](http://www.usb.org/developers/hidpage/HID1_11.pdf)
+2. USB DFU based on [USB Device Firmware Upgrade Specification, Revision 1.1] (http://www.usb.org/developers/docs/devclass_docs/DFU_1.1.pdf)
+3. USB CDC based on [Class definitions for Communication Devices 1.2] (http://www.usb.org/developers/docs/devclass_docs/CDC1.2_WMC1.1_012011.zip)
+
+### Useful Recources ###
+1. [USB Implementers Forum official site] (http://www.usb.org/home)
+2. [USB Made Simple] (http://www.usbmadesimple.co.uk/)
+3. [LUFA - the Lightweight USB Framework for AVRs.] (https://github.com/abcminiuser/lufa)
+4. [Open Source ARM cortex m microcontroller library] (https://github.com/libopencm3/libopencm3)

+ 800 - 0
src/usb_32l0A.S

@@ -0,0 +1,800 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#if !defined (__ASSEMBLER__)
+    #define __ASSEMBLER__
+#endif
+#include "..\inc\usbd_core.h"
+
+#define USB_EPBASE  0x40005C00
+#define USB_REGBASE 0x40005C40
+#define USB_PMABASE 0x40006000
+#define RCC_BASE    0x40021000
+#define UID_BASE    0x1FF80050
+
+#define EP_SETUP    0x0800
+#define EP_TYPE     0x0600
+#define EP_KIND     0x0100
+#define EP_ADDR     0x000F
+
+#define EP_RX_CTR   0x8000
+#define EP_RX_DTOG  0x4000
+#define EP_RX_STAT  0x3000
+#define EP_RX_SWBUF 0x0040
+
+#define EP_RX_DIS   0x0000
+#define EP_RX_STAL  0x1000
+#define EP_RX_NAK   0x2000
+#define EP_RX_VAL   0x3000
+
+#define EP_TX_CTR   0x0080
+#define EP_TX_DTOG  0x0040
+#define EP_TX_STAT  0x0030
+#define EP_TX_SWBUF 0x4000
+
+#define EP_TX_DIS   0x0000
+#define EP_TX_STAL  0x0010
+#define EP_TX_NAK   0x0020
+#define EP_TX_VAL   0x0030
+
+
+#define EP_NOTOG    (EP_RX_CTR | EP_TX_CTR | EP_SETUP | EP_TYPE | EP_KIND | EP_ADDR)
+
+#define TGL_SET(mask, bits)  ((EP_NOTOG | (mask))<<16 | (bits))
+
+    .syntax unified
+    .text
+    .thumb
+
+
+    .globl  usb_stml0a
+    .align  2
+usb_stml0a:
+    .long   _enable
+    .long   _reset
+    .long   _connect
+    .long   _setaddr
+    .long   _ep_config
+    .long   _ep_deconfig
+    .long   _ep_read
+    .long   _ep_write
+    .long   _ep_setstall
+    .long   _ep_isstalled
+    .long   _evt_poll
+    .long   _get_serial_desc
+    .size   usb_stml0a, . - usb_stml0a
+
+
+    .thumb_func
+    .type _get_serial_desc, %function
+
+/*  uint16_t get_serial_desc (void *buffer)
+ *  R0 <- buffer for the string descriptor
+ *  descrpitor size -> R0
+ */
+_get_serial_desc:
+    push    {r4, r5, lr}
+    movs    r1,18               //descriptor size 18 bytes
+    strb    r1,[r0]
+    movs    r1, #0x03           //DTYPE_STRING
+    strb    r1,[r0, #0x01]
+    ldr     r5, .L_uid_base     //UID3 this is the serial number
+    ldr     r4, .L_fnv1a_offset //FNV1A offset
+    ldr     r2, [r5, 0x00]      //UID0
+    bl      .L_fnv1a
+    ldr     r2, [r5, 0x04]      //UID1
+    bl      .L_fnv1a
+    ldr     r2, [r5, 0x14]      //UID2
+    bl      .L_fnv1a
+    movs    r3, #28
+.L_gsn_loop:
+    movs    r1, r4
+    lsrs    r1, r3
+    lsls    r1, #28
+    lsrs    r1, #28
+    adds    r1, #0x30           //'0'
+    cmp     r1, #0x3A
+    blo     .L_gsn_store
+    adds    r1, #0x07           //'A' - '0'
+.L_gsn_store:
+    adds    r0, #0x02
+    strb    r1, [r0]
+    lsrs    r1, #0x08
+    strb    r1, [r0, #0x01]
+    subs    r3, #0x04
+    bpl     .L_gsn_loop
+    movs    r0, #18
+    pop     {r4, r5, pc}
+
+.L_fnv1a:
+    ldr     r1, .L_fnv1a_prime       //FNV1A prime
+    movs    r3, #0xFF
+    ands    r3, r2
+    eors    r4, r3
+    muls    r4, r1
+    lsrs    r2, #8
+    movs    r3, #0xFF
+    ands    r3, r2
+    eors    r4, r3
+    muls    r4, r1
+    lsrs    r2, #8
+    movs    r3, #0xFF
+    ands    r3, r2
+    eors    r4, r3
+    muls    r4, r1
+    lsrs    r2, #8
+    eors    r4, r2
+    muls    r4, r1
+    bx      lr
+
+    .align 2
+.L_fnv1a_prime:     .long   16777619
+.L_fnv1a_offset:    .long   2166136261
+.L_uid_base:        .long   UID_BASE
+
+    .size _get_serial_desc, . - _get_serial_desc
+
+    .thumb_func
+    .type   _connect, %function
+_connect:
+    subs    r1, r0, #1
+    sbcs    r0, r1
+    lsls    r0, #15
+    ldr     r1, =USB_REGBASE
+    strh    r0, [r1, #0x18]      //USB->BCDR
+    bx      lr
+    .size   _connect, . - _connect
+
+
+    .thumb_func
+    .type   _setaddr, %function
+_setaddr:
+    ldr     r1, =USB_REGBASE
+    adds    r0, #0x80
+    strh    r0, [r1, #0x0C]     //USB->DADDR
+    bx      lr
+    .size   _setaddr, . - _setaddr
+
+    .thumb_func
+    .type   _reset, %function
+_reset:
+    ldr     r2, =USB_REGBASE
+    movs    r0, #0x01           //FRES
+    ldrh    r1, [r2]            //USB->CNTR
+    orrs    r1, r0
+    strh    r1, [r2]            // set FRES
+    bics    r1, r0
+    strh    r1, [r2]            // clr FRES
+    bx      lr
+    .size   _reset, . - _reset
+
+    .thumb_func
+    .type   _enable, %function
+_enable:
+    ldr     r1, =USB_REGBASE     //USB->CNTR
+    ldr     r2, =RCC_BASE        //RCC
+    movs    r3, #0x01
+    lsls    r3, #23             //USBEN or USBRST
+    tst     r0, r0
+    beq     .L_disable
+.L_enable:
+    ldr     r0, [r2, #0x38]
+    orrs    r0, r3
+    str     r0, [r2, #0x38]     //RCC->APB1ENR |= USBEN
+    ldr     r0, [r2, #0x28]
+    orrs    r0, r3
+    str     r0, [r2, #0x28]     //RCC->APB1RSTR |= USBRST
+    bics    r0, r3
+    str     r0, [r2, #0x28]     //RCC->APB1RSTR &= ~USBRST
+    movs    r0, #0xBE
+    lsls    r0, #0x08           // CTRM | ERRM | WKUPM | SUSPM | RESETM | SOFM
+    strh    r0, [r1]            //set USB->CNTR
+    bx      lr
+.L_disable:
+    ldr     r0, [r2, #0x38]
+    tst     r0, r3
+    beq     .L_enable_end       // usb is disabled
+    movs    r0, #0x00
+    strh    r0, [r1, #0x18]     //USB->BCDR disable USB I/O
+    ldr     r0, [r2, #0x28]
+    orrs    r0, r3
+    str     r0, [r2, #0x28]     //RCC->APB1RSTR |= USBRST
+    ldr     r0, [r2, #0x38]
+    bics    r0, r3
+    str     r0, [r2, #0x38]     //RCC->APB1ENR &= ~USBEN
+.L_enable_end:
+    bx      lr
+    .size   _enable, . - _enable
+
+    .thumb_func
+    .type   _ep_setstall, %function
+
+/*void ep_settall(uint8_t ep, bool stall)
+ * in  R0 <- endpoint number
+ * in  R1 <- 0 if unstall, !0 if stall
+ */
+_ep_setstall:
+    lsls    r2, r0, #28
+    lsrs    r2, #26
+    ldr     r3, =USB_EPBASE
+    adds    r3, r2          // epr -> r3
+    movs    r2, 0x30        // TX_STAT_MASK -> r2
+    cmp     r0, #80
+    blo     .L_eps_rx
+.L_eps_tx:
+    ldr     r0, =TGL_SET((EP_TX_STAT | EP_TX_DTOG) , EP_TX_STAL)  //stall TX
+    tst     r1, r1
+    bne     .L_eps_reg_set
+.L_eps_tx_unstall:
+    ldrh    r1, [r3]        // *epr -> r1
+    lsls    r1, #21
+    lsrs    r1, #29         // EPTTYPE | EPKIND mask only
+    ldr     r0, =TGL_SET((EP_TX_STAT | EP_TX_DTOG | EP_TX_SWBUF) , EP_TX_VAL) //unstall dblbulk or iso TX (VALID and clr DTOG_TX & SWBUF_TX)
+    cmp     r1, #0x01       // if doublebuffered bulk endpoint
+    beq     .L_eps_reg_set
+    cmp     r1, #0x04       // if isochronous endpoint
+    ldr     r0, =TGL_SET((EP_TX_STAT | EP_TX_DTOG) , EP_TX_NAK) // unstall other TX (NAKED + clr DTOG_TX)
+    b       .L_eps_reg_set
+.L_eps_rx:
+    lsls    r2, #8          // RX_STAT_MASK -> R2
+    ldr     r0,=TGL_SET((EP_RX_STAT | EP_RX_DTOG) , EP_RX_STAL)  //stall RX
+    tst     r1, r1
+    bne     .L_eps_reg_set
+.L_eps_rx_unstall:
+    ldrh    r1, [r3]        // *epr -> r1
+    lsls    r1, #21
+    lsrs    r1, #29         // EPTTYPE | EPKIND mask only
+    ldr     r0, =TGL_SET((EP_RX_STAT | EP_RX_DTOG | EP_RX_SWBUF) , (EP_RX_VAL | EP_RX_SWBUF)) //unstall dblbulk or iso (VALID. clr DTOG_RX set SWBUF_RX)
+    cmp     r1, #0x01       // if dblbulk
+    beq     .L_eps_reg_set
+    cmp     r1, #0x04       // if iso
+    beq     .L_eps_reg_set
+    ldr     r0, =TGL_SET((EP_RX_STAT | EP_RX_DTOG) , EP_RX_VAL) // unstall other RX (VALID + clr
+/* R0 - mask and toggle bits
+ * R2 - mask for STAT bits
+ * R3 - endpoint register pointer
+ */
+.L_eps_reg_set:
+    ldrh    r1, [r3]        // *epr -> r1
+    ands    r2, r1          // check if endpoint disabled
+    beq     .L_eps_exit     // do nothing
+    eors    r1, r0
+    lsrs    r0, #16
+    ands    r1, r0
+    strh    r1, [r3]
+.L_eps_exit:
+    bx      lr
+    .size   _ep_setstall, . - _ep_setstall
+
+
+    .thumb_func
+    .type   _ep_isstalled, %function
+/* bool ep_isstalled(uint8t ep) */
+_ep_isstalled:
+    ldr     r1, =USB_EPBASE
+    lsls    r2, r0, #28
+    lsrs    r2, #26
+    ldr     r1, [r1, r2]
+    lsls    r1, #17
+    cmp     r0, #0x80
+    bhs     .L_eis_check
+    lsls    r1, #8
+.L_eis_check:
+    lsrs    r1, r1, #28
+    subs    r1, #0x01
+    subs    r0, r1, #0x01
+    sbcs    r1, r1
+    rsbs    r0, r1, #0
+    bx      lr
+    .size  _ep_isstalled, . - _ep_isstalled
+
+
+    .thumb_func
+    .type       _ep_read, %function
+/* uint16_t _ep_read(uint8_t ep, void *buf, uint16_t blen)
+ * in  R0 <- endpoint
+ * in  R1 <- *buffer
+ * in  R2 <- length of the buffer
+ * out length of the recieved data -> R0
+ */
+_ep_read:
+    push    {r4, r5, lr}
+    ldr     r3, =USB_EPBASE
+    ldr     r4, =USB_PMABASE
+    lsls    r0, #28
+    lsrs    r0, #26
+    adds    r3, r0          // *EPR -> R3
+    lsls    r0, #1
+    adds    r4, r0          // *EPT -> R4
+    ldrh    r0, [r3]        // reading epr
+    lsls    r5, r0, #21
+    lsrs    r5, #29
+    cmp     r5, #0x04
+    beq     .L_epr_iso
+    cmp     r5, #0x01
+    bne     .L_epr_sngl
+.L_epr_dblbulk:
+//    ldr     r5, =0x00008F8F
+//    ldrh    r0, [r3]
+//    ands    r0, r5
+//    movs    r5, 0x40
+//    orrs    r0, r5
+//    strh    r0, [r3]
+//    ldrh    r0, [r3]
+    negs    r0, r0
+    lsrs    r0, #7          // ~SW_RX in CF
+    b       .L_epr_load_table
+.L_epr_iso:
+//    ldrh    r0, [r3]
+    lsrs    r0, #15     // DTOG_RX passsed to CF
+.L_epr_load_table:
+    ldrh    r0, [r4, #0]    // R0 rxaddr0
+    ldrh    r5, [r4, #2]    // R5 rxcnt0
+    bcs     .L_epr_prepare
+.L_epr_sngl:
+    ldrh    r0, [r4, #4]    // R0 rxaddr1 or rxaddr
+    ldrh    r5, [r4, #6]    // R5 rxcnt1 or rxcnt
+.L_epr_prepare:
+    ldr     r4, =USB_PMABASE
+    adds    r0, r4          // R0 now has a physical address
+    lsls    r5, #22
+    lsrs    r5, #22         // R5 bytes count
+    cmp     r2, r5
+    blo     .L_epr_read
+    mov     r2, r5          // if buffer is larger
+.L_epr_read:
+    cmp     r2, #1
+    blo     .L_epr_read_end
+    ldrh    r4, [r0]
+    strb    r4, [r1]
+    beq     .L_epr_read_end
+    lsrs    r4, #8
+    strb    r4, [r1, #1]
+    adds    r1, #2
+    adds    r0, #2
+    subs    r2, #2
+    bne     .L_epr_read
+.L_epr_read_end:
+    ldrh    r0, [r3]
+    lsls    r1, r0, #21
+    lsrs    r1, #29
+    cmp     r1, #0x04
+    beq     .L_epr_exit     // ep is iso. no needs to set it to valid
+    cmp     r1, #0x01
+    beq     .L_epr_exit     // ep is dblbulk. no needs to set it to valid
+    ldr     r2, =TGL_SET(EP_RX_STAT , EP_RX_VAL)  //0xBF8F3000
+    eors    r0, r2
+    lsrs    r2, #16
+    ands    r0, r2
+    strh    r0, [r3]        // set ep to VALID state
+.L_epr_exit:
+    mov     r0, r5
+    pop     {r4, r5, pc}
+    .size   _ep_read, . - _ep_read
+
+
+
+    .thumb_func
+    .type   _ep_write, %function
+/* uint16_t ep_write(uint8_t ep, void *buf, uint16_t blen)
+ *
+
+ */
+_ep_write:
+    push    {r2, r4, r5, lr}
+    ldr     r3, =USB_EPBASE
+    ldr     r4, =USB_PMABASE
+    lsls    r0, #28
+    lsrs    r0, #26
+    adds    r3, r0          // *EPR -> R3
+    lsls    r0, #1
+    adds    r4, r0          // *EPT -> R4
+    ldrh    r0, [r3]        // reading epr
+    lsls    r0, #21
+    lsrs    r0, #29
+    subs    r0, #0x04
+    beq     .L_epw_iso
+    adds    r0, #0x03
+    bne     .L_epw_sngl
+.L_epw_dblbulk:
+    ldrh    r0, [r3]
+    lsrs    r0, #15          // SW_TX in CF
+    bcc     .L_epw_sngl
+    b       .L_epw_settx1
+.L_epw_iso:
+    ldrh    r0, [r3]
+    lsrs    r0, #7          // DTOG_TX passsed to CF
+    bcs     .L_epw_sngl
+.L_epw_settx1:
+    adds    r4, #0x04
+.L_epw_sngl:
+    ldrh    r0, [r4, #0]    // R0 txaddr
+.L_epw_prepare:
+    strh    r2, [r4, #2]    // set txcount
+    ldr     r4, =USB_PMABASE
+    adds    r0, r4
+.L_epw_write:
+    cmp     r2, #0x01
+    blo     .L_epw_writeend
+    ldrb    r4, [r1]
+    beq     .L_epw_halfw
+    ldrb    r5, [r1, #1]
+    lsls    r5, #8
+    orrs    r4, r5
+    strh    r4, [r0]
+    adds    r1, #2
+    adds    r0, #2
+    subs    r2, #2
+    b       .L_epw_write
+.L_epw_halfw:
+    strh    r4, [r0]
+.L_epw_writeend:
+    ldrh    r0, [r3]
+    lsls    r1, r0, #21
+    lsrs    r1, #29
+    subs    r1, #0x04
+    beq     .L_epw_exit     // ep is iso. no needs to change states
+    ldr     r2, =TGL_SET(EP_TX_STAT , EP_TX_VAL) //0x8FBF0030
+    adds    r1, #0x03
+    bne     .L_epw_setstate
+// ep is dblbulk. needs to switch SW_TX
+    movs    r2, 0x01
+    lsls    r2, #14
+    orrs    r0, r2
+    ldr     r2, =TGL_SET(EP_TX_SWBUF, 0 ) //0xCF8F0000
+
+.L_epw_setstate:
+    eors    r0, r2
+    lsrs    r2, #16
+    ands    r0, r2
+    strh    r0, [r3]
+.L_epw_exit:
+    pop     {r0, r4, r5, pc}
+    .size   _ep_write, .- _ep_write
+
+
+
+/* internal function */
+/* requester size passed in R2 */
+/* result returns in R0 CF=1 if OK*/
+
+_get_next_pma:
+    push    {r1, r3, r4, lr}
+    movs    r1, #16
+    movs    r3, #1
+    lsls    r3, #10         //R3 MAX_PMA_SIZE
+    ldr     r0, =USB_PMABASE
+.L_gnp_chkaddr:
+    ldrh    r4, [r0, #0]    //txaddr
+    tst     r4, r4
+    beq     .L_gnp_nxtaddr
+    cmp     r3, r4
+    blo     .L_gnp_nxtaddr
+    mov     r3, r4
+.L_gnp_nxtaddr:
+    adds    r0, #4
+    subs    r1, #1
+    bne     .L_gnp_chkaddr
+    subs    r0, r3, r2
+    blo     .L_gnp_exit
+    cmp     r0, #0x40       //check for the pma table overlap
+.L_gnp_exit:
+    pop     {r1, r3, r4, pc}
+
+
+
+    .size   _get_next_pma, . - _get_next_pma
+
+    .thumb_func
+    .type   _ep_config, %function
+/* bool ep_config(uint8_t ep, uint8_t eptype, uint16_t epsize)
+ * R0 <- ep
+ * R1 <- eptype
+ * R2 <- epsize
+ * result -> R0
+ */
+_ep_config:
+    push    {r4, r5, lr}
+    movs    r3, 0x01
+    ands    r3, r2
+    adds    r2, r3      //R2 -> halfword aligned epsize
+    movs    r3, #0x00   //BULK
+    cmp     r1, #0x02   // is eptype bulk ?
+    beq     .L_epc_settype
+    movs    r3, #0x01   //DBLBULK
+    cmp     r1, #0x06
+    beq     .L_epc_settype
+    movs    r3, #0x02   //CONTROL
+    cmp     r1, #0x00
+    beq     .L_epc_settype
+    movs    r3, #0x04   //ISO
+    cmp     r1, #0x01
+    beq     .L_epc_settype
+    movs    r3, #0x06   //INTERRUPT
+.L_epc_settype:
+    lsls    r3, #8
+    lsls    r4, r0, #28
+    lsrs    r4, #28
+    orrs    r3, r4
+    lsls    r4, #2
+    ldr     r5, =USB_EPBASE
+    strh    r3, [r5, r4]    //setup EPTYPE EPKIND EPADDR
+    cmp     r1, #0x00       // is a control ep ?
+    beq     .L_epc_setuptx
+    cmp     r0, #0x80
+    blo     .L_epc_setuprx
+.L_epc_setuptx:
+    ldr     r5, =USB_PMABASE
+    lsls    r4, #1
+    adds    r5, r4
+    bl      _get_next_pma
+    bcc     .L_epc_fail
+    strh    r0, [r5, #0]    //store txaddr or txaddr0
+    movs    r0, #0x00
+    strh    r0, [r5, #2]    //store txcnt
+    cmp     r1, #0x06       // is DBLBULK
+    beq     .L_epc_txdbl
+    ldr     r3, =TGL_SET((EP_TX_STAT | EP_TX_DTOG) , EP_TX_NAK) // 0x8FFF0020 //mask ep to naked , clr DTOG_TX
+    cmp     r1, #0x01       // is ISO
+    bne     .L_epc_txsetstate   //
+.L_epc_txdbl:
+    ldr     r3, =TGL_SET((EP_TX_STAT | EP_TX_DTOG | EP_TX_SWBUF) , EP_TX_VAL) //xCFFF0030 mask to valid if dblbuffered or iso clr DTOG_TX & SWBUF_TX
+    bl      _get_next_pma
+    bcc     .L_epc_fail
+    strh    r0, [r5, #4]    //store txaddr1
+    movs    r0, #0x00
+    strh    r0, [r5, #6]    //store txcnt
+.L_epc_txsetstate:
+    ldr     r5, =USB_EPBASE
+    lsrs    r4, #1
+    ldrh    r0, [r5, r4]
+    eors    r0, r3
+    lsrs    r3, #16
+    ands    r0, r3
+    strh    r0, [r5, r4]
+    cmp     r1, #0x00       //is a control ep ?
+    bne     .L_epc_exit
+.L_epc_setuprx:
+    mov     r3, r2
+    cmp     r2, #62
+    bls     .L_epc_rxbb
+    movs    r3, #0x1F
+    ands    r3, r2
+    bne     .L_epc_rxaa
+    subs    r2, #0x20
+.L_epc_rxaa:
+    bics    r2, r3
+    lsrs    r3, r2, #4
+    adds    r3, #0x40
+    adds    r2, #0x20
+.L_epc_rxbb:
+    lsls    r3, #9
+    ldr     r5, =USB_PMABASE
+    lsls    r4, #1
+    adds    r5, r4
+    cmp     r1, 0x06    //if dblbulk
+    beq     .L_epc_rxdbl
+    cmp     r1, 0x01    // iso
+    bne     .L_epc_rxsngl
+.L_epc_rxdbl:
+    bl      _get_next_pma
+    bcc     .L_epc_fail
+    strh    r0, [r5, #0]    //store rxaddr0
+    strh    r3, [r5, #2]    //store rxcnt0
+    bl      _get_next_pma
+    bcc     .L_epc_fail
+    strh    r0, [r5, #4]    //store rxaddr1
+    strh    r3, [r5, #6]    //store rxcnt1
+    ldr     r3, =TGL_SET((EP_RX_STAT | EP_RX_DTOG | EP_RX_SWBUF) , (EP_RX_VAL | EP_RX_SWBUF)) //0xFFCF3040
+    b       .L_epc_rxsetstate
+.L_epc_rxsngl:
+    bl      _get_next_pma
+    bcc     .L_epc_fail
+    strh    r0, [r5, #4]    //store rxaddr1 or rxaddr
+    strh    r3, [r5, #6]    //store rxcnt1 or rxcnt
+    ldr     r3, =TGL_SET((EP_RX_STAT | EP_RX_DTOG) , EP_RX_VAL) //0xFF8F3000
+.L_epc_rxsetstate:
+    ldr     r5, =USB_EPBASE
+    lsrs    r4, #1
+    ldrh    r0, [r5, r4]
+    eors    r0, r3
+    lsrs    r3, #16
+    ands    r0, r3
+    strh    r0, [r5, r4]
+.L_epc_exit:
+    movs    r0, #0x01
+    pop     {r4, r5, pc}
+.L_epc_fail:
+    movs    r0, #0x00
+    pop     {r4, r5, pc}
+
+    .size   _ep_config, . - _ep_config
+
+    .thumb_func
+    .type   _ep_deconfig, %function
+
+
+/* void ep_deconfig( uint8_t ep)
+ * R0 <- ep
+ */
+_ep_deconfig:
+    lsls    r1, r0, #28
+    lsrs    r1, #26
+    ldr     r2, =USB_EPBASE
+    ldr     r3, =USB_PMABASE
+    adds    r2, r1
+    lsls    r1, #1
+    adds    r3, r1
+/* clearing endpoint register */
+    ldr     r1, =EP_NOTOG
+    ldrh    r0, [r2]
+    bics    r0, r1
+    strh    r0, [r2]
+/* clearing PMA data */
+    movs    r0, #0x00
+    strh    r0, [r3, #0x00]
+    strh    r0, [r3, #0x02]
+    strh    r0, [r3, #0x04]
+    strh    r0, [r3, #0x06]
+    bx      lr
+
+    .size   _ep_deconfig, . - _ep_config
+
+
+
+
+#define ISTRSHIFT   8
+#define ISTRBIT(bit) ((1 << bit) >> ISTRSHIFT)
+
+
+    .thumb_func
+    .type     _evt_poll, %function
+/*void evt_poll(usbd_device *dev, usbd_evt_callback callback)*/
+_evt_poll:
+    push    {r0, r1, r4, r5}
+    ldr     r3, =USB_REGBASE
+    ldrh    r0, [r3, #4]        //USB->ISTR -> R2
+/* ep_index -> R2 */
+    movs    r2, 0x07
+    ands    r2, r0
+/* checking USB->ISTR for events */
+    lsls    r0, #17             //CTRM -> CF
+    bcs     .L_ep_ctrm
+    lsls    r0, #2              //ERRM -> CF
+    bcs     .L_ep_errm
+    lsls    r0, #1              //WKUPM -> CF
+    bcs     .L_ep_wkupm
+    lsls    r0, #1              //SUSPM -> CF
+    bcs     .L_ep_suspm
+    lsls    r0, #1              //RESETM -> CF
+    bcs     .L_ep_resetm
+    lsls    r0, #1              //SOFM -> CF
+    bcs     .L_ep_sofm
+    lsls    r0, #1
+    bcs     .L_ep_esofm
+    /* exit with no callback */
+    pop     {r0, r1, r4 , r5}
+    bx      lr
+
+.L_ep_ctrm:
+    movs    r3, #0x00
+    ldr     r0,=#USB_EPBASE
+    lsrs    r0, #2
+    adds    r0, r2
+    lsls    r0, #2              // R0 ep register address
+    ldrh    r4, [r0]            //R4 *USB->EPx
+    lsrs    r5, r4, #8         // CTR_TX -> CF
+    bcc     .L_ep_ctr_rx
+/* CTR_TX event */
+    movs    r1, #usbd_evt_eptx
+    movs    r5, #0x80
+    adds    r2, #0x80           // set endpoint tx
+    b       .L_ep_clr_ctr
+.L_ep_ctr_rx:
+/* CTR_RX  RX or SETUP */
+    movs    r1, #usbd_evt_epsetup
+    lsls    r5, r4, #21             //SETUP -> CF
+    bcs     .L_ep_ctr_evt
+    movs    r1, #usbd_evt_eprx
+    lsrs    r5, #29                 //EP_TYPE | EP_KIND -> R5 LSB
+    cmp     r5, #0x01               //if dblbuf bulk
+    bne     .L_ep_ctr_evt
+/* if ep is dblbulk RX */
+    movs    r3, #EP_RX_SWBUF
+.L_ep_ctr_evt:
+/* clear CTR_RX */
+    movs    r5, #0x80
+    lsls    r5, #0x08
+.L_ep_clr_ctr:
+    bics    r4, r5
+    ldr     r5, =EP_NOTOG
+    ands    r4, r5
+    orrs    r4, r3
+    strh    r4, [r0]            // clr CTR flag
+    b       .L_ep_callback
+
+.L_ep_errm:
+    movs    r1, #usbd_evt_error
+    movs    r4, #ISTRBIT(13)
+    b      .L_ep_clristr
+
+.L_ep_sofm:
+    movs    r1, #usbd_evt_sof
+    movs    r4, #ISTRBIT(9)
+    b       .L_ep_clristr
+
+.L_ep_esofm:
+    movs    r1, #usbd_evt_esof
+    movs    r4, #ISTRBIT(8)
+    b       .L_ep_clristr
+
+.L_ep_wkupm:
+    ldrh    r1, [r3, #0]            //R1 USB->CNTR
+    movs    r5, #0x08
+    bics    r1, r5                  //clr FSUSP
+    strh    r1, [r3, #0]            //USB->CNTR R2
+    movs    r1, #usbd_evt_wkup
+    movs    r4, #ISTRBIT(12)
+    b       .L_ep_clristr
+
+.L_ep_suspm:
+    ldrh    r1, [r3, #0]            //R1 USB->CNTR
+    movs    r5, #0x08
+    orrs    r1, r5                  //set FSUSP
+    strh    r1, [r3, #0]            //USB->CNTR R2
+    movs    r1, #usbd_evt_susp
+    movs    r4, #ISTRBIT(11)
+    b       .L_ep_clristr
+
+/* do reset routine */
+.L_ep_resetm:
+    movs    r1, #7
+    ldr     r2, =USB_EPBASE
+    ldr     r0, =USB_PMABASE
+    ldr     r5, =EP_NOTOG
+.L_ep_reset_loop:
+    ldrh    r4, [r2]
+    bics    r4, r5
+    strh    r4, [r2]
+    movs    r4, #0
+    strh    r4, [r0, #0]
+    strh    r4, [r0, #2]
+    strh    r4, [r0, #4]
+    strh    r4, [r0, #6]
+    adds    r2, #4
+    adds    r0, #8
+    subs    r1, #1
+    bpl     .L_ep_reset_loop
+    movs    r2, #0x00
+    strh    r2, [r3, #0x10]     // 0 -> USB->BTABLE
+    movs    r1, #usbd_evt_reset
+    movs    r4, #ISTRBIT(10)
+.L_ep_clristr:
+    lsls    r4, #ISTRSHIFT
+    ldrh    r0, [r3, #4]
+    bics    r0, r4
+    strh    r0, [r3, #4]
+.L_ep_callback:
+    pop     {r0, r3, r4, r5 }
+    bx      r3
+
+    .size   _evt_poll, . - _evt_poll
+
+
+
+
+    .pool
+
+   .end

+ 414 - 0
src/usbd_core.c

@@ -0,0 +1,414 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdint.h>
+#include <string.h>
+#include "usb.h"
+
+#define _MIN(a, b) ((a) < (b)) ? (a) : (b)
+
+static void usbd_process_ep0 (usbd_device *dev, uint8_t event, uint8_t ep);
+
+/** \brief Resets USB device state
+ * \param dev pointer to usb device
+ * \return none
+ */
+static void usbd_process_reset(usbd_device *dev) {
+    dev->status.device_state = usbd_state_default;
+    dev->status.control_state = usbd_ctl_idle;
+    dev->status.device_cfg = 0;
+    dev->driver->ep_config(0, USB_EPTYPE_CONTROL, dev->status.ep0size);
+    dev->endpoint[0] = usbd_process_ep0;
+    dev->driver->setaddr(0);
+}
+
+/** \brief Callback that sets USB device address
+ * \param dev pointer to usb device
+ * \param req pointer to usb control request data
+ * \return none
+ */
+static void usbd_set_address (usbd_device *dev, usbd_ctlreq *req) {
+    dev->driver->setaddr(req->wValue);
+    dev->status.device_state = (req->wValue) ? usbd_state_addressed : usbd_state_default;
+}
+
+/** \brief Callback processing after STATUS-IN or STATUS-OUT stage completed
+ * \param dev pointer to the usb device
+ * \return none
+ */
+static void usbd_process_callback (usbd_device *dev) {
+    if (dev->complete_callback) {
+//        dev->complete_callback(dev, &(dev->req));
+        dev->complete_callback(dev, dev->status.data_buf);
+        dev->complete_callback = 0;
+    }
+}
+
+static bool usbd_configure(usbd_device *dev, uint8_t config) {
+    if (0 == config) {
+        /* de-configuring endpoints except EP0 */
+        for (int i = 1; i < 8; i++) {
+            dev->driver->ep_deconfig(i);
+        }
+        if (dev->config_callback) {
+            dev->config_callback(dev, config);
+        }
+        dev->status.device_cfg = 0;
+        dev->status.device_state = usbd_state_addressed;
+        return true;
+    } else {
+        if (dev->config_callback) {
+            if (dev->config_callback(dev, config)) {
+                dev->status.device_cfg = config;
+                dev->status.device_state = usbd_state_configured;
+                return true;
+            }
+        }
+    }
+    return false;
+}
+
+
+/** \brief Processing standard device control request
+ * \param dev pointer to usb device
+ * \param req pointer to control request
+ * \return TRUE if request is handled
+ */
+static bool usbd_process_devrq (usbd_device *dev, usbd_ctlreq *req) {
+    switch (req->bRequest) {
+    case USB_STD_CLEAR_FEATURE:
+        /* not yet supported */
+        break;
+
+    case USB_STD_GET_CONFIG:
+        req->data[0] = dev->status.device_cfg;
+        return true;
+
+    case USB_STD_GET_DESCRIPTOR:
+        if (req->wValue == ((USB_DTYPE_STRING << 8) | INTSERIALNO_DESCRIPTOR )) {
+            dev->status.data_count = dev->driver->get_serialno_desc(req->data);
+            return true;
+        } else {
+            if (dev->descriptor_callback) {
+                return dev->descriptor_callback(req, &(dev->status.data_ptr), &(dev->status.data_count));
+            }
+        }
+        break;
+    case USB_STD_GET_STATUS:
+        req->data[0] = 0;
+        req->data[1] = 0;
+        return true;
+    case USB_STD_SET_ADDRESS:
+        dev->complete_callback = usbd_set_address;
+        return true;
+    case USB_STD_SET_CONFIG:
+        return usbd_configure(dev, req->wValue);
+    case USB_STD_SET_DESCRIPTOR:
+        /* should be externally handled */
+        break;
+
+    case USB_STD_SET_FEATURE:
+        /* not yet supported */
+        break;
+
+    default:
+        break;
+    }
+    return false;
+}
+
+/** \brief Processing standard interface control request
+ * \param dev pointer to usb device
+ * \param req pointer to control request
+ * \return TRUE if request is handled
+ */
+static bool usbd_process_intrq(usbd_device *dev, usbd_ctlreq *req) {
+    switch (req->bRequest) {
+    case USB_STD_GET_STATUS:
+        req->data[0] = 0;
+        req->data[1] = 0;
+        return true;
+    default:
+        break;
+    }
+    return false;
+}
+
+/** \brief Processing standard endpoint control request
+ * \param dev pointer to usb device
+ * \param req pointer to control request
+ * \return TRUE if request is handled
+ */
+static bool usbd_process_eptrq(usbd_device *dev, usbd_ctlreq *req) {
+    switch (req->bRequest) {
+    case USB_STD_SET_FEATURE:
+        dev->driver->ep_setstall(req->wIndex, 1);
+        return true;
+    case USB_STD_CLEAR_FEATURE:
+        dev->driver->ep_setstall(req->wIndex, 0);
+        return true;
+    case USB_STD_GET_STATUS:
+        req->data[0] = dev->driver->ep_isstalled(req->wIndex) ? 1 : 0;
+        req->data[1] = 0;
+        return true;
+    default:
+        return false;
+    }
+}
+
+/** \brief Processing control request
+ * \param dev pointer to usb device
+ * \param req pointer to usb control request
+ * \return TRUE if request is handled
+ */
+static bool usbd_process_request(usbd_device *dev, usbd_ctlreq *req) {
+    /* processing control request by callback */
+    if (dev->control_callback) {
+//        if (dev->control_callback(dev, &(dev->req), &(dev->complete_callback))) {
+        if (dev->control_callback(dev, req, &(dev->complete_callback))) {
+            return true;
+        }
+    }
+    /* continuing standard USB requests */
+    switch (req->bmRequestType & (USB_REQ_TYPE | USB_REQ_RECIPIENT)) {
+    case USB_REQ_STANDARD | USB_REQ_DEVICE:
+        return usbd_process_devrq(dev, req);
+    case USB_REQ_STANDARD | USB_REQ_INTERFACE:
+        return usbd_process_intrq(dev, req);
+    case USB_REQ_STANDARD | USB_REQ_ENDPOINT:
+        return usbd_process_eptrq(dev, req);
+    default:
+        break;
+    }
+    return false;
+}
+
+
+/** \brief Control endpoint stall (STALL PID)
+ * \param dev pointer to usb device
+ * \param ep endpoint number
+ */
+static void usbd_stall_pid(usbd_device *dev, uint8_t ep) {
+    dev->driver->ep_setstall(ep & 0x7F, 1);
+    dev->driver->ep_setstall(ep | 0x80, 1);
+    dev->status.control_state = usbd_ctl_idle;
+}
+
+
+/** \brief Control endpoint TX event processing
+ * \param dev pointer to usb device
+ * \param ep endpoint number
+ */
+static void usbd_process_eptx(usbd_device *dev, uint8_t ep) {
+    uint16_t _t;
+    switch (dev->status.control_state) {
+    case usbd_ctl_ztxdata:
+    case usbd_ctl_txdata:
+        _t = _MIN(dev->status.data_count, dev->status.ep0size);
+        dev->driver->ep_write(ep, dev->status.data_ptr, _t);
+        dev->status.data_ptr += _t;
+        dev->status.data_count -= _t;
+        /* if all data is not sent */
+        if (0 != dev->status.data_count) break;
+        /* if last packet has a EP0 size and host awaiting for the more data ZLP should be sent*/
+        /* if ZLP required state is unchanged */
+        /* next TX event sends ZLP */
+        if ((dev->status.control_state == usbd_ctl_ztxdata) && (_t == dev->status.ep0size)) break;
+        dev->status.control_state = usbd_ctl_lastdata; /* no ZLP required */
+        break;
+    case usbd_ctl_lastdata:
+        dev->status.control_state = usbd_ctl_statusout;
+        break;
+    case usbd_ctl_statusin:
+        dev->status.control_state = usbd_ctl_idle;
+        return usbd_process_callback(dev);
+    default:
+        /* unexpected TX completion */
+        /* just skipping it */
+        break;
+    }
+}
+
+
+/** \brief Control endpoint RX event processing
+ * \param dev pointer to usb device
+ * \param ep endpoint number
+ */
+static void usbd_process_eprx(usbd_device *dev, uint8_t ep) {
+    uint16_t _t;
+    usbd_ctlreq *const req = dev->status.data_buf;
+    switch (dev->status.control_state) {
+    case usbd_ctl_idle:
+        /* read SETUP packet, stall if incorrect packet length */
+        if (0x08 !=  dev->driver->ep_read(ep, req, dev->status.data_maxsize)) {
+            return usbd_stall_pid(dev, ep);
+        }
+        dev->status.data_ptr = req->data;
+        dev->status.data_count = req->wLength;
+        /* processing request if no payload data*/
+        if ((req->bmRequestType & USB_REQ_DEVTOHOST) || (0 == req->wLength)) goto do_process_request;
+        /* checking available memory for DATA OUT stage */
+        if (req->wLength > dev->status.data_maxsize) {
+            return usbd_stall_pid(dev, ep);
+        }
+        /* continue DATA OUT stage */
+        dev->status.control_state = usbd_ctl_rxdata;
+        break;
+    case usbd_ctl_rxdata:
+        /*receive DATA OUT packet(s) */
+        _t = dev->driver->ep_read(ep, dev->status.data_ptr, dev->status.data_count);
+        if (dev->status.data_count < _t) {
+        /* if received packet is large than expected */
+        /* Must be error. Let's drop this request */
+            return usbd_stall_pid(dev, ep);
+        } else if (dev->status.data_count != _t) {
+        /* if all data payload was not received yet */
+            dev->status.data_count -= _t;
+            dev->status.data_ptr += _t;
+            break;
+        }
+do_process_request:
+        /* usb request received */
+        /* let's handle it */
+        /* preparing */
+        ep |= 0x80;
+        dev->status.data_ptr = req->data;
+        dev->status.data_count = /*dev->req.wLength*/ dev->status.data_maxsize;
+        if (usbd_process_request(dev, req)) {
+            if (req->bmRequestType & USB_REQ_DEVTOHOST) {
+                /* return data from function */
+                dev->status.control_state = usbd_ctl_txdata;
+                if (dev->status.data_count >= req->wLength) {
+                    dev->status.data_count = req->wLength;
+                    dev->status.control_state = usbd_ctl_txdata;
+                } else {
+                    /* DATA IN packet smaller than requested */
+                    /* ZLP maybe wanted */
+                    dev->status.control_state = usbd_ctl_ztxdata;
+                }
+                return usbd_process_eptx(dev, ep);
+            } else {
+                /* confirming by ZLP in STATUS_IN stage */
+                dev->status.control_state = usbd_ctl_statusin;
+                dev->driver->ep_write(ep, 0, 0);
+            }
+        } else {
+            /* unsupported function. stall TX STATUS_IN stage */
+            /* Sends STALL PID */
+            return usbd_stall_pid(dev, ep);
+        }
+        break;
+    case usbd_ctl_statusout:
+        /* reading STATUS OUT data to buffer */
+        dev->driver->ep_read(ep, dev->status.data_ptr, dev->status.data_maxsize);
+        dev->status.control_state = usbd_ctl_idle;
+        return usbd_process_callback(dev);
+    default:
+        /* unexpected RX packet */
+        return usbd_stall_pid(dev, ep);
+    }
+}
+
+/** \brief Control endpoint 0 event processing callback
+ * \param dev usb device
+ * \param event endpoint event
+ */
+static void usbd_process_ep0 (usbd_device *dev, uint8_t event, uint8_t ep) {
+    switch (event) {
+    case usbd_evt_epsetup:
+        /* force switch to setup state */
+        dev->status.control_state = usbd_ctl_idle;
+        dev->complete_callback = 0;
+    case usbd_evt_eprx:
+        return usbd_process_eprx(dev, ep);
+    case usbd_evt_eptx:
+        return usbd_process_eptx(dev, ep);
+    default:
+        break;
+    }
+}
+
+
+/** \brief General event processing callback
+ * \param dev usb device
+ * \param evt usb event
+ * \param ep active endpoint
+ */
+static void usbd_process_evt(usbd_device *dev, uint8_t evt, uint8_t ep) {
+    switch (evt) {
+    case usbd_evt_reset:
+        usbd_process_reset(dev);
+        break;
+    case usbd_evt_eprx:
+    case usbd_evt_eptx:
+    case usbd_evt_epsetup:
+        if (dev->endpoint[ep & 0x07]) dev->endpoint[ep & 0x07](dev, evt, ep);
+        break;
+    default:
+        break;
+    }
+    if (dev->events[evt]) dev->events[evt](dev, evt, ep);
+}
+
+
+
+void usbd_init(usbd_device *dev, const struct usbd_driver *drv, const uint8_t ep0size, void *buffer, const uint16_t bsize) {
+    memset(dev, 0, sizeof(struct usbd_device));
+    dev->driver = drv;
+    dev->status.ep0size = ep0size;
+    dev->status.data_ptr = buffer;
+    dev->status.data_buf = buffer;
+    dev->status.data_maxsize = bsize - offsetof(struct usbd_ctlreq, data);
+}
+
+void usbd_poll(usbd_device *dev) {
+    return dev->driver->poll(dev, usbd_process_evt);
+}
+
+void usbd_control(usbd_device *dev, enum usbd_commands cmd) {
+    switch (cmd) {
+    case usbd_cmd_enable:
+        dev->driver->enable(true);
+        dev->status.device_state = usbd_state_disconnected;
+        break;
+    case usbd_cmd_disable:
+        dev->driver->enable(false);
+        dev->status.device_state = usbd_state_disabled;
+        break;
+    case usbd_cmd_connect:
+        dev->driver->connect(true);
+        break;
+    case usbd_cmd_disconnect:
+        dev->driver->connect(false);
+        dev->status.device_state = usbd_state_disconnected;
+        break;
+    case usbd_cmd_reset:
+        dev->driver->reset();
+        break;
+    default:
+        break;
+    }
+}
+
+
+/*
+const struct usbd_api usbd = {
+    usbd_init,
+    usbd_poll,
+};
+
+*/
+
+

+ 40 - 0
usb.h

@@ -0,0 +1,40 @@
+/* This file is the part of the LUS32 project
+ *
+ * Copyright ©2016 Dmitry Filimonchuk <dmitrystu[at]gmail[dot]com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+#ifndef _USB_H_
+#define _USB_H_
+#if defined(__cplusplus)
+    extern "C" {
+#endif
+
+
+#include "inc\usbd_core.h"
+#include "inc\usb_std.h"
+
+
+#if defined(STM32L0)
+    extern const struct usbd_driver usb_stml0a;
+    #define usb_hw_driver usb_stml0a
+#else
+    #error "No supported MCU family selected"
+#endif
+
+
+
+#if defined (__cplusplus)
+    }
+#endif
+#endif //_USB_H_