SAMV71 Xplained Ultra Software Package 1.5

main.c

Go to the documentation of this file.
00001 /* ---------------------------------------------------------------------------- */
00002 /*                  Atmel Microcontroller Software Support                      */
00003 /*                       SAM Software Package License                           */
00004 /* ---------------------------------------------------------------------------- */
00005 /* Copyright (c) 2015, Atmel Corporation                                        */
00006 /*                                                                              */
00007 /* All rights reserved.                                                         */
00008 /*                                                                              */
00009 /* Redistribution and use in source and binary forms, with or without           */
00010 /* modification, are permitted provided that the following condition is met:    */
00011 /*                                                                              */
00012 /* - Redistributions of source code must retain the above copyright notice,     */
00013 /* this list of conditions and the disclaimer below.                            */
00014 /*                                                                              */
00015 /* Atmel's name may not be used to endorse or promote products derived from     */
00016 /* this software without specific prior written permission.                     */
00017 /*                                                                              */
00018 /* DISCLAIMER:  THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR   */
00019 /* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF */
00020 /* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE   */
00021 /* DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT,      */
00022 /* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT */
00023 /* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,  */
00024 /* OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF    */
00025 /* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING         */
00026 /* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, */
00027 /* EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.                           */
00028 /* ---------------------------------------------------------------------------- */
00029 
00030 /** \cond usb_iad_cdc_msd
00031  * \page usb_iad_cdc_msd USB CDC(Serial)+MSD Example
00032  *
00033  * \section Purpose
00034  *
00035  * The USB CDCMSD Project will help you to get familiar with the
00036  * USB Device Port(UDP)interface and also some of the other interfaces in
00037  * SAMV7/E7 Microcontrollers. Also it can help you to be familiar with the USB
00038  * Framework that is used for rapid development of USB-compliant class
00039  * drivers such as USB Communication Device class (CDC), and how to combine
00040  * two USB functions to a single CDCMSD device (such as CDC + MSD).
00041  *
00042  * \section Requirements
00043  *
00044  * This package can be used with SAMV71 Xplained Ultra board or SAME70 Xplained board
00045  * that have UDP interface, depending on the functions included.
00046  *
00047  *  \section win_drv_update Windows Driver Update
00048  *
00049  * The composite device is generally supported by Microsoft windows, but some
00050  * patches are needed for muti-interface functions such as CDC & Audio.
00051  *
00052  * \section Description
00053  *
00054  * The demo simulates a USB composite device that integrates USB CDC Serial
00055  * RS232 Converter function and USB Disk function.
00056  *
00057  * When the board running this program connected to a host (PC for example),
00058  * with USB cable, host will notice the attachment of a USB device. No device
00059  * driver offered for the device now.
00060  *
00061  * \section Usage
00062  *
00063  *  -# Build the program and download it inside the board.
00064  *     Please refer to the Getting Started with SAM V71/E70 Microcontrollers.pdf
00065  * -# On the computer, open and configure a terminal application
00066  *    (e.g. HyperTerminal on Microsoft Windows) with these settings:
00067  *   - 115200 baud rate
00068  *   - 8 bits of data
00069  *   - No parity
00070  *   - 1 stop bit
00071  *   - No flow control
00072  * -# Start the application.
00073  * -# In the terminal window, the following text should appear:
00074  *     \code
00075  *     -- USB CDC MSD Device Project xxx --
00076  *     -- SAMxxxxx-xx
00077  *     -- Compiled: xxx xx xxxx xx:xx:xx --
00078  *     \endcode
00079  * -# When connecting USB cable to windows, the LED blinks, and the host
00080  *    reports a new USB device attachment.
00081  * -# For the windows driver installation and the test functions, please
00082  *      refer to "USB CDC serial converter" &
00083  *      "USB Device Mass Storage Project".
00084  * -# You can use the inf file
00085  *    libraries\\usb\\device\\composite\\drv\\CompositeCDCSerial.inf
00086  *    to install the CDC serial  port.
00087  *
00088  * \section References
00089  *
00090  * - usb_iad_cdc_msd/main.c
00091  * - pio: Pin configurations and peripheral configure.
00092  * - memories: Storage Media interface for MSD
00093  * - usb: USB Device Framework, USB CDC driver and UDP interface driver
00094  *    - \ref usbd_framework
00095  *        - \ref usbd_api
00096  *    - \ref usbd_composite "composite"
00097  *       - \ref usbd_composite_drv
00098  *    - \ref usbd_msd "massstorage"
00099  *       - \ref usbd_msd_drv
00100  *    - \ref usbd_cdc "cdc-serial"
00101  *       - \ref usbd_cdc_serial_drv
00102  * - projects:
00103  *    - \ref usb_massstorage
00104  *    - \ref usb_cdc_serial
00105  */
00106 
00107 /**
00108  * \file
00109  *
00110  * \section Purpose
00111  *
00112  * This file contains all the specific code for the
00113  * usb_iad_cdc_msd project
00114  */
00115 
00116 /*---------------------------------------------------------------------------
00117  *         Headers
00118  *---------------------------------------------------------------------------*/
00119 
00120 #include "board.h"
00121 
00122 #include "libstoragemedia.h"
00123 
00124 #include <USBD_Config.h>
00125 #include <CDCMSDDriver.h>
00126 #include <CDCDSerial.h>
00127 #include <MSDFunction.h>
00128 
00129 #include <stdint.h>
00130 #include <stdio.h>
00131 #include <string.h>
00132 #include <stdbool.h>
00133 
00134 /*---------------------------------------------------------------------------
00135  *      Definitions
00136  *---------------------------------------------------------------------------*/
00137 
00138 /** Size in bytes of the packet used for reading data from USB */
00139 #define DATAPACKETSIZE \
00140     CHIP_USB_ENDPOINTS_MAXPACKETSIZE(CDCDSerialDriverDescriptors_DATAIN)
00141 
00142 /** Size in bytes of the buffer used for reading data from the USB & USART */
00143 #define DATABUFFERSIZE (DATAPACKETSIZE+2)
00144 
00145 /** Maximum number of LUNs which can be defined. */
00146 #define MAX_LUNS            1
00147 /** Media index for different disks */
00148 #define DRV_RAMDISK         0    /**< RAM disk */
00149 #define DRV_SDMMC           1    /**< SD card */
00150 
00151 /** Size of one block in bytes. */
00152 #define BLOCK_SIZE          512
00153 
00154 /** Size of the MSD IO buffer in bytes (6K, more the better). */
00155 #define MSD_BUFFER_SIZE     (12*BLOCK_SIZE)
00156 
00157 /** RamDisk size: (WinXP can not format the disk if lower than 20K) */
00158 #define RAMDISK_SIZE        128*1024
00159 
00160 COMPILER_SECTION("ramdisk_region") static uint8_t
00161 ramdisk_reserved[RAMDISK_SIZE];
00162 #define RAMDISK_BASE_ADDR ((uint32_t)ramdisk_reserved)
00163 
00164 /** Delay for MSD refresh (*4ms) */
00165 #define MSD_REFRESH_DELAY    250
00166 
00167 /** Delay for waiting DBGU input (*4ms) */
00168 #define INPUT_DELAY          (2*250)
00169 
00170 /*---------------------------------------------------------------------------
00171  *      External variables
00172  *---------------------------------------------------------------------------*/
00173 
00174 /** Descriptor list for the device to bring up */
00175 extern const USBDDriverDescriptors cdcmsddDriverDescriptors;
00176 
00177 /*---------------------------------------------------------------------------
00178  *      Internal variables
00179  *---------------------------------------------------------------------------*/
00180 /** Buffer for storing incoming USB data. */
00181 static uint8_t usbSerialBuffer0[DATABUFFERSIZE];
00182 
00183 /** Serial port opened */
00184 static uint8_t isSerialPortON = 0;
00185 
00186 /*- MSD */
00187 /** Available media. */
00188 sMedia medias[MAX_LUNS];
00189 
00190 /** Device LUNs. */
00191 MSDLun luns[MAX_LUNS];
00192 
00193 /** LUN read/write buffer. */
00194 uint8_t msdBuffer[MSD_BUFFER_SIZE];
00195 
00196 /** Total data write to disk */
00197 uint32_t msdWriteTotal = 0;
00198 /** Delay for data write refresh */
00199 uint32_t msdDelay = MSD_REFRESH_DELAY;
00200 /** Delay TO event */
00201 uint8_t  msdRefresh = 0;
00202 
00203 
00204 /*-----------------------------------------------------------------------------
00205  *         Callback re-implementation
00206  *-----------------------------------------------------------------------------*/
00207 /**
00208  * Invoked when the configuration of the device changes. Parse used endpoints.
00209  * \param cfgnum New configuration number.
00210  */
00211 void USBDDriverCallbacks_ConfigurationChanged(uint8_t cfgnum)
00212 {
00213     CDCMSDDriver_ConfigurationChangedHandler(cfgnum);
00214 }
00215 
00216 /**
00217  * Invoked when a new SETUP request is received from the host. Forwards the
00218  * request to the Mass Storage device driver handler function.
00219  * \param request  Pointer to a USBGenericRequest instance.
00220  */
00221 void USBDCallbacks_RequestReceived(const USBGenericRequest *request)
00222 {
00223     CDCMSDDriver_RequestHandler(request);
00224 }
00225 
00226 /*----------------------------------------------------------------------------
00227  *         Callbacks
00228  *----------------------------------------------------------------------------*/
00229 
00230 /**
00231  * Invoked when the MSD finish a READ/WRITE.
00232  * \param flowDirection 1 - device to host (READ10)
00233  *                      0 - host to device (WRITE10)
00234  * \param dataLength Length of data transferred in bytes.
00235  * \param fifoNullCount Times that FIFO is NULL to wait
00236  * \param fifoFullCount Times that FIFO is filled to wait
00237  */
00238 static void MSDCallbacks_Data(uint8_t flowDirection,
00239                               uint32_t  dataLength,
00240                               uint32_t  fifoNullCount,
00241                               uint32_t  fifoFullCount)
00242 {
00243     fifoNullCount = fifoNullCount; /* dummy */
00244     fifoFullCount = fifoFullCount;  /*dummy */
00245 
00246     if (!flowDirection)
00247         msdWriteTotal += dataLength;
00248 }
00249 
00250 /**
00251  * Invoked when the CDC ControlLineState is changed
00252  * \param DTR   New DTR value.
00253  * \param RTS   New RTS value.
00254  */
00255 void CDCDSerial_ControlLineStateChanged(uint8_t DTR,
00256                                         uint8_t RTS)
00257 {
00258     isSerialPortON = DTR;
00259     RTS = RTS; /* dummy */
00260 }
00261 
00262 /**
00263  * Invoked when the CDC LineCoding is requested to changed
00264  * \param pLineCoding   Pointer to new LineCoding settings.
00265  * \return USBRC_SUCCESS if ready to receive the line coding.
00266  */
00267 uint8_t CDCDSerial_LineCodingIsToChange(CDCLineCoding *pLineCoding)
00268 {
00269     pLineCoding = pLineCoding; /*dummy */
00270     return USBD_STATUS_SUCCESS;
00271 }
00272 
00273 /*---------------------------------------------------------------------------
00274  *         Internal functions
00275  *---------------------------------------------------------------------------*/
00276 /**
00277  * Configure USBHS settings for USB device
00278  */
00279 static void _ConfigureUotghs(void)
00280 {
00281 
00282     /* UTMI parallel mode, High/Full/Low Speed */
00283     /* UUSBCK not used in this configuration (High Speed) */
00284     PMC->PMC_SCDR = PMC_SCDR_USBCLK;
00285     /* USB clock register: USB Clock Input is UTMI PLL */
00286     PMC->PMC_USB = PMC_USB_USBS;
00287     /* Enable peripheral clock for USBHS */
00288     PMC_EnablePeripheral(ID_USBHS);
00289     USBHS->USBHS_CTRL = USBHS_CTRL_UIMOD_DEVICE;
00290     /* Enable PLL 480 MHz */
00291     PMC->CKGR_UCKR = CKGR_UCKR_UPLLEN | CKGR_UCKR_UPLLCOUNT(0xF);
00292 
00293     /* Wait that PLL is considered locked by the PMC */
00294     while (!(PMC->PMC_SR & PMC_SR_LOCKU));
00295 
00296     /* IRQ */
00297     NVIC_EnableIRQ(USBHS_IRQn);
00298 }
00299 
00300 /**
00301  * Initialize DDRAM to assign RamDisk block
00302  */
00303 static void RamDiskInit(void)
00304 {
00305     BOARD_ConfigureSdram();
00306 
00307     printf("RamDisk @ %x, size %d\n\r", (unsigned int)RAMDISK_BASE_ADDR, RAMDISK_SIZE);
00308 
00309     MEDRamDisk_Initialize(&(medias[DRV_RAMDISK]),
00310                           BLOCK_SIZE,
00311                           (RAMDISK_BASE_ADDR) / BLOCK_SIZE,
00312                           RAMDISK_SIZE / BLOCK_SIZE,
00313                           1);
00314     LUN_Init(&(luns[DRV_RAMDISK]),
00315              &(medias[DRV_RAMDISK]),
00316              msdBuffer, MSD_BUFFER_SIZE,
00317              0, 0, 0, 0,
00318              MSDCallbacks_Data);
00319 
00320     gNbMedias = 1;
00321 }
00322 
00323 /**
00324  * Initialize MSD Media & LUNs
00325  */
00326 static void _MemoriesInitialize(void)
00327 {
00328     uint32_t i;
00329 
00330     /* Reset all LUNs */
00331     for (i = 0; i < MAX_LUNS; i ++)
00332         LUN_Init(&luns[i], 0, 0, 0, 0, 0, 0, 0, 0);
00333 
00334     /* TODO: Add LUN Init here */
00335 
00336     /* RAM disk initialize */
00337     RamDiskInit();
00338     /* Nand Flash Init */
00339     /* SD Card Init */
00340 }
00341 
00342 /*---------------------------------------------------------------------------
00343  *         Exported function
00344  *---------------------------------------------------------------------------*/
00345 
00346 /*---------------------------------------------------------------------------
00347  *          Main
00348  *---------------------------------------------------------------------------*/
00349 
00350 /**
00351  * Initializes drivers and start the USB CDCMSD device.
00352  */
00353 int main(void)
00354 {
00355     uint8_t usbConnected = 0, serialON = 0;
00356 
00357     /* Disable watchdog */
00358     WDT_Disable(WDT);
00359 
00360     SCB_EnableICache();
00361     SCB_EnableDCache();
00362 
00363     printf("-- USB CDCMSD Device Project %s --\n\r", SOFTPACK_VERSION);
00364     printf("-- %s\n\r", BOARD_NAME);
00365     printf("-- Compiled: %s %s With %s--\n\r", __DATE__, __TIME__ ,
00366             COMPILER_NAME);
00367 
00368     /* If they are present, configure Vbus & Wake-up pins */
00369     PIO_InitializeInterrupts(0);
00370 
00371     /* If there is on board power, switch it off */
00372     _ConfigureUotghs();
00373 
00374     /* ----- MSD Function Initialize */
00375     /* Configure memories */
00376     _MemoriesInitialize();
00377 
00378     /* USB CDCMSD driver initialization */
00379     CDCMSDDriver_Initialize(&cdcmsddDriverDescriptors, luns, MAX_LUNS);
00380 
00381     /* connect if needed */
00382     USBD_Connect();
00383 
00384     /* Driver loop */
00385     while (1) {
00386         /* Device is not configured */
00387         if (USBD_GetState() < USBD_STATE_CONFIGURED) {
00388             if (usbConnected) {
00389                 printf("-I- USB Disconnect/Suspend\n\r");
00390                 usbConnected = 0;
00391 
00392                 /* Serial port closed */
00393                 isSerialPortON = 0;
00394             }
00395         } else {
00396             if (usbConnected == 0) {
00397                 printf("-I- USB Connect\n\r");
00398                 usbConnected = 1;
00399             }
00400 
00401             if (!serialON && isSerialPortON) {
00402                 printf("-I- SerialPort ON\n\r");
00403                 /* Start receiving data on the USART */
00404                 /* Start receiving data on the USB */
00405                 CDCDSerial_Read(usbSerialBuffer0, DATAPACKETSIZE, 0, 0);
00406                 serialON = 1;
00407             } else if (serialON && !isSerialPortON) {
00408                 printf("-I- SeriaoPort OFF\n\r");
00409                 serialON = 0;
00410             }
00411 
00412             MSDFunction_StateMachine();
00413 
00414             if (msdRefresh) {
00415                 msdRefresh = 0;
00416 
00417                 if (msdWriteTotal < 50 * 1000) {
00418                     /* Flush Disk Media */
00419                 }
00420 
00421                 msdWriteTotal = 0;
00422             }
00423         }
00424     }
00425 }
00426 /** \endcond */
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Defines