mirror of
https://github.com/arduino/Arduino.git
synced 2024-12-02 13:24:12 +01:00
487 lines
13 KiB
C
487 lines
13 KiB
C
/*
|
|
Copyright (c) 2012 Arduino. All right reserved.
|
|
|
|
This library is free software; you can redistribute it and/or
|
|
modify it under the terms of the GNU Lesser General Public
|
|
License as published by the Free Software Foundation; either
|
|
version 2.1 of the License, or (at your option) any later version.
|
|
|
|
This library is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
See the GNU Lesser General Public License for more details.
|
|
|
|
You should have received a copy of the GNU Lesser General Public
|
|
License along with this library; if not, write to the Free Software
|
|
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
|
|
*/
|
|
|
|
#include "chip.h"
|
|
#include <stdio.h>
|
|
|
|
#if SAM3XA_SERIES
|
|
|
|
static void (*gpf_isr)(void)=(0UL);
|
|
|
|
uint32_t ul_ep = 0;
|
|
|
|
void UDD_SetStack(void (*pf_isr)(void))
|
|
{
|
|
gpf_isr = pf_isr;
|
|
}
|
|
|
|
void UOTGHS_Handler( void )
|
|
{
|
|
if (gpf_isr)
|
|
gpf_isr();
|
|
}
|
|
|
|
uint32_t UDD_Init(void)
|
|
{
|
|
uint32_t ul ;
|
|
|
|
// Enables the USB Clock
|
|
pmc_enable_periph_clk(ID_UOTGHS);
|
|
pmc_enable_upll_clock();
|
|
pmc_switch_udpck_to_upllck(0); // div=0+1
|
|
pmc_enable_udpck();
|
|
|
|
// Configure interrupts
|
|
NVIC_SetPriority((IRQn_Type) ID_UOTGHS, 0UL);
|
|
NVIC_EnableIRQ((IRQn_Type) ID_UOTGHS);
|
|
|
|
// Always authorize asynchrone USB interrupts to exit from sleep mode
|
|
// for SAM3 USB wake up device except BACKUP mode
|
|
//pmc_set_fast_startup_input(PMC_FSMR_USBAL);
|
|
|
|
|
|
|
|
|
|
// ID pin not used then force device mode
|
|
otg_disable_id_pin();
|
|
otg_force_device_mode();
|
|
|
|
// Enable USB hardware
|
|
otg_disable_pad();
|
|
otg_enable_pad();
|
|
otg_enable();
|
|
otg_unfreeze_clock();
|
|
// Check USB clock
|
|
while (!Is_otg_clock_usable())
|
|
;
|
|
|
|
udd_low_speed_disable();
|
|
udd_high_speed_disable();
|
|
|
|
|
|
//otg_ack_vbus_transition();
|
|
// Force Vbus interrupt in case of Vbus always with a high level
|
|
// This is possible with a short timing between a Host mode stop/start.
|
|
/*if (Is_otg_vbus_high()) {
|
|
otg_raise_vbus_transition();
|
|
}
|
|
otg_enable_vbus_interrupt();*/
|
|
otg_freeze_clock();
|
|
|
|
|
|
|
|
|
|
|
|
// Enable USB
|
|
/*UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_USBE;
|
|
|
|
// Automatic mode speed for device
|
|
UOTGHS->UOTGHS_DEVCTRL &= ~UOTGHS_DEVCTRL_SPDCONF_Msk; // Normal mode
|
|
|
|
UOTGHS->UOTGHS_DEVCTRL &= ~( UOTGHS_DEVCTRL_LS | UOTGHS_DEVCTRL_TSTJ | UOTGHS_DEVCTRL_TSTK |
|
|
UOTGHS_DEVCTRL_TSTPCKT | UOTGHS_DEVCTRL_OPMODE2 ); // Normal mode
|
|
|
|
UOTGHS->UOTGHS_DEVCTRL = 0;
|
|
UOTGHS->UOTGHS_HSTCTRL = 0;
|
|
|
|
// Enable OTG pad
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_OTGPADE;
|
|
|
|
// Enable clock OTG pad
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_FRZCLK;
|
|
|
|
// Usb disable
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_USBE;
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_OTGPADE;
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_FRZCLK;
|
|
|
|
// Usb enable
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_USBE;
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_OTGPADE;
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_FRZCLK;
|
|
|
|
// Usb select device mode
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_UIDE;
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_UIMOD_Device;
|
|
|
|
// Device is in the Attached state
|
|
// deviceState = USBD_STATE_SUSPENDED;
|
|
// previousDeviceState = USBD_STATE_POWERED;
|
|
|
|
// Enable USB and clear all other bits
|
|
//UOTGHS->UOTGHS_DEVCTRL |= UOTGHS_CTRL_USBE;
|
|
//UOTGHS->UOTGHS_DEVCTRL = UOTGHS_CTRL_USBE;
|
|
|
|
// Configure the pull-up on D+ and disconnect it
|
|
UDD_Detach();
|
|
|
|
// Clear General IT
|
|
UOTGHS->UOTGHS_SCR = (UOTGHS_SCR_IDTIC|UOTGHS_SCR_VBUSTIC|UOTGHS_SCR_SRPIC|UOTGHS_SCR_VBERRIC|UOTGHS_SCR_BCERRIC|UOTGHS_SCR_ROLEEXIC|UOTGHS_SCR_HNPERRIC|UOTGHS_SCR_STOIC|UOTGHS_SCR_VBUSRQC);
|
|
|
|
// Clear OTG Device IT
|
|
UOTGHS->UOTGHS_DEVICR = (UOTGHS_DEVICR_SUSPC|UOTGHS_DEVICR_MSOFC|UOTGHS_DEVICR_SOFC|UOTGHS_DEVICR_EORSTC|UOTGHS_DEVICR_WAKEUPC|UOTGHS_DEVICR_EORSMC|UOTGHS_DEVICR_UPRSMC);
|
|
|
|
// Clear OTG Host IT
|
|
UOTGHS->UOTGHS_HSTICR = (UOTGHS_HSTICR_DCONNIC|UOTGHS_HSTICR_DDISCIC|UOTGHS_HSTICR_RSTIC|UOTGHS_HSTICR_RSMEDIC|UOTGHS_HSTICR_RXRSMIC|UOTGHS_HSTICR_HSOFIC|UOTGHS_HSTICR_HWUPIC);
|
|
|
|
// Reset all Endpoints Fifos
|
|
UOTGHS->UOTGHS_DEVEPT |= (UOTGHS_DEVEPT_EPRST0|UOTGHS_DEVEPT_EPRST1|UOTGHS_DEVEPT_EPRST2|UOTGHS_DEVEPT_EPRST3|UOTGHS_DEVEPT_EPRST4|
|
|
UOTGHS_DEVEPT_EPRST5|UOTGHS_DEVEPT_EPRST6|UOTGHS_DEVEPT_EPRST7|UOTGHS_DEVEPT_EPRST8);
|
|
UOTGHS->UOTGHS_DEVEPT &= ~(UOTGHS_DEVEPT_EPRST0|UOTGHS_DEVEPT_EPRST1|UOTGHS_DEVEPT_EPRST2|UOTGHS_DEVEPT_EPRST3|UOTGHS_DEVEPT_EPRST4|
|
|
UOTGHS_DEVEPT_EPRST5|UOTGHS_DEVEPT_EPRST6|UOTGHS_DEVEPT_EPRST7|UOTGHS_DEVEPT_EPRST8);
|
|
|
|
// Disable all endpoints
|
|
UOTGHS->UOTGHS_DEVEPT &= ~(UOTGHS_DEVEPT_EPEN0|UOTGHS_DEVEPT_EPEN1|UOTGHS_DEVEPT_EPEN2|UOTGHS_DEVEPT_EPEN3|UOTGHS_DEVEPT_EPEN4|
|
|
UOTGHS_DEVEPT_EPEN5|UOTGHS_DEVEPT_EPEN6|UOTGHS_DEVEPT_EPEN7|UOTGHS_DEVEPT_EPEN8);
|
|
|
|
// Device is in the Attached state
|
|
// deviceState = USBD_STATE_SUSPENDED;
|
|
// previousDeviceState = USBD_STATE_POWERED;
|
|
|
|
// Automatic mode speed for device
|
|
UOTGHS->UOTGHS_DEVCTRL &= ~UOTGHS_DEVCTRL_SPDCONF_Msk;
|
|
// Force Full Speed mode for device
|
|
//UOTGHS->UOTGHS_DEVCTRL = UOTGHS_DEVCTRL_SPDCONF_FORCED_FS;
|
|
// Force High Speed mode for device
|
|
//UOTGHS->UOTGHS_DEVCTRL = UOTGHS_DEVCTRL_SPDCONF_HIGH_SPEED;
|
|
|
|
UOTGHS->UOTGHS_DEVCTRL &= ~(UOTGHS_DEVCTRL_LS|UOTGHS_DEVCTRL_TSTJ| UOTGHS_DEVCTRL_TSTK|UOTGHS_DEVCTRL_TSTPCKT|UOTGHS_DEVCTRL_OPMODE2) ;
|
|
|
|
// Enable USB macro
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_USBE;
|
|
|
|
// Enable the UID pin select
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_UIDE;
|
|
|
|
// Enable OTG pad
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_OTGPADE;
|
|
|
|
// Enable clock OTG pad
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_FRZCLK;
|
|
|
|
// With OR without DMA !!!
|
|
// Initialization of DMA
|
|
for( ul=1; ul<= UOTGHSDEVDMA_NUMBER ; ul++ )
|
|
{
|
|
// RESET endpoint canal DMA:
|
|
// DMA stop channel command
|
|
UOTGHS->UOTGHS_DEVDMA[ul].UOTGHS_DEVDMACONTROL = 0; // STOP command
|
|
|
|
// Disable endpoint
|
|
UOTGHS->UOTGHS_DEVEPTIDR[ul] = (UOTGHS_DEVEPTIDR_TXINEC|UOTGHS_DEVEPTIDR_RXOUTEC|UOTGHS_DEVEPTIDR_RXSTPEC|UOTGHS_DEVEPTIDR_UNDERFEC|UOTGHS_DEVEPTIDR_NAKOUTEC|
|
|
UOTGHS_DEVEPTIDR_HBISOINERREC|UOTGHS_DEVEPTIDR_NAKINEC|UOTGHS_DEVEPTIDR_HBISOFLUSHEC|UOTGHS_DEVEPTIDR_OVERFEC|UOTGHS_DEVEPTIDR_STALLEDEC|
|
|
UOTGHS_DEVEPTIDR_CRCERREC|UOTGHS_DEVEPTIDR_SHORTPACKETEC|UOTGHS_DEVEPTIDR_MDATEC|UOTGHS_DEVEPTIDR_DATAXEC|UOTGHS_DEVEPTIDR_ERRORTRANSEC|
|
|
UOTGHS_DEVEPTIDR_NBUSYBKEC|UOTGHS_DEVEPTIDR_FIFOCONC|UOTGHS_DEVEPTIDR_EPDISHDMAC|UOTGHS_DEVEPTIDR_NYETDISC|UOTGHS_DEVEPTIDR_STALLRQC);
|
|
|
|
// Reset endpoint config
|
|
UOTGHS->UOTGHS_DEVEPTCFG[ul] = 0UL;
|
|
|
|
// Reset DMA channel (Buff count and Control field)
|
|
UOTGHS->UOTGHS_DEVDMA[ul].UOTGHS_DEVDMACONTROL = 0x02UL; // NON STOP command
|
|
|
|
// Reset DMA channel 0 (STOP)
|
|
UOTGHS->UOTGHS_DEVDMA[ul].UOTGHS_DEVDMACONTROL = 0UL; // STOP command
|
|
|
|
// Clear DMA channel status (read the register to clear it)
|
|
UOTGHS->UOTGHS_DEVDMA[ul].UOTGHS_DEVDMASTATUS = UOTGHS->UOTGHS_DEVDMA[ul].UOTGHS_DEVDMASTATUS;
|
|
}
|
|
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_VBUSTE;
|
|
UOTGHS->UOTGHS_DEVIER = UOTGHS_DEVIER_WAKEUPES;
|
|
*/
|
|
return 0UL ;
|
|
}
|
|
|
|
void UDD_Attach(void)
|
|
{
|
|
//USBCON = ((1<<USBE)|(1<<OTGPADE)); // start USB clock
|
|
//UDIEN = (1<<EORSTE)|(1<<SOFE); // Enable interrupts for EOR (End of Reset) and SOF (start of frame)
|
|
//UDCON = 0; // enable attach resistor
|
|
|
|
|
|
|
|
|
|
irqflags_t flags = cpu_irq_save();
|
|
|
|
|
|
printf("=> UDD_Attach\r\n");
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
otg_unfreeze_clock();
|
|
|
|
// This section of clock check can be improved with a chek of
|
|
// USB clock source via sysclk()
|
|
// Check USB clock because the source can be a PLL
|
|
while (!Is_otg_clock_usable());
|
|
|
|
// Authorize attach if Vbus is present
|
|
udd_attach_device();
|
|
|
|
// Enable USB line events
|
|
udd_enable_reset_interrupt();
|
|
//udd_enable_suspend_interrupt();
|
|
//udd_enable_wake_up_interrupt();
|
|
|
|
|
|
//////////////udd_enable_sof_interrupt();
|
|
|
|
|
|
|
|
|
|
// Reset following interupts flag
|
|
//udd_ack_reset();
|
|
//udd_ack_sof();
|
|
|
|
|
|
// The first suspend interrupt must be forced
|
|
// The first suspend interrupt is not detected else raise it
|
|
//udd_raise_suspend();
|
|
|
|
//udd_ack_wake_up();
|
|
//otg_freeze_clock();
|
|
|
|
cpu_irq_restore(flags);
|
|
|
|
|
|
|
|
|
|
/*
|
|
otg_disable_id_pin();
|
|
otg_force_device_mode();
|
|
|
|
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_OTGPADE;
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_OTGPADE;
|
|
UOTGHS->UOTGHS_CTRL |= UOTGHS_CTRL_USBE;
|
|
UOTGHS->UOTGHS_CTRL &= ~UOTGHS_CTRL_FRZCLK;
|
|
|
|
udd_low_speed_disable();
|
|
udd_high_speed_disable();
|
|
|
|
|
|
UOTGHS->UOTGHS_DEVIER = (UOTGHS_DEVIER_EORSTES | UOTGHS_DEVIER_SOFES);
|
|
|
|
otg_ack_vbus_transition();
|
|
// Force Vbus interrupt in case of Vbus always with a high level
|
|
// This is possible with a short timing between a Host mode stop/start.
|
|
if (Is_otg_vbus_high()) {
|
|
otg_raise_vbus_transition();
|
|
}
|
|
otg_enable_vbus_interrupt();
|
|
otg_freeze_clock();
|
|
*/
|
|
|
|
}
|
|
|
|
void UDD_Detach(void)
|
|
{
|
|
printf("=> UDD_Detach\r\n");
|
|
UOTGHS->UOTGHS_DEVCTRL |= UOTGHS_DEVCTRL_DETACH;
|
|
}
|
|
|
|
void UDD_InitEP( uint32_t ul_ep_nb, uint32_t ul_ep_cfg )
|
|
{
|
|
printf("=> UDD_InitEP\r\n");
|
|
|
|
// Reset EP
|
|
UOTGHS->UOTGHS_DEVEPT = (UOTGHS_DEVEPT_EPRST0 << ul_ep_nb);
|
|
// Configure EP
|
|
UOTGHS->UOTGHS_DEVEPTCFG[ul_ep_nb] = ul_ep_cfg;
|
|
// Enable EP
|
|
UOTGHS->UOTGHS_DEVEPT = (UOTGHS_DEVEPT_EPEN0 << ul_ep_nb);
|
|
}
|
|
|
|
void UDD_InitEndpoints(const uint32_t* eps_table)
|
|
{
|
|
uint32_t ul_ep_nb ;
|
|
|
|
printf("=> UDD_InitEndpoints\r\n");
|
|
|
|
for (ul_ep_nb = 1; ul_ep_nb < sizeof(eps_table); ul_ep_nb++)
|
|
{
|
|
// Reset Endpoint Fifos
|
|
/* UOTGHS->UOTGHS_DEVEPTISR[ul_EP].UDPHS_EPTCLRSTA = UDPHS_EPTCLRSTA_TOGGLESQ | UDPHS_EPTCLRSTA_FRCESTALL;
|
|
UOTGHS->UOTGHS_DEVEPT = 1<<ul_EP;
|
|
|
|
//UECONX = 1;
|
|
//UECFG0X = pgm_read_byte(_initEndpoints+ul_EP);
|
|
UOTGHS->UDPHS_EPT[ul_EP].UDPHS_EPTCFG = _initEndpoints[ul_EP];
|
|
|
|
while( (signed int)UDPHS_EPTCFG_EPT_MAPD != (signed int)((UOTGHS->UDPHS_EPT[ul_EP].UDPHS_EPTCFG) & (unsigned int)UDPHS_EPTCFG_EPT_MAPD) )
|
|
;
|
|
UOTGHS->UDPHS_EPT[ul_EP].UDPHS_EPTCTLENB = UDPHS_EPTCTLENB_EPT_ENABL;
|
|
|
|
// UECFG1X = EP_DOUBLE_64;
|
|
}*/
|
|
|
|
// Reset EP
|
|
UOTGHS->UOTGHS_DEVEPT = (UOTGHS_DEVEPT_EPRST0 << ul_ep_nb);
|
|
// Configure EP
|
|
UOTGHS->UOTGHS_DEVEPTCFG[ul_ep_nb] = eps_table[ul_ep_nb];
|
|
// Enable EP
|
|
UOTGHS->UOTGHS_DEVEPT = (UOTGHS_DEVEPT_EPEN0 << ul_ep_nb);
|
|
}
|
|
}
|
|
|
|
void UDD_SetEP( uint32_t ep )
|
|
{
|
|
ul_ep = ep;
|
|
}
|
|
|
|
// Wait until ready to accept IN packet.
|
|
void UDD_WaitIN(void)
|
|
{
|
|
//while (!(UEINTX & (1<<TXINI)));
|
|
while (!(UOTGHS->UOTGHS_DEVEPTISR[ul_ep] & UOTGHS_DEVEPTISR_TXINI))
|
|
;
|
|
}
|
|
|
|
void UDD_WaitOUT(void)
|
|
{
|
|
//while (!(UEINTX & (1<<RXOUTI)));
|
|
while (!(UOTGHS->UOTGHS_DEVEPTISR[ul_ep] & UOTGHS_DEVEPTISR_RXOUTI))
|
|
;
|
|
}
|
|
|
|
uint32_t ul_send_index = 0;
|
|
uint32_t ul_rcv_index = 0;
|
|
|
|
// Send packet.
|
|
void UDD_ClearIN(void)
|
|
{
|
|
printf("=> UDD_ClearIN: sent %d bytes\r\n", ul_send_index);
|
|
// UEINTX = ~(1<<TXINI);
|
|
UOTGHS->UOTGHS_DEVEPTICR[ul_ep] = UOTGHS_DEVEPTICR_TXINIC;
|
|
ul_send_index = 0;
|
|
}
|
|
|
|
void UDD_ClearOUT(void)
|
|
{
|
|
// UEINTX = ~(1<<RXOUTI);
|
|
UOTGHS->UOTGHS_DEVEPTICR[ul_ep] = UOTGHS_DEVEPTICR_RXOUTIC;
|
|
ul_rcv_index = 0;
|
|
}
|
|
|
|
// Wait for IN FIFO to be ready to accept data or OUT FIFO to receive data.
|
|
// Return true if new IN FIFO buffer available.
|
|
uint32_t UDD_WaitForINOrOUT(void)
|
|
{
|
|
//while (!(UEINTX & ((1<<TXINI)|(1<<RXOUTI))));
|
|
//return (UEINTX & (1<<RXOUTI)) == 0;
|
|
while (!(UOTGHS->UOTGHS_DEVEPTISR[ul_ep] & (UOTGHS_DEVEPTISR_TXINI | UOTGHS_DEVEPTISR_RXOUTI)))
|
|
;
|
|
return ((UOTGHS->UOTGHS_DEVEPTISR[ul_ep] & UOTGHS_DEVEPTISR_RXOUTI) == 0);
|
|
}
|
|
|
|
uint32_t UDD_ReceivedSetupInt(void)
|
|
{
|
|
return UOTGHS->UOTGHS_DEVEPTISR[ul_ep] & UOTGHS_DEVEPTISR_RXSTPI;
|
|
}
|
|
|
|
void UDD_ClearSetupInt(void)
|
|
{
|
|
//UEINTX = ~((1<<RXSTPI) | (1<<RXOUTI) | (1<<TXINI));
|
|
//UOTGHS->UOTGHS_DEVEPTICR[ul_ep] = (UOTGHS_DEVEPTICR_RXSTPIC | UOTGHS_DEVEPTICR_RXOUTIC | UOTGHS_DEVEPTICR_TXINIC);
|
|
UOTGHS->UOTGHS_DEVEPTICR[ul_ep] = (UOTGHS_DEVEPTICR_RXSTPIC);
|
|
}
|
|
|
|
void UDD_Send8( uint8_t data )
|
|
{
|
|
uint8_t *ptr_dest = (uint8_t *) &udd_get_endpoint_fifo_access8(ul_ep);
|
|
|
|
printf("=> UDD_Send8 : ul_send_index=%d\r\n", ul_send_index);
|
|
ptr_dest[ul_send_index++] = data;
|
|
}
|
|
|
|
uint8_t UDD_Recv8(void)
|
|
{
|
|
uint8_t *ptr_dest = (uint8_t *) &udd_get_endpoint_fifo_access8(ul_ep);
|
|
|
|
return ptr_dest[ul_rcv_index++];
|
|
}
|
|
|
|
void UDD_Recv(volatile uint8_t* data, uint32_t count)
|
|
{
|
|
uint8_t *ptr_dest = (uint8_t *) &udd_get_endpoint_fifo_access8(ul_ep);
|
|
|
|
while (count--)
|
|
*data++ = ptr_dest[ul_rcv_index++];
|
|
}
|
|
|
|
void UDD_Stall(void)
|
|
{
|
|
//UECONX = (1<<STALLRQ) | (1<<EPEN);
|
|
UOTGHS->UOTGHS_DEVEPT = (UOTGHS_DEVEPT_EPEN0 << ul_ep);
|
|
UOTGHS->UOTGHS_DEVEPTIER[ul_ep] = UOTGHS_DEVEPTIER_STALLRQS;
|
|
}
|
|
|
|
|
|
uint32_t UDD_FifoByteCount(void)
|
|
{
|
|
return ((UOTGHS->UOTGHS_DEVEPTISR[ul_ep] & UOTGHS_DEVEPTISR_BYCT_Msk) >> UOTGHS_DEVEPTISR_BYCT_Pos);
|
|
}
|
|
|
|
void UDD_ReleaseRX(void)
|
|
{
|
|
/* UEINTX = 0x6B; // FIFOCON=0 NAKINI=1 RWAL=1 NAKOUTI=0 RXSTPI=1 RXOUTI=0 STALLEDI=1 TXINI=1
|
|
clear fifocon = send and switch bank
|
|
nakouti a clearer
|
|
rxouti/killbank a clearer*/
|
|
|
|
puts("=> UDD_ReleaseRX\r\n");
|
|
UOTGHS->UOTGHS_DEVEPTICR[ul_ep] = (UOTGHS_DEVEPTICR_NAKOUTIC | UOTGHS_DEVEPTICR_RXOUTIC);
|
|
UOTGHS->UOTGHS_DEVEPTIDR[ul_ep] = UOTGHS_DEVEPTIDR_FIFOCONC;
|
|
}
|
|
|
|
void UDD_ReleaseTX(void)
|
|
{
|
|
/* UEINTX = 0x3A; // FIFOCON=0 NAKINI=0 RWAL=1 NAKOUTI=1 RXSTPI=1 RXOUTI=0 STALLEDI=1 TXINI=0
|
|
clear fifocon = send and switch bank
|
|
nakini a clearer
|
|
rxouti/killbank a clearer
|
|
txini a clearer*/
|
|
|
|
puts("=> UDD_ReleaseTX\r\n");
|
|
UOTGHS->UOTGHS_DEVEPTICR[ul_ep] = (UOTGHS_DEVEPTICR_NAKINIC | UOTGHS_DEVEPTICR_RXOUTIC | UOTGHS_DEVEPTICR_TXINIC);
|
|
UOTGHS->UOTGHS_DEVEPTIDR[ul_ep] = UOTGHS_DEVEPTIDR_FIFOCONC;
|
|
}
|
|
|
|
uint32_t UDD_ReadWriteAllowed(void)
|
|
{
|
|
return (UOTGHS->UOTGHS_DEVEPTISR[ul_ep] & UOTGHS_DEVEPTISR_RWALL);
|
|
}
|
|
|
|
void UDD_SetAddress(uint32_t addr)
|
|
{
|
|
printf("=> UDD_SetAddress : setting address to %d\r\n", addr);
|
|
udd_configure_address(addr);
|
|
udd_enable_address();
|
|
}
|
|
|
|
uint32_t UDD_GetFrameNumber(void)
|
|
{
|
|
return udd_frame_number();
|
|
}
|
|
|
|
#endif /* SAM3XA_SERIES */
|