start with USB CDC echo example

this is the Atmel START USB CDC Echo example project for the
SAM E54 Xplained Pro board using an Atmel ATSAME54P20A
microcontroller.
Atmel START information:
- Version: 1.4.1810 (Dec 18, 2018, 5:52 AM GMT+1)
- Server: 1.4.93
- Content version: 1.0.1340

This will serve as basis for the sysmoOCTSIM project

A jenkins contrib script has also been added to the
osmo-ccid-firmware project to build the sysmoOCTSIM firmware

Change-Id: I356de75e7b730d63fb819248e71d36f785932199
diff --git a/sysmoOCTSIM/hal/include/hpl_usb_host.h b/sysmoOCTSIM/hal/include/hpl_usb_host.h
new file mode 100644
index 0000000..635950b
--- /dev/null
+++ b/sysmoOCTSIM/hal/include/hpl_usb_host.h
@@ -0,0 +1,618 @@
+/**
+ * \file
+ *
+ * \brief SAM USB host HPL
+ *
+ * Copyright (c) 2016-2018 Microchip Technology Inc. and its subsidiaries.
+ *
+ * \asf_license_start
+ *
+ * \page License
+ *
+ * Subject to your compliance with these terms, you may use Microchip
+ * software and any derivatives exclusively with Microchip products.
+ * It is your responsibility to comply with third party license terms applicable
+ * to your use of third party software (including open source software) that
+ * may accompany Microchip software.
+ *
+ * THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES,
+ * WHETHER EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE,
+ * INCLUDING ANY IMPLIED WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY,
+ * AND FITNESS FOR A PARTICULAR PURPOSE. IN NO EVENT WILL MICROCHIP BE
+ * LIABLE FOR ANY INDIRECT, SPECIAL, PUNITIVE, INCIDENTAL OR CONSEQUENTIAL
+ * LOSS, DAMAGE, COST OR EXPENSE OF ANY KIND WHATSOEVER RELATED TO THE
+ * SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP HAS BEEN ADVISED OF THE
+ * POSSIBILITY OR THE DAMAGES ARE FORESEEABLE.  TO THE FULLEST EXTENT
+ * ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS IN ANY WAY
+ * RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF ANY,
+ * THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE.
+ *
+ * \asf_license_stop
+ *
+ */
+
+#ifndef _HPL_USB_HOST_H_INCLUDED
+#define _HPL_USB_HOST_H_INCLUDED
+
+#include <hpl_usb.h>
+#include <hpl_irq.h>
+#include "hpl_usb_config.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/** Driver version */
+#define USB_H_VERSION 0x00000001
+
+/**
+ * @brief      USB HCD callback types
+ */
+enum usb_h_cb_type {
+	/** SOF generated */
+	USB_H_CB_SOF,
+	/** Root Hub change detected */
+	USB_H_CB_ROOTHUB_CHANGE,
+	/** Number of USB HCD callback types */
+	USB_H_CB_N
+};
+
+/**
+ * @brief      USB HCD resource strategy
+ */
+enum usb_h_rsc_strategy {
+	/** Normal resource allocation, e.g.,
+	 *  1 bank for interrupt endpoint,
+	 *  2 bank for bulk endpoint and normal iso endpoint,
+	 *  3 bank for iso high bandwidth endpoint.
+	 */
+	USB_H_RSC_NORMAL = false,
+	/** Minimal resource allocation, e.g., only 1 bank for bulk endpoints */
+	USB_H_RSC_MINIMAL = true
+};
+
+/**
+ * @brief      USB HCD pipe states
+ */
+enum usb_h_pipe_state {
+	/** Pipe is free to allocate */
+	USB_H_PIPE_S_FREE = 0x00,
+	/** Pipe is in configuration */
+	USB_H_PIPE_S_CFG = 0x01,
+	/** Pipe is allocated and idle */
+	USB_H_PIPE_S_IDLE = 0x02,
+	/** Pipe in control setup stage */
+	USB_H_PIPE_S_SETUP = 0x03,
+	/** Pipe in data IN stage */
+	USB_H_PIPE_S_DATI = 0x05,
+	/** Pipe in data OUT stage */
+	USB_H_PIPE_S_DATO = 0x06,
+	/** Pipe in data IN ZLP stage */
+	USB_H_PIPE_S_ZLPI = 0x07,
+	/** Pipe in data OUT ZLP stage */
+	USB_H_PIPE_S_ZLPO = 0x08,
+	/** Pipe in control status IN stage */
+	USB_H_PIPE_S_STATI = 0x09,
+	/** Pipe in control status OUT stage */
+	USB_H_PIPE_S_STATO = 0x0A,
+	/** Taken by physical pipe (in process) */
+	USB_H_PIPE_S_TAKEN = 0x10
+};
+
+/**
+ * @brief      USB HCD status code
+ */
+enum usb_h_status {
+	/** OK */
+	USB_H_OK = ERR_NONE,
+	/** Busy */
+	USB_H_BUSY = ERR_BUSY,
+	/** Denied */
+	USB_H_DENIED = ERR_DENIED,
+	/** Timeout */
+	USB_H_TIMEOUT = ERR_TIMEOUT,
+	/** Abort */
+	USB_H_ABORT = ERR_ABORTED,
+	/** Stall protocol */
+	USB_H_STALL = ERR_PROTOCOL,
+	/** Transfer reset by pipe re-configure */
+	USB_H_RESET = ERR_REQ_FLUSHED,
+	/** Argument error */
+	USB_H_ERR_ARG = ERR_INVALID_ARG,
+	/** Operation not supported */
+	USB_H_ERR_UNSP_OP = ERR_UNSUPPORTED_OP,
+	/** No resource */
+	USB_H_ERR_NO_RSC = ERR_NO_RESOURCE,
+	/** Not initialized */
+	USB_H_ERR_NOT_INIT = ERR_NOT_INITIALIZED,
+	/** Some general error */
+	USB_H_ERR = ERR_IO
+};
+
+/** Forward declare for pipe structure */
+struct usb_h_pipe;
+
+/** Forward declare for driver descriptor structure */
+struct usb_h_desc;
+
+/**
+ * \brief Prototyping USB HCD callback of SOF
+ */
+typedef void (*usb_h_cb_sof_t)(struct usb_h_desc *drv);
+
+/**
+ * \brief Prototyping USB HCD callback of root hub changing.
+ * According to the bitmap size, max port number is 31.
+ */
+typedef void (*usb_h_cb_roothub_t)(struct usb_h_desc *drv, uint8_t port, uint8_t ftr);
+
+/**
+ * Prototyping USB HCD callback of pipe transfer done.
+ * For control pipe, it's forced to call even if there is no transfer
+ * in progress, since the pipe size could be changed at run time.
+ */
+typedef void (*usb_h_pipe_cb_xfer_t)(struct usb_h_pipe *pipe);
+
+/** Access to max packet size of a pipe */
+#define usb_h_pipe_max_pkt_size(p) (p->max_pkt_size)
+
+/** Access to device address of a pipe */
+#define usb_h_pipe_dev_addr(p) (p->dev)
+
+/** Access to endpoint address of a pipe */
+#define usb_h_pipe_ep_addr(p) (p->ep)
+
+/** Access to state of a pipe */
+#define usb_h_pipe_state(p) (p->x.general.state)
+
+/** Access to status of a pipe */
+#define usb_h_pipe_status(p) (p->x.general.status)
+
+/**
+ * @brief      USB Host Controller device structure
+ */
+struct usb_h_desc {
+	/** Pointer to hardware base */
+	void *hw;
+	/** Pointer to private data for Host Controller driver */
+	void *prvt;
+	/** Interrupt handling descriptor */
+	struct _irq_descriptor irq;
+	/** Callback of SOF */
+	usb_h_cb_sof_t sof_cb;
+	/** Callback of root hub change */
+	usb_h_cb_roothub_t rh_cb;
+#if CONF_USB_H_INST_OWNER_SP
+	/** Extension for the driver owner (upper layer user) */
+	void *owner;
+#endif
+};
+
+/**
+ * @brief      Transfer descriptor for control transfer
+ *
+ * Timing in USB 2.0 spec.:
+ * - 9.2.6.1 : USB sets an upper limit of 5 seconds as the upper limit for any
+ *             command to be processed.
+ * - 9.2.6.3 : if a device receives a SetAddress() request, the device must be
+ *             able to complete processing of the request and be able to
+ *             successfully complete the Status stage of the request within
+ *             50 ms.
+ *             After successful completion of the Status stage, the device is
+ *             allowed a SetAddress() recovery interval of 2 ms. At the end of
+ *             this interval, the device must be able to accept Setup packets
+ *             addressed to the new address.
+ * - 9.2.6.4 : For standard device requests that require no Data stage, a device
+ *             must be able to complete the request and be able to successfully
+ *             complete the Status stage of the request within 50 ms of receipt
+ *             of the request. This limitation applies to requests to the
+ *             device, interface, or endpoint.
+ *             For standard device requests that require data stage transfer to
+ *             the host, the device must be able to return the first data packet
+ *             to the host within 500 ms of receipt of the request. For
+ *             subsequent data packets, if any, the device must be able to
+ *             return them within 500 ms of successful completion of the
+ *             transmission of the previous packet. The device must then be
+ *             able to successfully complete the status stage within 50 ms after
+ *             returning the last data packet.
+ *             For standard device requests that require a data stage transfer
+ *             to the device, the 5-second limit applies.
+ * - 9.2.6.5 : Unless specifically exempted in the class document, all
+ *             class-specific requests must meet the timing limitations for
+ *             standard device requests.
+ *
+ * Conclusion:
+ * 1. Whole request with data: 5 seconds
+ * 2. Whole request without data: 50 ms
+ * 3. Data packets: 500 ms
+ */
+struct usb_h_ctrl_xfer {
+	/** Pointer to transfer data */
+	uint8_t *data;
+	/** Pointer to setup packet */
+	uint8_t *setup;
+	/** Expected transfer size */
+	uint16_t size;
+	/** Transfer count */
+	uint16_t count;
+	/** Timeout for request, -1 if disable timeout */
+	int16_t req_timeout;
+	/** Timeout between packets
+	 *  (500ms for data and 50ms for status), -1 if disabled */
+	int16_t pkt_timeout;
+	/** Packet size during transfer (<= allocate max packet size) */
+	uint16_t pkt_size;
+
+	/** Transfer state */
+	uint8_t state;
+	/** Last transfer status */
+	int8_t status;
+};
+
+/**
+ * @brief      Transfer descriptor for bulk / interrupt / iso transfer
+ */
+struct usb_h_bulk_int_iso_xfer {
+	/** Expected transfer size */
+	uint32_t size;
+	/** Transfer count */
+	uint32_t count;
+	/** Pointer to transfer data */
+	uint8_t *data;
+	/** Reserved */
+	uint16_t reserved[3];
+
+	/** Transfer state */
+	uint8_t state;
+	/** Last transfer status */
+	int8_t status;
+};
+
+/**
+ * @brief      Transfer descriptor for periodic high bandwidth transfer
+ */
+struct usb_h_high_bw_xfer {
+	/** Expected transfer size */
+	uint32_t size;
+	/** Transfer count */
+	uint32_t count;
+	/** Pointer to transfer data */
+	uint8_t *data;
+	/** Micro frame packet sizes */
+	uint16_t pkt_size[3];
+
+	/** Transfer state */
+	uint8_t state;
+	/** Last transfer status */
+	int8_t status;
+};
+
+/**
+ * @brief General transfer descriptor
+ */
+struct usb_h_xfer {
+	/** Reserved for different transfer */
+	union {
+		uint16_t u16[9];
+		uint8_t  u8[18];
+	} reserved;
+	/** Transfer state */
+	uint8_t state;
+	/** Last transfer status */
+	int8_t status;
+};
+
+/**
+ * @brief      USB Host Controller Driver Pipe structure
+ */
+struct usb_h_pipe {
+	/** Pointer to the USB Host Controller Driver */
+	struct usb_h_desc *hcd;
+	/** Pointer to the callback for transfer done */
+	usb_h_pipe_cb_xfer_t done;
+#if CONF_USB_H_INST_OWNER_SP
+	/** Pointer to the pipe owner */
+	void *owner;
+#endif
+
+	/** Endpoint max packet size (bits 10..0) */
+	uint16_t max_pkt_size;
+	/** Device address */
+	uint8_t dev;
+	/** Endpoint address */
+	uint8_t ep;
+
+	/** Endpoint interval */
+	uint8_t interval;
+	/** Endpoint type: Control, Isochronous, Bulk or Interrupt */
+	uint8_t type;
+	/** Current toggle (driver dependent) */
+	uint8_t toggle;
+	/** Endpoint number of banks (HW dependent) */
+	uint8_t bank : 2;
+	/** Transfer speed (HW dependent) */
+	uint8_t speed : 2;
+	/** High bandwidth periodic out */
+	uint8_t high_bw_out : 1;
+	/** Uses DMA (on transfer) */
+	uint8_t dma : 1;
+	/** Transfer ZLP support */
+	uint8_t zlp : 1;
+	/** Transfer periodic */
+	uint8_t periodic_start : 1;
+
+	/** Transfer status */
+	union {
+		/** General transfer info */
+		struct usb_h_xfer general;
+		/** Control transfer status */
+		struct usb_h_ctrl_xfer ctrl;
+		/** Bulk interrupt iso transfer status */
+		struct usb_h_bulk_int_iso_xfer bii;
+		/** Periodic high bandwidth transfer status */
+		struct usb_h_high_bw_xfer hbw;
+	} x;
+};
+
+/**
+ * @brief      USB HCD Initialization
+ *
+ * @param      drv     Pointer to the HCD driver instance
+ * @param[in]  hw      Pointer to hardware base
+ * @param[in]  prvt    The private driver data (implement specific)
+ *
+ * @return     Operation result status
+ * @retval     ERR_DENIED Hardware has been enabled
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_init(struct usb_h_desc *drv, void *hw, void *prvt);
+
+/**
+ * @brief      USB HCD de-initialization
+ *
+ * @param      drv   The driver
+ */
+void _usb_h_deinit(struct usb_h_desc *drv);
+
+/**
+ * @brief      USB HCD enable
+ *
+ * @param      drv   The driver
+ */
+void _usb_h_enable(struct usb_h_desc *drv);
+
+/**
+ * @brief      USB HCD disable
+ *
+ * @param      drv   The driver
+ */
+void _usb_h_disable(struct usb_h_desc *drv);
+
+/**
+ * @brief      Register callbacks for USB HCD
+ *
+ * @param      drv   The driver
+ * @param[in]  type  The callback type
+ * @param[in]  cb    The callback function entry
+ *
+ * @return     Operation result status
+ * @retval     ERR_INVALID_ARG Argument error
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_register_callback(struct usb_h_desc *drv, enum usb_h_cb_type type, FUNC_PTR cb);
+
+/**
+ * @brief      Return current frame number
+ *
+ * @param      drv   The driver
+ *
+ * @return     current frame number
+ */
+uint16_t _usb_h_get_frame_n(struct usb_h_desc *drv);
+
+/**
+ * @brief      Return current micro frame number
+ *
+ * @param      drv   The driver
+ *
+ * @return     current micro frame number
+ */
+uint8_t _usb_h_get_microframe_n(struct usb_h_desc *drv);
+
+/**
+ * @brief Suspend the USB bus
+ *
+ * @param drv The driver
+ */
+void _usb_h_suspend(struct usb_h_desc *drv);
+
+/**
+ * @brief Resume the USB bus
+ *
+ * @param drv The driver
+ */
+void _usb_h_resume(struct usb_h_desc *drv);
+
+/* Root hub related APIs */
+
+/**
+ * \brief Reset the root hub port
+ *
+ * \param[in,out] drv  Pointer to the USB HCD driver
+ * \param[in]     port Root hub port, ignored if there is only one port
+ */
+void _usb_h_rh_reset(struct usb_h_desc *drv, uint8_t port);
+
+/**
+ * \brief Suspend the root hub port
+ *
+ * \param[in,out] drv  Pointer to the USB HCD driver
+ * \param[in]     port Root hub port, ignored if there is only one port
+ */
+void _usb_h_rh_suspend(struct usb_h_desc *drv, uint8_t port);
+
+/**
+ * \brief Resume the root hub port
+ *
+ * \param[in,out] drv  Pointer to the USB HCD driver
+ * \param[in]     port Root hub port, ignored if there is only one port
+ */
+void _usb_h_rh_resume(struct usb_h_desc *drv, uint8_t port);
+
+/**
+ * \brief Root hub or port feature status check
+ *
+ * Check USB Spec. for hub status and feature selectors.
+ *
+ * \param[in] drv  Pointer to the USB HCD driver
+ * \param[in] port Set to 0 to get hub status, otherwise to get port status
+ * \param[in] ftr  Hub feature/status selector
+ *                 (0: connection, 2: suspend, 4: reset, 9: LS, 10: HS)
+ *
+ * \return     \c true if the status bit is 1
+ */
+bool _usb_h_rh_check_status(struct usb_h_desc *drv, uint8_t port, uint8_t ftr);
+
+/* Pipe transfer functions */
+
+/**
+ * @brief      Allocate a pipe for USB host communication
+ *
+ * @param      drv           The USB HCD driver
+ * @param[in]  dev           The device address
+ * @param[in]  ep            The endpoint address
+ * @param[in]  max_pkt_size  The endpoint maximum packet size
+ * @param[in]  attr          The endpoint attribute
+ * @param[in]  interval      The endpoint interval
+ *                           (bInterval of USB Endpoint Descriptor)
+ * @param[in]  speed         The transfer speed of the endpoint
+ * @param[in]  minimum_rsc   Minimum the resource usage, \sa usb_h_rsc_strategy
+ *
+ * @return     Pointer to allocated pipe structure instance
+ * @retval     NULL allocation fail
+ */
+struct usb_h_pipe *_usb_h_pipe_allocate(struct usb_h_desc *drv, uint8_t dev, uint8_t ep, uint16_t max_pkt_size,
+                                        uint8_t attr, uint8_t interval, uint8_t speed, bool minimum_rsc);
+
+/**
+ * @brief      Free an allocated pipe
+ *
+ * @param      pipe  The pipe
+ *
+ * @return     Operation result status
+ * @retval     ERR_BUSY Pipe is busy, use \ref _usb_h_pipe_abort to abort
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_pipe_free(struct usb_h_pipe *pipe);
+
+/**
+ * @brief      Modify parameters of an allocated control pipe
+ *
+ * @param      pipe          The pipe
+ * @param[in]  dev           The device address
+ * @param[in]  ep            The endpoint address
+ * @param[in]  max_pkt_size  The maximum packet size, must be equal or
+ *                           less than allocated size
+ * @param[in]  speed         The working speed
+ *
+ * @return     Operation result status
+ * @retval     ERR_NOT_INITIALIZED Pipe is not allocated
+ * @retval     ERR_BUSY Pipe is busy transferring
+ * @retval     ERR_INVALID_ARG Argument error
+ * @retval     ERR_UNSUPPORTED_OP Pipe is not control pipe
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_pipe_set_control_param(struct usb_h_pipe *pipe, uint8_t dev, uint8_t ep, uint16_t max_pkt_size,
+                                      uint8_t speed);
+
+/**
+ * @brief      Register transfer callback on a pipe
+ *
+ * @param      pipe  The pipe
+ * @param[in]  cb    Transfer callback function
+ *
+ * @return     Operation result status
+ * @retval     ERR_INVALID_ARG Argument error
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_pipe_register_callback(struct usb_h_pipe *pipe, usb_h_pipe_cb_xfer_t cb);
+
+/**
+ * @brief      Issue a control transfer (request) on a pipe
+ *
+ * \note When there is data stage, timeout between data packets is 500ms, the
+ *       timeout between last data packet and the status packet is 50ms.
+ *
+ * @param         pipe    The pipe
+ * @param[in]     setup   Pointer to the setup packet
+ * @param[in,out] data    Pointer to the data buffer
+ * @param[in]     length  The data length
+ * @param[in]     timeout Timeout for whole request in ms
+ *
+ * @return     Operation result status
+ * @retval     ERR_NOT_INITIALIZED Pipe is not allocated
+ * @retval     ERR_BUSY Pipe is busy transferring
+ * @retval     ERR_INVALID_ARG Argument error
+ * @retval     ERR_UNSUPPORTED_OP Pipe is not control pipe
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_control_xfer(struct usb_h_pipe *pipe, uint8_t *setup, uint8_t *data, uint16_t length, int16_t timeout);
+
+/**
+ * @brief      Issue a bulk / interrupt / iso transfer on a pipe
+ *
+ * @param         pipe     The pipe
+ * @param[in,out] data     Pointer to the data buffer
+ * @param[in]     length   The data length
+ * @param[in]     auto_zlp Auto append ZLP for OUT
+ *
+ * @return     Operation result status
+ * @retval     ERR_NOT_INITIALIZED Pipe is not allocated
+ * @retval     ERR_BUSY Pipe is busy transferring
+ * @retval     ERR_INVALID_ARG Argument error
+ * @retval     ERR_UNSUPPORTED_OP Pipe is control pipe
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_bulk_int_iso_xfer(struct usb_h_pipe *pipe, uint8_t *data, uint32_t length, bool auto_zlp);
+
+/**
+ * @brief      Issue a periodic high bandwidth output on a pipe
+ *
+ * @param         pipe             The pipe
+ * @param[in,out] data             Pointer to the data buffer
+ * @param[in]     length           The data length
+ * @param[in]     trans_pkt_size   The transaction packet sizes in a micro frame,
+ *                                 0 to use endpoint max packet size
+ *
+ * @return     Operation result status
+ * @retval     ERR_NOT_INITIALIZED Pipe is not allocated
+ * @retval     ERR_BUSY Pipe is busy transferring
+ * @retval     ERR_INVALID_ARG Argument error
+ * @retval     ERR_UNSUPPORTED_OP Pipe is not high bandwidth periodic pipe, or
+ *                                DMA feature not enabled, or
+ *                                high bandwidth not enabled
+ * @retval     ERR_NONE Operation done successfully
+ */
+int32_t _usb_h_high_bw_out(struct usb_h_pipe *pipe, uint8_t *data, uint32_t length, uint16_t trans_pkt_size[3]);
+
+/**
+ * @brief      Check if pipe is busy transferring
+ *
+ * @param      pipe  The pipe
+ *
+ * @return     \c true if pipe is busy
+ */
+bool _usb_h_pipe_is_busy(struct usb_h_pipe *pipe);
+
+/**
+ * @brief      Abort pending transfer on a pipe
+ *
+ * @param      pipe  The pipe
+ */
+void _usb_h_pipe_abort(struct usb_h_pipe *pipe);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _HPL_USB_HOST_H_INCLUDED */